diff --git a/.gitignore b/.gitignore
index 4a9783d..1c5e235 100644
--- a/.gitignore
+++ b/.gitignore
@@ -50,6 +50,7 @@
 android/HeronAndroid/.externalNativeBuild/
 
 # release
+apache-weex-incubating-*
 apache_release_temp
 RELEASE_NOTE.md
 RELEASE_AUDIT.LOG
diff --git a/.rat-excludes b/.rat-excludes
index 45a4dce..6a131ce 100644
--- a/.rat-excludes
+++ b/.rat-excludes
@@ -1,11 +1,18 @@
-\.gitignore
-\.git/.*
-ios/playground 
-.rat-excludes
-build
-.*\.json
-Info\.plist
-.*\.xml
-.*\.pch
-main\.js
-\./ios/playground/Pods/.*
+index.js
+array.js
+dep.js
+object.js
+observer.js
+state.js
+watcher.js
+WXDataStructureUtil.java
+json11.cc
+json11.hpp
+modp_b64_data.h
+modp_b64.cc
+modp_b64.h
+icu_utf.h
+icu_utf.cpp
+jni_generator.py
+futex.h
+base64.hpp
\ No newline at end of file
diff --git a/.travis.yml b/.travis.yml
index d9f4191..6ecd0eb 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -7,6 +7,8 @@
       - env: TEST_SUITE=danger 
       - env: TEST_SUITE=jsfm
       - env: TEST_SUITE=ios
+        os: osx
+        osx_image: xcode11.2
         language: objective-c
       - env: TEST_SUITE=android ABI=armeabi-v7a
         language: android
@@ -34,7 +36,8 @@
             - extra-android-m2repository 
       # static check
       - env: TEST_SUITE=static_code_analysis OCLINT=true
-        osx_image: xcode7.2
+        os: osx
+        osx_image: xcode11.2
         language: objective-c
       - env: TEST_SUITE=static_code_analysis ANDROID_LINT=true
         language: android
@@ -112,7 +115,7 @@
         git submodule update --init --remote
         cd weex-playground/ios && bash update_podfile_for_travisci.sh
         cd ../../ && npm install
-        cd weex-playground/ios && pod install --repo-update
+        cd weex-playground/ios && bundle install && pod install --repo-update
         cd ../../
     fi
     
@@ -137,8 +140,10 @@
         esac
         if npm run danger -- ci --dangerfile ./dangerfile-android.js | grep -q "hasAndroidFile" ; then
           cd android
-          ./gradlew clean assembleRelease -PbuildRuntimeApi=true ${GRADLE_ABI} --info || exit 1
-          ./gradlew assembleRelease -PbuildRuntimeApi=false ${GRADLE_ABI} --info || exit 1
+          ./gradlew clean assembleRelease --quiet -PbuildRuntimeApi=true ${GRADLE_ABI} -PapachePackageName="false" || exit 1
+          ./gradlew assembleRelease --quiet ${GRADLE_ABI} -PbuildRuntimeApi=false -Pjsc_url="https://raw.githubusercontent.com/apache/incubator-weex/release/0.26/android/sdk/weex_sdk-0.26.0.aar" -Paar_name="weex_sdk" -PJSInterpolatorName="JavaScriptCore" -PapachePackageName="false" || exit 1
+          ./gradlew :weex_sdk:assembleRelease --quiet -PbuildRuntimeApi=true ${GRADLE_ABI} -PapachePackageName="true" || exit 1
+          ./gradlew :weex_sdk:assembleRelease --quiet  ${GRADLE_ABI} -PbuildRuntimeApi=false -Pjsc_url="https://raw.githubusercontent.com/apache/incubator-weex/release/0.26/android/sdk/weex_sdk-0.26.0.aar" -Paar_name="weex_sdk" -PJSInterpolatorName="JavaScriptCore" -PapachePackageName="true" || exit 1
         fi
         ;;
       "jsfm" )
@@ -188,7 +193,8 @@
       if npm run danger -- ci --dangerfile ./dangerfile-static-check.js | grep -q "hasAndroidFile" ; then
         echo "hasAndroidFile"
         cd android
-        ./gradlew :weex_sdk:lint --quiet
+        ./gradlew :weex_sdk:lintLegacyRelease -PapachePackageName="false" --quiet
+        ./gradlew :weex_sdk:lintApacheRelease -PapachePackageName="true" --quiet
         export TITLE="AndroidLint Result"
         cd ../ && npm run danger -- ci -i androidlint --dangerfile ./dangerfile-output.js || exit 1
       fi
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 5775a3e..e84c768 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -4,6 +4,8 @@
 * Unified C++ log system of WeexCore.
 
 ### Android
-*  Upgrade targetsdk & compilesdk to 28
+* Upgrade targetsdk & compilesdk to 28
+* Change Android package name from `com.taobao.weex` to `org.apache.weex`, ref [link](https://github.com/apache/incubator-weex/tree/master/android#build-types)
+* Switch to BSD-Licensed [android-jsc](https://www.npmjs.com/package/jsc-android) as the default JavaScript Interpreter.
 
 ## Main Bugfix
diff --git a/HOW-TO-BUILD.md b/HOW-TO-BUILD.md
index a07099f..ee73899 100644
--- a/HOW-TO-BUILD.md
+++ b/HOW-TO-BUILD.md
@@ -1,5 +1,5 @@
 # Weex Apache Source Release
-Weex produce SDKs to integrate with iOS/Android/Mobile web applications. This file will cover how to build Weex from source. You can either use the script we provided or manually build from source step by step.
+Weex produce SDKs to integrate with iOS/Android/Mobile web applications. This file will cover how to build Weex from command line. You can either use the script we provided or manually build from source step by step.
 See `README.md` for further information about the Weex Framework.
 
 Weex SDK includes 3 different SDKs to use in corresponding system/browser:
@@ -9,32 +9,36 @@
 
 See our [guide in our website](http://weex.apache.org/guide/integrate-to-your-app.html) to learn more about how to integrate Weex SDK into your app.
 
-## Build Environment
-The environment required to build weex is:
-* Android SDK:
-    * NodeJS 4.0+
-    * JDK 1.6+
-    * Android SDK(`$ANDROID_HOME` must be set properly)
-    * Gradle 2.0+
-    * NDK r18 and ndk 13 (**Both of them are needed**)
-    * [Ninja 1.8.2+](https://ninja-build.org/)
-    * CMake 3.9.0+
-* iOS SDK:
-    * NodeJS 4.0+
-    * XCode & Command Tools 8.0+
-* Mobile web SDK:
-    * NodeJS 4.0+
+# Build Environment
+The environment required to build weex is categorized by platforms.
+
+## Android
+* JDK `1.8+`
+* Android SDK Platform 28
+  * `ANDROID_HOME` must be configured by using `export ANDROID_HOME=/path_to_sdk`
+  * Normally, you should install [Android Studio](https://developer.android.com/studio) to get Android SDK Platform 28 installed.
+* Gradle 4.10+
+* NDK `r18`
+  * `ANDROID_NDK_HOME` must be configured by using `export ANDROID_NDK_HOME=/path_to_ndk`
+  * Higher version of NDK than `r18` isn't not tested yet.
+* CMake 3.4.1+
+
+## iOS
+* Install [iOS Environment](https://developer.apple.com/library/ios/documentation/IDEs/Conceptual/AppStoreDistributionTutorial/Setup/Setup.html)
+* Install [CocoaPods](https://guides.cocoapods.org/using/getting-started.html)
+* XCode Command Tools 8.0+
+
+## Mobile
+* NodeJS 4.0+
 
 This article was tested in MacOSX system.
 
 # Build All by Script
 
 This script will build Android and iOS SDKs:
-> `$ bash scripts/build_from_source.sh $NDK13_dir $NDK_16dir`
+> `$ bash scripts/build_from_source.sh `
 
-The `$NDK18_dir` should be the directory of NDK 18, otherwise the Android build would failed.
-
-This may take a while. After that, you can look in `dist/`, `android/sdk/build/output/` and `ios/sdk/Products` for Web/Android/iOS SDK artifacts.
+This may take a while. After that, you can look in `dist/`, `android/sdk/build/outputs/aar` and `ios/sdk/Products` for Web / Android / iOS SDK artifacts.
 
 # Build for Platforms
 
@@ -53,37 +57,25 @@
 
 ### Before build Native SDK
 Move `min` version to Native SDK folder, which will be used by native SDK build.
-> `cp packages/weex-js-framework/index.min.js ios_sdk/WeexSDK/Resources/main.js`
-> `cp packages/weex-js-framework/index.min.js android_sdk/assets/main.js`
+
+```
+cp packages/weex-js-framework/index.min.js ios/sdk/WeexSDK/Resources/main.js
+cp packages/weex-js-framework/index.min.js android/sdk/assets/main.js
+```
 
 ## Build Android SDK
+1. Install the [Android environment](#android).
+2. Execute the following command
 
-check env
+    ```
+    cd android
+    ./gradlew :weex_sdk:clean :weex_sdk:assembleRelease
+    ```
 
-- you have gradle installed, see more details about 'how to install gradle' on the [gradle website](https://gradle.org/install).
-- [NDK r18](https://developer.android.com/ndk/downloads/older_releases.html)
-- edit local.propteries (in `Android` dir)
-
-	```
-	ndk.dir=/Users/{user}/Library/Android/sdk/ndk-bundle-r18
-	sdk.dir=/Users/{user}/Library/Android/sdk
-	```
-
-then do buid
-
-> cd Android/sdk
-
-> ../gradlew clean assemble
-
-
-artifacts path:
-
-` android/sdk/build/outputs/aar`
-
-You can now import the aar file to your android project.
+3. Output can be found at `android/sdk/build/outputs/aar`
 
 ## Build iOS SDK
 Execute command below to compile iOS SDK:
-> `$ xcodebuild -project ios_sdk/WeexSDK.xcodeproj -target WeexSDK_MTL`
+> `$ xcodebuild -project ios/sdk/WeexSDK.xcodeproj -target WeexSDK_MTL`
 
 Then you'll find the iOS library(Framework file) under `ios_sdk/Products`.
diff --git a/LICENSE b/LICENSE
index 8cf0003..4d5db27 100644
--- a/LICENSE
+++ b/LICENSE
@@ -187,7 +187,7 @@
       same "printed page" as the copyright notice for easier
       identification within third-party archives.
 
-   Copyright [yyyy] [name of copyright owner]
+   Copyright 2019 Apache Weex (Incubating)
 
    Licensed under the Apache License, Version 2.0 (the "License");
    you may not use this file except in compliance with the License.
@@ -244,10 +244,9 @@
 
 
 This product bundles Guava v20.0, which is available under a "Apache" license. For details, see https://github.com/google/guava/blob/v20.0/COPYING and following files:
-  android_sdk/src/main/java/org/apache/taobao/weex/utils/WXDataStructureUtil.java
+  android/sdk/src/main/java/org/apache/weex/utils/WXDataStructureUtil.java
 
 This product bundles json11 v1.0.0, which is available under a "MIT" license. For details, see https://github.com/dropbox/json11/tree/v1.0.0 and following files:
-   weex_core/Source/third_party/json11/CMakeLists.txt
    weex_core/Source/third_party/json11/json11.cc
    weex_core/Source/third_party/json11/json11.hpp
 
@@ -408,305 +407,6 @@
 This product bundles Android Open Source Project vandroid-4.2.2_r1, which is available under a "BSD" license. For details, see https://android.googlesource.com/platform/bionic/+/android-4.2.2_r1/libc/README and following files:
   weex_core/Source/IPC/futex.h
 
-This product bundles Webkit 2.17.4, which is available under a "BSD-style" license. For details, reference https://webkit.org/licensing-webkit/ for license and see https://svn.webkit.org/repository/webkit/releases/WebKitGTK/webkit-2.17.4 for following files:
-
-   Bmalloc in WebKit:
-      weex_core/Source/android/jsengine/dependence/bmalloc:
-         CMakeLists.txt
-         ChangeLog
-         Makefile
-
-      weex_core/Source/android/jsengine/dependence/bmalloc/Configurations:
-         Base.xcconfig
-         DebugRelease.xcconfig
-         bmalloc.xcconfig
-         mbmalloc.xcconfig
-
-      weex_core/Source/android/jsengine/dependence/bmalloc/bmalloc:
-         Algorithm.h
-         Allocator.cpp
-         Allocator.h
-         AsyncTask.h
-         AvailableMemory.cpp
-         AvailableMemory.h
-         BAssert.h
-         BPlatform.h
-         BumpAllocator.h
-         BumpRange.h
-         Cache.cpp
-         Cache.h
-         Chunk.h
-         Deallocator.cpp
-         Deallocator.h
-         DebugHeap.cpp
-         DebugHeap.h
-         Environment.cpp
-         Environment.h
-         FixedVector.h
-         Heap.cpp
-         Heap.h
-         Inline.h
-         LargeMap.cpp
-         LargeMap.h
-         LargeRange.h
-         LineMetadata.h
-         List.h
-         Logging.cpp
-         Logging.h
-         Map.h
-         Mutex.h
-         Object.h
-         ObjectType.cpp
-         ObjectType.h
-         PerProcess.h
-         PerThread.h
-         Range.h
-         ScopeExit.h
-         Sizes.h
-         SmallLine.h
-         SmallPage.h
-         StaticMutex.cpp
-         StaticMutex.h
-         Syscall.h
-         VMAllocate.h
-         VMHeap.cpp
-         VMHeap.h
-         Vector.h
-         Zone.cpp
-         Zone.h
-         bmalloc.h
-         mbmalloc.cpp
-
-      weex_core/Source/android/jsengine/dependence/bmalloc/bmalloc/darwin:
-         BSoftLinking.h
-
-      weex_core/Source/android/jsengine/dependence/bmalloc/bmalloc.xcodeproj:
-         project.pbxproj
-
-   ICU in WebKit:
-      weex_core/Source/android/jsengine/dependence/icu:
-         LICENSE
-         README
-
-      weex_core/Source/android/jsengine/dependence/icu/unicode:
-         localpointer.h
-         parseerr.h
-         platform.h
-         ptypes.h
-         putil.h
-         ucal.h
-         uchar.h
-         ucnv.h
-         ucnv_err.h
-         ucol.h
-         uconfig.h
-         ucurr.h
-         udat.h
-         udatpg.h
-         udisplaycontext.h
-         uenum.h
-         uformattable.h
-         uiter.h
-         uloc.h
-         umachine.h
-         umisc.h
-         unorm.h
-         unorm2.h
-         unum.h
-         unumsys.h
-         urename.h
-         uscript.h
-         uset.h
-         ustring.h
-         utf.h
-         utf16.h
-         utf8.h
-         utf_old.h
-         utypes.h
-         uvernum.h
-         uversion.h
-   
-   JavaScriptCore in WebKit:
-      weex_core/Source/include/JavaScriptCore/API:
-         APICallbackFunction.h
-         APICast.h
-         APIUtils.h
-         JSAPIWrapperObject.h
-         JSBase.h
-         JSBasePrivate.h
-         JSCTestRunnerUtils.h
-         JSCallbackConstructor.h
-         JSCallbackFunction.h
-         JSCallbackObject.h
-         JSCallbackObjectFunctions.h
-         JSClassRef.h
-         JSContext.h
-         JSContextInternal.h
-         JSContextPrivate.h
-         JSContextRef.h
-         JSContextRefInspectorSupport.h
-         JSContextRefInternal.h
-         JSContextRefPrivate.h
-         JSExport.h
-         JSManagedValue.h
-         JSManagedValueInternal.h
-         JSObjectRef.h
-         JSObjectRefPrivate.h
-         JSRemoteInspector.h
-         JSRetainPtr.h
-         JSScriptRefPrivate.h
-         JSStringRef.h
-         JSStringRefBSTR.h
-         JSStringRefCF.h
-         JSStringRefPrivate.h
-         JSTypedArray.h
-         JSValue.h
-         JSValueInternal.h
-         JSValueRef.h
-         JSVirtualMachine.h
-         JSVirtualMachineInternal.h
-         JSWeakObjectMapRefInternal.h
-         JSWeakObjectMapRefPrivate.h
-         JSWrapperMap.h
-         JavaScript.h
-         JavaScriptCore.h
-         ObjCCallbackFunction.h
-         ObjcRuntimeExtras.h
-         OpaqueJSString.h
-         WebKitAvailability.h
-
-      weex_core/Source/include/JavaScriptCore/ForwardingHeaders/JavaScriptCore:
-         APICast.h
-         JSBase.h
-         JSCTestRunnerUtils.h
-         JSContextRef.h
-         JSObjectRef.h
-         JSObjectRefPrivate.h
-         JSRetainPtr.h
-         JSStringRef.h
-         JSStringRefCF.h
-         JSTypedArray.h
-         JSValueRef.h
-         JavaScript.h
-         JavaScriptCore.h
-         OpaqueJSString.h
-         WebKitAvailability.h
-
-   Other files in Webkit:
-      weex_core/Source/android/jsengine/dependence:
-         OptionsCommon.cmake
-         OptionsJSCOnly.cmake
-
-   The copyright for files above is listed below:
-      weex_core/Source/android/jsengine/dependence/icu:
-         COPYRIGHT AND PERMISSION NOTICE
-
-         Copyright (c) 1995-2006 International Business Machines Corporation and others
-
-         All rights reserved.
-
-         Permission is hereby granted, free of charge, to any person obtaining a copy of this
-         software and associated documentation files (the "Software"), to deal in the Software
-         without restriction, including without limitation the rights to use, copy, modify,
-         merge, publish, distribute, and/or sell copies of the Software, and to permit persons
-         to whom the Software is furnished to do so, provided that the above copyright notice(s)
-         and this permission notice appear in all copies of the Software and that both the above
-         copyright notice(s) and this permission notice appear in supporting documentation.
-
-         THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
-         INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
-         PURPOSE AND NONINFRINGEMENT OF THIRD PARTY RIGHTS. IN NO EVENT SHALL THE COPYRIGHT HOLDER
-         OR HOLDERS INCLUDED IN THIS NOTICE BE LIABLE FOR ANY CLAIM, OR ANY SPECIAL INDIRECT OR
-         CONSEQUENTIAL DAMAGES, OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
-         PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
-         OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-
-         Except as contained in this notice, the name of a copyright holder shall not be used in
-         advertising or otherwise to promote the sale, use or other dealings in this Software
-         without prior written authorization of the copyright holder.
-      
-      weex_core/Source/include/JavaScriptCore:
-
-         /*
-         * Copyright (C) 2005, 2006, 2007, 2010 Apple Inc. All rights reserved.
-         * Copyright (C) 2006 Apple Inc.  All rights reserved.
-         * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
-         * Copyright (C) 2006, 2008 Apple Inc. All rights reserved.
-         * Copyright (C) 2006, 2008, 2016 Apple Inc. All rights reserved.
-         * Copyright (C) 2006-2016 Apple Inc. All rights reserved.
-         * Copyright (C) 2007 Apple Inc.  All rights reserved.
-         * Copyright (C) 2008 Apple Inc.  All rights reserved.
-         * Copyright (C) 2008, 2009, 2010, 2014 Apple Inc. All Rights Reserved.
-         * Copyright (C) 2009 Apple Inc.  All rights reserved.
-         * Copyright (C) 2010 Apple Inc. All rights reserved.
-         * Copyright (C) 2012 Apple Inc. All rights reserved.
-         * Copyright (C) 2013 Apple Inc. All rights reserved.
-         * Copyright (C) 2013, 2016 Apple Inc. All rights reserved.
-         * Copyright (C) 2013, 2017 Apple Inc. All rights reserved.
-         * Copyright (C) 2014 Apple Inc. All rights reserved.
-         * Copyright (C) 2015 Apple Inc.  All rights reserved.
-         * Copyright (C) 2015-2016 Apple Inc. All rights reserved.
-         * Copyright (C) 2016 Apple Inc. All rights reserved.
-         * Copyright (C) 2007 Eric Seidel <eric@webkit.org>
-         * Copyright (C) 2007 Eric Seidel <eric@webkit.org>
-         * Copyright (C) 2008 Alp Toker <alp@atoker.com>
-         * Copyright (C) 2008 Kelvin W Sherlock (ksherlock@gmail.com)
-         * Copyright (C) 2015 Dominic Szablewski (dominic@phoboslab.org)
-         *
-         * Redistribution and use in source and binary forms, with or without
-         * modification, are permitted provided that the following conditions
-         * are met:
-         * 1. Redistributions of source code must retain the above copyright
-         *    notice, this list of conditions and the following disclaimer.
-         * 2. Redistributions in binary form must reproduce the above copyright
-         *    notice, this list of conditions and the following disclaimer in the
-         *    documentation and/or other materials provided with the distribution.
-         *
-         * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
-         * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
-         * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
-         * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
-         * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
-         * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
-         * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
-         * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
-         * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-         * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-         * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
-         */
-
-         weex_core/Source/android/jsengine/dependence/bmalloc:
-
-         /*
-         * Copyright (C) 2007, 2008, 2011-2016 Apple Inc. All rights reserved.
-         * Copyright (C) 2012-2017 Apple Inc. All rights reserved.
-         * Copyright (C) 2014 Apple Inc. All rights reserved.
-         * Copyright (C) 2014, 2015 Apple Inc. All rights reserved.
-         * Copyright (C) 2014, 2016 Apple Inc. All rights reserved.
-         * Copyright (C) 2014-2016 Apple Inc. All rights reserved.
-         * Copyright (C) 2016 Apple Inc. All rights reserved.
-         *
-         * Redistribution and use in source and binary forms, with or without
-         * modification, are permitted provided that the following conditions
-         * are met:
-         * 1.  Redistributions of source code must retain the above copyright
-         *     notice, this list of conditions and the following disclaimer.
-         * 2.  Redistributions in binary form must reproduce the above copyright
-         *     notice, this list of conditions and the following disclaimer in the
-         *     documentation and/or other materials provided with the distribution.
-         *
-         * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND ANY
-         * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
-         * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
-         * DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY
-         * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
-         * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
-         * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
-         * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-         * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
-         * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-         */
-
 This product bundles files from Boost under "Boost Software License". For more details, reference http://www.boost.org/LICENSE_1_0.txt
   weex_core/Source/js_runtime/utils/base64.hpp
 
diff --git a/NOTICE b/NOTICE
index 81c698c..ea6b3ac 100644
--- a/NOTICE
+++ b/NOTICE
@@ -1,4 +1,4 @@
-Apache Weex
+Apache Weex (Incubating)
 Copyright 2019 The Apache Software Foundation
 
 This product includes software developed at
diff --git a/POSSIBLE-NOTICES-FOR-BIN-DIST b/POSSIBLE-NOTICES-FOR-BIN-DIST
deleted file mode 100644
index a0e2329..0000000
--- a/POSSIBLE-NOTICES-FOR-BIN-DIST
+++ /dev/null
@@ -1,98 +0,0 @@
-Apache Weex
-Copyright 2018 The Apache Software Foundation
-
-This product includes software developed at
-The Apache Software Foundation (http://www.apache.org/).
-
-This product contains software semver(http://semver.org/) developed
-by Tom Preston-Werner , licensed under the Creative Commons - CC BY 3.0 License.
-
-This product contains software core-js(https://github.com/zloirock/core-js) developed
-by Denis Pushkarev , licensed under the MIT License.
-
-This product contains software weex-rax-framework(https://github.com/alibaba/rax) developed
-by yuanyan  , licensed under the BSD-3-Clause License.
-
-This product contains software weex-vue-framework(https://github.com/vuejs/vue) developed
-by fkysly  , licensed under the MIT License.
-
-This product contains software weex-vue-render(https://github.com/weexteam/weex-vue-render) developed
-by MrRaindrop  , licensed under the Apache 2.0 License.
-
-This product contains software weex-styler(https://github.com/weexteam/weex-styler) developed
-by songsiqi  , licensed under the MIT License.
-
-This product contains software vuejs(https://github.com/vuejs/vue) developed
-by Yuxi Evan You , licensed under the MIT License.
-
-This product contains software fastjson(https://github.com/alibaba/fastjson) developed
-by alibaba inc.  , licensed under the Apache 2.0 License.
-
-This product contains software dexposed(https://github.com/alibaba/dexposed) developed
-by alibaba inc.  , licensed under the Apache 2.0 License.
-
-This product contains software js_engine(https://github.com/alibaba/weex_js_engine/) developed
-by alibaba inc.  , licensed under the Apache 2.0 License.
-
-This product contains software bindingX(https://github.com/alibaba/bindingx) developed
-by alibaba inc.  , licensed under the Apache 2.0 License.
-
-This product contains software loopj(https://github.com/loopj/android-async-http) developed
-by loopj , licensed under the Apache 2.0 License.
-
-This product contains software fresco(https://github.com/facebook/fresco) developed
-by facebook , licensed under the BSD-3-Clause License.
-
-This product contains software animated-gif(https://github.com/facebook/fresco) developed
-by facebook , licensed under the BSD-3-Clause License.
-
-This product contains software SocketRocket(https://github.com/facebook/SocketRocket) developed
-by facebook , licensed under the BSD-3-Clause License.
-
-This product contains software zxing(https://github.com/zxing/zxing) developed
-by zxing , licensed under the Apache 2.0 License.
-
-This product contains software okhttp(https://github.com/square/okhttp) developed
-by square , licensed under the Apache 2.0 License.
-
-This product contains software okio(https://github.com/square/okio) developed
-by square , licensed under the Apache 2.0 License.
-
-This product contains software scalpel(https://github.com/JakeWharton/scalpel) developed
-by Jake Wharton , licensed under the Apache 2.0 License.
-
-This product contains software espresso-idling-resource(https://google.github.io/android-testing-support-library/docs/espresso/idling-resource/) developed
-by google , licensed under the Apache 2.0 License.
-
-This product contains software AOSP(https://source.android.com/) developed
-by The Android Open Source Project , licensed under the Apache 2.0 License.
-
-This product contains software SDWebImage(https://github.com/rs/SDWebImage) developed
-by Olivier Poitrey  , licensed under the MIT License.
-
-This product contains software Guava(https://github.com/google/guava) developed
-by google  , licensed under the Apache License.
-
-This product contains shelljs Guava(https://github.com/shelljs/shelljs) developed
-by shelljs  , licensed under BSD 3-clause "New" or "Revised" License.
-
-This product contains software fpconv(https://github.com/night-shift/fpconv) developed
-by night-shift  , licensed under the MIT License.
-
-This product contains software rapidjson(https://github.com/Tencent/rapidjson) developed
-by tencent  , licensed under the MIT License.
-
-This product contains software flexbox-layout(https://github.com/google/flexbox-layout) developed
-by google  , licensed under the Apache License.
-
-This product contains software IPC(https://source.android.com/) developed
-by google  , licensed under the Apache License.
-
-This product contains software JNI(https://chromium.googlesource.com/) developed
-by google, licensed under the BSD-style License.
-
-This product contains software modp(http://modp.com/release/base64) developed
-by modp, licensed under the BSD-style License.
-
-This product contains software jni_generator(https://chromium.googlesource.com/) developed
-by google, licensed under the BSD-style License.
diff --git a/README.md b/README.md
index 5ff48fe..7770d94 100644
--- a/README.md
+++ b/README.md
@@ -4,24 +4,35 @@
 
 [![Build Status](https://travis-ci.org/apache/incubator-weex.svg?branch=master)](https://travis-ci.org/apache/incubator-weex/)
 
+## Join Us
+**Join us through [mailing list](https://weex.apache.org/guide/contribute/how-to-contribute.html#mailing-list).**
+
+## Convenience Distribution 
+**Since 0.28.0, Weex would publish two convince binary in each release for Android, please [read the documentation about the detail](major_change.html).**
+
+**Please take the above link seriously, otherwise you would be able to use the latest version of Weex.**
+
 | platform | status |
 | -------- | ------ |
-| Android | [![Download](https://api.bintray.com/packages/alibabaweex/maven/weex_sdk/images/download.svg)](https://bintray.com/alibabaweex/maven/weex_sdk/_latestVersion) |
+| Android | [sdk ![Download](https://api.bintray.com/packages/weex/Android/sdk/images/download.svg)](https://bintray.com/weex/Android/sdk/_latestVersion) Or [sdk_legacy ![Download](https://api.bintray.com/packages/weex/Android/sdk_legacy/images/download.svg)](https://bintray.com/weex/Android/sdk_legacy/_latestVersion) |
 | iOS | [![Pod version](https://badge.fury.io/co/WeexSDK.svg)](https://cocoapods.org/pods/WeexSDK) [![Carthage compatible](https://img.shields.io/badge/Carthage-compatible-4BC51D.svg?style=flat)](https://github.com/Carthage/Carthage) |
-| [Mobile Web](https://github.com/weexteam/weex-vue-render) | [![npm version](https://badge.fury.io/js/weex-html5.svg)](https://www.npmjs.com/package/weex-vue-render) |
+| [Mobile Web](https://github.com/weexteam/vue-render-for-apache-weex) | [![npm version](https://badge.fury.io/js/weex-vue-render.svg)](https://www.npmjs.com/package/weex-vue-render) |
 
 Support Android 4.1 (API 16), iOS 8.0+ and WebKit 534.30+.
 
-**Note: Please note the above download distribution is only for users' users' convenience. Weex Release is always in the format of [source code](https://weex.apache.org/download/download.html).**
+**FYI: The [mobile web render](https://github.com/weexteam/vue-render-for-apache-weex) is not supported by Apache Weex officially**
 
 ## For Windows
+First of all, compiling or building Weex from Windows is not support officially.
 
-Please ***INSTALL [Git for Windows](https://git-scm.com/download/win)*** and run all the following commands in git-bash.
+You could install [Git for Windows](https://git-scm.com/download/win) and run all the following commands in git-bash.
+
+Good Luck.
 
 ## Meet Weex
 
-* Install [Weex Playground App](https://weex.apache.org/tools/playground.html) to see examples we already written.
-* If you want to write a demo, install [weex-toolkit](https://www.npmjs.com/package/weex-toolkit) in [Node.js](http://nodejs.org/) 8.0+ and
+* Install [Weex Playground](https://weex.apache.org/tools/playground.html) to see examples we already written.
+* If you want to write a demo, install [weex-cli](https://www.npmjs.com/package/weex-toolkit) in [Node.js](http://nodejs.org/) 8.0+ and
 * Run `weex init` to generate & start a simple project in an empty folder.
 * Follow the instructions in the project README.
 * Enjoy it.
@@ -32,41 +43,29 @@
 * [Documents](http://weex.apache.org/references)
 
 ### Android
+**You should install [android environment](./HOW-TO-BUILD.md#android) before building.**
 
-* Prerequisites
-  * Install [Node.js](http://nodejs.org/) 8.0+
-  * Under project root
-    * `npm install`, install project
-    * `./start`
-    * Install [Android Environment](http://developer.android.com/training/basics/firstapp/index.html)
-    * Install [NDK](https://developer.android.com/ndk/) r18
-    * Install [Cmake](https://cmake.org/download/) 3.9.0+
-* Run playground, In Android Studio
-    * Open `android/playground`
-    * In `app/java/com.alibaba.weex/IndexActivity`, modify `CURRENT_IP` to your local IP
-    * Click <img src="http://gtms04.alicdn.com/tps/i4/TB1wCcqMpXXXXakXpXX3G7tGXXX-34-44.png" height="16" > (`Run` button)
-* [Add an example](./examples/README.md#add-an-example)
+You can either build Weex from IDE (*Android Studio*) or command line.
 
-#### Runtime
+#### Build From Android Studio
+1. Open `android` directory in Android Studio.
+2. Run `git submodule update --init --remote` in `android` directory if this is the first time you try to run Weex.
 
-On Android Platform , Weex code is executed in [weex_js_engine](https://github.com/alibaba/weex_js_engine/tree/bridge_branch_mergeTimer) which is based on JavaScriptCore engine.
+#### Build From Command Line
+Please read [How To Build](./HOW-TO-BUILD.md) for detail.
 
 ### iOS
-* run playground
-  * Prerequisites
-    * Install [Node.js](http://nodejs.org/) 8.0+
-      * Under project root
-          * `npm install`, install project
-          * `./start`
-      * Install [iOS Environment](https://developer.apple.com/library/ios/documentation/IDEs/Conceptual/AppStoreDistributionTutorial/Setup/Setup.html)
-      * Install [CocoaPods](https://guides.cocoapods.org/using/getting-started.html)
-  * Run playground
-      * `cd ios/playground`
-      * `pod install`
-      * Open `WeexDemo.xcworkspace` in Xcode
-      * Click <img src="http://img1.tbcdn.cn/L1/461/1/5470b677a2f2eaaecf412cc55eeae062dbc275f9" height="16" > (`Run` button) or use default shortcut `cmd + r` in Xcode
-      * If you want to run the demo on your device, don't need to modify `CURRENT_IP` manually. ~~In `DemoDefine.h`(you can search this file by Xcode default shortcut `cmd + shift + o`), modify `CURRENT_IP` to your local IP~~
-  * [Add an example](./examples/README.md#add-an-example)
+**You should install [iOS environment](./HOW-TO-BUILD.md#ios) before building.**
+
+You can either build Weex from IDE (*XCode*) or command line.
+
+#### Build From XCode
+* Run playground
+  * `cd ios/playground`
+  * `pod install`
+  * Open `WeexDemo.xcworkspace` in Xcode
+  * Click <img src="http://img1.tbcdn.cn/L1/461/1/5470b677a2f2eaaecf412cc55eeae062dbc275f9" height="16" > (`Run` button) or use default shortcut `cmd + r` in Xcode
+  * If you want to run the demo on your device, don't need to modify `CURRENT_IP` manually. ~~In `DemoDefine.h`(you can search this file by Xcode default shortcut `cmd + shift + o`), modify `CURRENT_IP` to your local IP~~
 * integrate to your application
 
   - **[CocoaPods](https://cocoapods.org)**
@@ -85,19 +84,20 @@
    ```
    Run `carthage update`, and you should now have the latest version of   `WeexSDK` in your `Carthage` folder.
 
+#### Build From Command Line
+Please read [How To Build](./HOW-TO-BUILD.md) for detail.
+
 ### Mobile Web
+**Vue Render for Apache Weex is a third party plugin, and not developed nor maintained by Apache Weex.**
 
-see [weex-vue-render](https://github.com/weexteam/weex-vue-render).
+see [Vue Render for Apache Weex](https://github.com/weexteam/vue-render-for-apache-weex).
 
-## Scripts
+## Third part plugin
+There is a third party plugin provides for debugging purpose.
+* [Android](https://weex.apache.org/guide/debug/integrate-devtool-to-android.html)
+* [iOS](https://weex.apache.org/guide/debug/integrate-devtool-to-ios.html)
 
-See [SCRIPTS.md](./SCRIPTS.md) for more information.
-
-## IDE Plugin & Syntax Highlight & DevTool
-
-Weex team have developed a [DevTool](https://github.com/weexteam/weex-devtool) to help you to improve the debugging efficiency.
-
-See more stuff on [this wiki page](https://github.com/alibaba/weex/wiki/Weex-Community)
+You can also view this page for all [third party plugin](https://weex.apache.org/tools).
 
 ## Weex Community
 * [Mailing List](https://weex.apache.org/guide/contribute/how-to-contribute.html#mailing-list) Weex Mailing List, where most discussion happens.
diff --git a/WeexSDK.podspec b/WeexSDK.podspec
index af264dd..050e37f 100644
--- a/WeexSDK.podspec
+++ b/WeexSDK.podspec
@@ -4,7 +4,7 @@
 
   s.name         = "WeexSDK"
 
-  s.version      = "0.26.0"
+  s.version      = "0.28.0"
 
   s.summary      = "WeexSDK Source."
 
@@ -12,21 +12,12 @@
                    A framework for building Mobile cross-platform UI
                    DESC
 
-  s.homepage     = "https://github.com/alibaba/weex"
+  s.homepage     = "https://github.com/apache/incubator-weex"
   s.license = {
-    :type => 'Copyright',
-    :text => <<-LICENSE
-           Alibaba-INC copyright
-    LICENSE
+    :type => 'Apache-2.0'
   }
   s.authors      = {
-                    "cxfeng1"      => "cxfeng1@gmail.com",
-                    "boboning"     => "ningli928@163.com",
-                    "yangshengtao" => "yangshengtao1314@163.com",
-                    "kfeagle"      => "sunjjbobo@163.com",
-                    "acton393"     => "zhangxing610321@gmail.com",
-                    "wqyfavor"     => "wqyfavor88@gmail.com",
-                    "doumafang "   => "doumafang@gmail.com"
+                    "dev" => "dev@weex.apache.org"
                    }
   s.platform     = :ios
   s.ios.deployment_target = '9.0'
@@ -132,4 +123,4 @@
   
   s.libraries = 'c++'
 
-end
\ No newline at end of file
+end
diff --git a/android/README.md b/android/README.md
index 29507f8..c88cff2 100644
--- a/android/README.md
+++ b/android/README.md
@@ -2,8 +2,28 @@
 ## Install gradlew   
   See https://gradle.org/install#with-a-package-manager
 ## Build Weex   
-run `gradle build`   
-Playground app artifact will be under 'playground/build'
+run `./gradlew clean assembleRelease` to build `weex_sdk`
+
+### Build Types
+For historical reason, the java files of weex_sdk was under the package name of `com.taobao.weex`, despite the fact that they are under `org.apache.weex` now.
+
+In order to provide backward compatibility for users, there are two type of convince binary of Weex generated by different building argument.
+
+#### weex_sdk
+`weex_sdk` is the library we give officially support now, where all java files in `.aar` is under `org.apache.weex`.
+
+New users of Weex should always choose `weex_sdk`, while for existing users, using `weex_sdk` could cause compiling issues and you could use `weex_sdk_legacy` for temporary solution. See below for detail.
+
+#### weex_sdk_legacy
+`weex_sdk_legacy`  is provided only for backward compatibility reason, and **would not be maintained in the future**. Please migrate to `weex_sdk` when you are available.
+
+`weex_sdk_legacy` is built by `./gradlew clean assembleRelease -PapachePackageName="false"`, where all java files in `.aar` is under `com.taobao.weex`
+
+## Android-Studio integrated
+Double type `SHIFT` and enter `Build Variants`, will give you build variants window.
+* Select `apacheRelease` in the dropdown window of Active Build Variants to enable Android-Studio integrated for files under `org.apache.weex`
+* Select `legacyRelease` or `release` in the dropdown window of Active Build Variants to enable Android-Studio integrated for files under `com.taobao.weex`
+
 ## The submodule weex-playground
 [Weex Playground](https://github.com/apache/incubator-weex-playground) can be used to test and preview weex pages on Android and it has been added as a submodule.
 ### Relationship between weex and playground
@@ -12,12 +32,12 @@
 ### When to publish SNAPSHOT
 When some commits of  playground rely on unpublished features of weex-sdk,a SNAPSHOT of weex-sdk will be needed to support it.
 ### How to publish SNAPSHOT
- `cd android `  
-`./gradlew clean install ArtifactoryPublish -PweexVersion=$PUBLISH_VERSION -PbintrayUser=alibabaweex -PbintrayApiKey=$JCENTER_TOKEN `  
+
+```
+cd android
+./gradlew clean install ArtifactoryPublish -PgroupId="org.apache.weex" -PartifactName="sdk_legacy" -PapachePackageName="false" -PunbundlingJSC="true" -PbuildRuntimeApi=true -PweexVersion=$PUBLISH_VERSION -PbintrayUser=weex -PbintrayApiKey=$JCENTER_TOKEN 
+```
 
 * Explanation for variable:  
 $PUBLISH_VERSION The version of snapshot, like 0.26.1.3-SNAPSHOT  
-$JCENTER_TOKEN The private key for JCenter (https://bintray.com/alibabaweex/maven/weex_sdk/), which is the distribution channel for Android
-
-
-
+$JCENTER_TOKEN The private key for JCenter (https://bintray.com/alibabaweex/maven/weex_sdk/), which is the distribution channel for Android
\ No newline at end of file
diff --git a/android/build.gradle b/android/build.gradle
index 3112b63..8898559 100644
--- a/android/build.gradle
+++ b/android/build.gradle
@@ -1,4 +1,21 @@
-
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
 buildscript {
     repositories {
         google()
@@ -36,8 +53,8 @@
     }
     buildscript {
         dependencies {
-            classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.0'
-            classpath 'com.github.dcendents:android-maven-gradle-plugin:1.5'
+            classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.8.4'
+            classpath 'com.github.dcendents:android-maven-gradle-plugin:2.1'
         }
         repositories {
             google()
@@ -58,6 +75,11 @@
     fastjsonLibVersion="1.1.70.android"
     //Default value for disableCov is false
     disableCov = project.hasProperty("disableCov") && disableCov.equals("true")
+    useApachePackageName = project.hasProperty('apachePackageName') ? project.property('apachePackageName').toBoolean() : false
+    unbundlingJSC = project.hasProperty('unbundlingJSC') ? project.property('unbundlingJSC').toBoolean() : false
+    artifactName = project.hasProperty('artifactName') ? project.property('artifactName') : 'weex_sdk'
+    groupId = project.hasProperty('groupId') ? project.property('groupId') : 'com.taobao.android'
+    weexVersion = project.hasProperty('weexVersion') ? project.getProperty('weexVersion') : '0.28.0.1'
     implementFromWeex = true
 }
 
diff --git a/android/gradle.properties b/android/gradle.properties
index 8583e59..c520341 100755
--- a/android/gradle.properties
+++ b/android/gradle.properties
@@ -13,5 +13,4 @@
 #Mon Jun 27 20:06:22 CST 2016
 org.gradle.jvmargs=-Xmx4096m -XX:MaxPermSize=2048m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8
 org.gradle.parallel=true
-android.enableAapt2=false
 android.enableD8=false
\ No newline at end of file
diff --git a/android/sdk/.gitignore b/android/sdk/.gitignore
index b173f6b..8074061 100755
--- a/android/sdk/.gitignore
+++ b/android/sdk/.gitignore
@@ -16,5 +16,8 @@
 assets/weex-rax-api.js
 .externalNativeBuild
 
-/libs/armeabi
+/libs/
+/src/main/jniLibs
 
+/src/legacyRelease/
+proguard-rules-legacy.pro
\ No newline at end of file
diff --git a/android/sdk/README.md b/android/sdk/README.md
deleted file mode 100755
index 239bde2..0000000
--- a/android/sdk/README.md
+++ /dev/null
@@ -1,7 +0,0 @@
-## Unit Test
-
-Unit test code is under 'src/test'. You can run unit test use command:   
-```bash
-./gradlew clean testDebugUnitTest jacocoTestReportDebug
-```
-This task will run all unit test and produce both unit test report and jacoco test coverage report in 'build/reports'.   
diff --git a/android/sdk/build.gradle b/android/sdk/build.gradle
index 2a9654e..15be1de 100755
--- a/android/sdk/build.gradle
+++ b/android/sdk/build.gradle
@@ -18,7 +18,7 @@
  */
  plugins {
      id "com.github.hierynomus.license" version "0.14.0"
-     id 'com.jfrog.artifactory' version '4.9.7'
+     id 'com.jfrog.artifactory' version '4.10.0'
  }
 
 apply plugin: 'com.android.library'
@@ -26,29 +26,15 @@
 apply plugin: 'com.jfrog.bintray'
 apply plugin: 'com.github.dcendents.android-maven'
 
-//if(!project.disableCov){
-//    apply plugin: 'com.vanniktech.android.junit.jacoco'
-//    junitJacoco {
-//        excludes = ['com/taobao/weex/dom/flex/**','com/taobao/weex/ui/view/refresh/circlebar/**']
-//    }
-//}
+apply from: 'buildSrc/jcenter.gradle'
+apply from: 'buildSrc/unstripped.gradle'
+apply from: 'buildSrc/checkStyle.gradle'
+apply from: 'buildSrc/download_jsc.gradle'
+apply from: 'buildSrc/packageName.gradle'
+apply from: 'buildSrc/asan.gradle'
 
-task checkstyle(type: Checkstyle) {
-    configFile file("${project.rootDir}/sdk/config/quality/checkstyle.xml") // Where my checkstyle config is...
-    // configProperties.checkstyleSuppressionsPath = file("${project.rootDir}/config/quality/checkstyle/suppressions.xml").absolutePath // Where is my suppressions file for checkstyle is...
-    source 'src'
-    include '**/*.java'
-    exclude '**/gen/**'
-    exclude '**/test/**'
-    exclude '**/com/taobao/weex/dom/flex/**'
-    classpath = files()
-}
-
-checkstyle {
-    toolVersion = '6.9'
-}
-
-version = project.hasProperty('weexVersion') ? project.getProperty('weexVersion') : '0.26.0.1'
+version = project.weexVersion
+group = project.groupId
 
 //Check version, the version must have 4 sections. The leading three section must be number, and the last section is odd number with or without suffix string.
 if (!project.hasProperty('ignoreVersionCheck') || !project.getProperty('ignoreVersionCheck').equals("true")) {
@@ -117,11 +103,17 @@
 
     def android_project_dir = projectDir
 
-    def buildRuntimeApi = project.hasProperty('buildRuntimeApi') ? project.property('buildRuntimeApi') : false
+    def buildRuntimeApi = project.hasProperty('buildRuntimeApi') ? project.property('buildRuntimeApi').toBoolean() : true
+    def jsInterpolatorName = project.hasProperty('JSInterpolatorName') ? project.property('JSInterpolatorName') : 'jsc'
+    def initJSCPrivateApi = false
+    if (buildRuntimeApi){
+        initJSCPrivateApi = jsInterpolatorName =="JavaScriptCore"
+    }
 
     defaultConfig {
         buildConfigField "String", "buildJavascriptFrameworkVersion", "\"${jsfmVersion}\""
         buildConfigField "String", "buildVersion", "\"${version}\""
+        buildConfigField "String", "JSInterpolatorName", "\"${jsInterpolatorName}\""
         minSdkVersion project.minSdkVersion
         targetSdkVersion project.targetSdkVersion
 
@@ -149,8 +141,13 @@
                         '-DANDROID_STL=' + "${cxx_stl}",
                         '-DCMAKE_BUILD_TYPE=Release',
                         '-DANDROID_PROJECT_DIR=' + "${android_project_dir}",
-                        '-DENABLE_ASAN=false',
-                        '-DBUILD_RUNTIME_API='+"${buildRuntimeApi}"
+                        '-DENABLE_ASAN=false'
+                if(buildRuntimeApi){
+                    arguments '-DBUILD_RUNTIME_API='+"${buildRuntimeApi}"
+                    if (initJSCPrivateApi){
+                        arguments '-DINIT_JSC_PRIVATE_API='+"${initJSCPrivateApi}"
+                    }
+                }
                 if(project.hasProperty('enableASan') && "true" == project.getProperty('enableASan')) {
                     cppFlags "-fsanitize=address -fno-omit-frame-pointer"
                 }
@@ -160,9 +157,9 @@
     buildTypes {
         release {
             minifyEnabled false
-            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
             buildConfigField "boolean", "ENABLE_TRACE", "false"
-            consumerProguardFiles 'proguard-rules.pro'
+            proguardFiles getDefaultProguardFile('proguard-android.txt'), useApachePackageName ? 'proguard-rules.pro' : 'proguard-rules-legacy.pro'
+            consumerProguardFiles useApachePackageName ? 'proguard-rules.pro' : 'proguard-rules-legacy.pro'
         }
 
         debug {
@@ -172,24 +169,49 @@
             testCoverageEnabled disableCov.toBoolean()
             consumerProguardFiles 'proguard-rules.pro'
         }
+
+        apacheRelease{
+            initWith release
+            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
+            consumerProguardFiles 'proguard-rules.pro'
+        }
+
+        legacyRelease{
+            initWith release
+            proguardFiles getDefaultProguardFile('proguard-android.txt'),  'proguard-rules-legacy.pro'
+            consumerProguardFiles 'proguard-rules-legacy.pro'
+        }
     }
 
     externalNativeBuild {
         cmake {
-            path '../../weex_core/CMakeLists.txt'
+            if(project.useApachePackageName) {
+                path '../../weex_core/CMakeLists.txt'
+            }
+            else{
+                copy{
+                    from new File('../../weex_core/CMakeLists.txt')
+                    into new File('src/legacyRelease/cpp')
+                }
+                path 'src/legacyRelease/cpp/CMakeLists.txt'
+            }
         }
     }
 
     sourceSets {
-        main {
-            assets.srcDirs = ['assets']
-            jniLibs.srcDir(['libs'])
-            java {
-                srcDirs = ["src/main/java"];
-            }
+        main.assets.srcDirs = ['assets']
+        apacheRelease.java.srcDirs = ['src/main/java']
+        apacheRelease.manifest.srcFile(new File('src/main/AndroidManifest.xml'))
+        legacyRelease.java.srcDirs = ['src/legacyRelease/java']
+        legacyRelease.manifest.srcFile(new File('src/legacyRelease/AndroidManifest.xml'))
+        if(!project.useApachePackageName){
+            main.java.srcDirs = ['src/legacyRelease/java']
+            main.manifest.srcFile(new File('src/legacyRelease/AndroidManifest.xml'))
         }
-        debug.setRoot('build-types/debug')
-        release.setRoot('build-types/release')
+
+        if(project.unbundlingJSC){
+            main.jniLibs.srcDirs = []
+        }
     }
 
     compileOptions.encoding = "UTF-8"
@@ -209,7 +231,6 @@
 }
 
 dependencies {
-    implementation fileTree(include: ['*.jar'], dir: 'libs')
     //noinspection GradleDependency
     compileOnly "com.android.support:recyclerview-v7:${project.supportLibVersion}"
     //noinspection GradleDependency
@@ -238,202 +259,32 @@
     testImplementation 'org.json:json:20160212'
 }
 
-if(file('../license/LICENSE').exists()){
-    license {
-        header = file('../license/LICENSE')
-        mapping('cpp','JAVADOC_STYLE')
-        mapping('h','JAVADOC_STYLE')
-        excludes(['com/taobao/weex/utils/WXDataStructureUtil.java'])
-    }
-
-    task weex_core_license(type: com.hierynomus.gradle.license.tasks.LicenseFormat){
-        source = fileTree(dir:"../../weex_core").include(['**/*.h','**/*.cpp', '**/*.cc', '**/*.c']).
-                exclude(['Source/rapidjson/**/*.h','Source/rapidjson/**/*.cpp',
-                         'Source/android/jniprebuild/jniheader/*.h',
-                         'Source/base/Compatible.cpp',
-                         'Source/IPC/**/*.h','Source/IPC/**/*.cpp', 'Source/IPC/**/*.c',
-                         'Source/base/base64/modp_base64/**/*.h',
-                         'Source/base/base64/modp_base64/**/*.cc',
-                         'Source/base/third_party/icu/*.h',
-                         'Source/base/third_party/icu/*.cpp',
-                         'Source/android/jsengine/dependence/**/*.h',
-                         'Source/android/jsengine/dependence/**/*.cpp',
-                         'Source/include/wtf/**/*.h',
-                         'Source/include/wtf/**/*.c',
-                         'Source/include/wtf/**/*.cpp',
-                         'Source/include/JavaScriptCore/**/*.h',
-                         'Source/include/JavaScriptCore/**/*.c',
-                         'Source/include/JavaScriptCore/**/*.cpp'])
-    }
-    preBuild.dependsOn licenseFormat
-}
-def ndkDir = ''
-task checkNdkVersion() {
-    def rootDir = project.rootDir
-    def localProperties = new File(rootDir, "local.properties")
-    if (localProperties.exists()) {
-        Properties properties = new Properties()
-        localProperties.withInputStream { instr ->
-            properties.load(instr)
-        }
-        ndkDir = properties.getProperty('ndk.dir')
-    }
-
-//    if(null == ndkDir){
-//        def errMsg ='please set ndk.dir path in project/local.properties and ndk-16 supported only,example: ndk.dir=/Users/xxx/Library/Android/sdk/ndk-bundle-r16'
-//        throw new StopActionException(errMsg)
-//    }
+license {
+    header = file('../license/LICENSE')
+    mapping('cpp', 'JAVADOC_STYLE')
+    mapping('h', 'JAVADOC_STYLE')
+    excludes(['org/apache/weex/utils/WXDataStructureUtil.java'])
 }
 
-preBuild.dependsOn checkNdkVersion
-
-def siteUrl = 'https://weex.incubator.apache.org'
-def gitUrl = 'https://github.com/apache/incubator-weex.git'
-group = "com.taobao.android"
-install {
-    repositories.mavenInstaller {
-        // This generates POM.xml with proper parameters
-        pom {
-            project {
-                packaging 'aar'
-                name 'weex_sdk'
-                url siteUrl
-                licenses {
-                    license {
-                        name 'The Apache Software License, Version 2.0'
-                        url 'https://www.apache.org/licenses/LICENSE-2.0.txt'
-                    }
-                }
-                developers {
-                    developer {
-                        id 'weex alibaba'
-                        name 'weex alibaba'
-                        email 'alibabaweex@gmail.com'
-                    }
-                }
-                scm {
-                    connection gitUrl
-                    developerConnection gitUrl
-                    url siteUrl
-                }
-            }
-        }
-    }
+task weex_core_license(type: com.hierynomus.gradle.license.tasks.LicenseFormat) {
+    source = fileTree(dir: "../../weex_core").include(['**/*.h', '**/*.cpp', '**/*.cc', '**/*.c']).
+            exclude(['Source/rapidjson/**/*.h', 'Source/rapidjson/**/*.cpp',
+                     'Source/android/jniprebuild/jniheader/*.h',
+                     'Source/base/Compatible.cpp',
+                     'Source/IPC/**/*.h', 'Source/IPC/**/*.cpp', 'Source/IPC/**/*.c',
+                     'Source/base/base64/modp_base64/**/*.h',
+                     'Source/base/base64/modp_base64/**/*.cc',
+                     'Source/base/third_party/icu/*.h',
+                     'Source/base/third_party/icu/*.cpp',
+                     'Source/android/jsengine/dependence/**/*.h',
+                     'Source/android/jsengine/dependence/**/*.cpp',
+                     'Source/include/wtf/**/*.h',
+                     'Source/include/wtf/**/*.c',
+                     'Source/include/wtf/**/*.cpp',
+                     'Source/include/JavaScriptCore/**/*.h',
+                     'Source/include/JavaScriptCore/**/*.c',
+                     'Source/include/JavaScriptCore/**/*.cpp'])
 }
 
-task sourcesJar(type: Jar) {
-    from android.sourceSets.main.java.srcDirs
-    classifier = 'sources'
-}
-
-artifacts {
-    archives sourcesJar
-}
-
-bintray {
-    configurations = ['archives']
-    user = project.hasProperty('bintrayUser') ? project.property('bintrayUser') : System.getenv('BINTRAY_USER')
-    key = project.hasProperty('bintrayApiKey') ? project.property('bintrayApiKey') : System.getenv('BINTRAY_API_KEY')
-    pkg {
-        repo = "maven"
-        name = "weex_sdk"
-        websiteUrl = siteUrl
-        vcsUrl = gitUrl
-        licenses = ["Apache-2.0"]
-        publish = true
-        version {
-            //The version to be published
-            name = project.version
-            vcsTag = project.version
-        }
-    }
-}
-artifactory {
-    contextUrl = 'http://oss.jfrog.org/artifactory'
-    publish {
-        repository {
-            repoKey = 'oss-snapshot-local'
-            username = bintray.user
-            password = bintray.key
-            maven = true
-        }
-        defaults {
-            publishConfigs('archives')
-        }
-    }
-}
-def asanAbi = project.hasProperty('asanAbi') ? project.getProperty('asanAbi') : 'arm64-v8a'
-task clearASanLibs(type: Delete){
-    delete project.android.sourceSets.main.resources.srcDirs
-    delete fileTree(project.android.sourceSets.main.jniLibs.srcDirs[-1]) {
-        include '**/libclang_rt.asan-*-android.so'
-    }
-}
-task copyWrapScript(type: Copy,dependsOn: clearASanLibs) {
-    if(project.hasProperty('enableASan') && "true" == project.getProperty('enableASan')) {
-        from 'wrap.sh'
-        into new File(project.android.sourceSets.main.resources.srcDirs[-1], "lib")
-        eachFile {
-            it.path = "${asanAbi}/${it.name}"
-        }
-    }
-}
-task copyASanLib(type: Copy,dependsOn: copyWrapScript){
-    if(project.hasProperty('enableASan') && "true" == project.getProperty('enableASan')) {
-        def ndkPath = ndkDir == '' ? System.getenv("ANDROID_NDK_HOME"):ndkDir
-        def dir = ndkPath + '/toolchains/llvm/prebuilt/'
-        def renamedAbi = asanAbi
-        if (asanAbi == "armeabi-v7a" || asanAbi == "armeabi")
-            renamedAbi = "arm"
-        if (asanAbi == "arm64-v8a")
-            renamedAbi = "aarch64"
-        if (asanAbi == "x86")
-            renamedAbi = "i686"
-        new File(dir).eachFileRecurse { file ->
-            if (file.name == 'libclang_rt.asan-' + renamedAbi + '-android.so')
-                from file.absolutePath
-                into project.android.sourceSets.main.jniLibs.srcDirs[-1]
-                eachFile {
-                    it.path = "${asanAbi}/${it.name}"
-                }
-            includeEmptyDirs = false
-        }
-    }
-}
-preBuild.dependsOn copyASanLib
-
-afterEvaluate { project ->
-    transformNativeLibsWithStripDebugSymbolForRelease << {
-        copy{
-            from transformNativeLibsWithMergeJniLibsForRelease
-            into new File(project.buildDir, "unstrippedSo")
-            include '**/libweexjss.so', '**/libweexcore.so'
-            eachFile {
-                it.path = "${it.relativePath.segments[-2]}_${it.name}"
-            }
-        }
-
-        if(project.hasProperty('supportArmeabi') && "true" == project.getProperty('supportArmeabi')){
-            //Copy stripped shared library from armeabi-v7a into armeabi
-            copy{
-                from transformNativeLibsWithStripDebugSymbolForRelease
-                into project.android.sourceSets.main.jniLibs.srcDirs[-1]
-                include '**/armeabi-v7a/**'
-                exclude '**/libc++_shared.so'
-                eachFile {
-                    it.path = "armeabi/${it.name}"
-                }
-            }
-
-            //Copy Unstripped shared library from armeabi-v7a into armeabi
-            copy{
-                from transformNativeLibsWithMergeJniLibsForRelease
-                into new File(project.buildDir, "unstrippedSo")
-                include '**/armeabi-v7a/libweexjss.so', '**/armeabi-v7a/libweexcore.so'
-                eachFile {
-                    it.path = "armeabi_${it.name}"
-                }
-            }
-        }
-    }
-}
\ No newline at end of file
+preBuild.dependsOn licenseFormat, copyJSCHeaderToWeexCore
+clean.dependsOn cleanCopyJSCHeaderToWeexCore
\ No newline at end of file
diff --git a/android/sdk/buildSrc/asan.gradle b/android/sdk/buildSrc/asan.gradle
new file mode 100644
index 0000000..df81979
--- /dev/null
+++ b/android/sdk/buildSrc/asan.gradle
@@ -0,0 +1,73 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+def asanAbi = project.hasProperty('asanAbi') ? project.getProperty('asanAbi') : 'arm64-v8a'
+def ndkDir = ''
+
+task checkNdkVersion() {
+    def rootDir = project.rootDir
+    def localProperties = new File(rootDir, "local.properties")
+    if (localProperties.exists()) {
+        Properties properties = new Properties()
+        localProperties.withInputStream { instr ->
+            properties.load(instr)
+        }
+        ndkDir = properties.getProperty('ndk.dir')
+    }
+}
+
+task clearASanLibs(type: Delete){
+    delete project.android.sourceSets.main.resources.srcDirs
+    delete fileTree(project.android.sourceSets.main.jniLibs.srcDirs[-1]) {
+        include '**/libclang_rt.asan-*-android.so'
+    }
+}
+task copyWrapScript(type: Copy,dependsOn: clearASanLibs) {
+    if(project.hasProperty('enableASan') && "true" == project.getProperty('enableASan')) {
+        from 'wrap.sh'
+        into new File(project.android.sourceSets.main.resources.srcDirs[-1], "lib")
+        eachFile {
+            it.path = "${asanAbi}/${it.name}"
+        }
+    }
+}
+task copyASanLib(type: Copy){
+    dependsOn copyWrapScript, copyJscToJniDir
+    if(project.hasProperty('enableASan') && "true" == project.getProperty('enableASan')) {
+        def ndkPath = ndkDir == '' ? System.getenv("ANDROID_NDK_HOME"):ndkDir
+        def dir = ndkPath + '/toolchains/llvm/prebuilt/'
+        def renamedAbi = asanAbi
+        if (asanAbi == "armeabi-v7a" || asanAbi == "armeabi")
+            renamedAbi = "arm"
+        if (asanAbi == "arm64-v8a")
+            renamedAbi = "aarch64"
+        if (asanAbi == "x86")
+            renamedAbi = "i686"
+        new File(dir).eachFileRecurse { file ->
+            if (file.name == 'libclang_rt.asan-' + renamedAbi + '-android.so')
+                from file.absolutePath
+            into project.android.sourceSets.main.jniLibs.srcDirs[-1]
+            eachFile {
+                it.path = "${asanAbi}/${it.name}"
+            }
+            includeEmptyDirs = false
+        }
+    }
+}
+
+preBuild.dependsOn copyASanLib, checkNdkVersion
\ No newline at end of file
diff --git a/android/sdk/buildSrc/checkStyle.gradle b/android/sdk/buildSrc/checkStyle.gradle
new file mode 100644
index 0000000..2df40e0
--- /dev/null
+++ b/android/sdk/buildSrc/checkStyle.gradle
@@ -0,0 +1,32 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+task checkstyle(type: Checkstyle) {
+    configFile file("${project.rootDir}/sdk/config/quality/checkstyle.xml") // Where my checkstyle config is...
+    // configProperties.checkstyleSuppressionsPath = file("${project.rootDir}/config/quality/checkstyle/suppressions.xml").absolutePath // Where is my suppressions file for checkstyle is...
+    source 'src'
+    include '**/*.java'
+    exclude '**/gen/**'
+    exclude '**/test/**'
+    exclude '**/com/taobao/weex/dom/flex/**'
+    classpath = files()
+}
+
+checkstyle {
+    toolVersion = '6.9'
+}
\ No newline at end of file
diff --git a/android/sdk/buildSrc/download_jsc.gradle b/android/sdk/buildSrc/download_jsc.gradle
new file mode 100644
index 0000000..c75c90e
--- /dev/null
+++ b/android/sdk/buildSrc/download_jsc.gradle
@@ -0,0 +1,93 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+def jsc_dir = new File(project.buildDir, 'jsc')
+def jsc_url = project.hasProperty('jsc_url') ? new URL(project.getProperty('jsc_url').toString()) : new URL('https://registry.npmjs.org/jsc-android/-/jsc-android-241213.1.0.tgz')
+def aar_name = project.hasProperty('aar_name') ? project.getProperty('aar_name').toString() : 'android-jsc-intl'
+
+def jsc_file = new File(jsc_dir, jsc_url.path.split('/').last())
+def aar_file = new File(jsc_dir, "${aar_name}.aar")
+
+def downloadJSC = { URL url, File dest ->
+    if (!dest.getParentFile().exists()) {
+        dest.getParentFile().mkdirs()
+    }
+    url.withInputStream { i -> dest.withOutputStream { it << i } }
+}
+
+task download(){
+    inputs.property('url', jsc_url)
+    outputs.file(jsc_file)
+    outputs.upToDateWhen {
+        jsc_file.exists()
+    }
+    doFirst {
+        if (!jsc_file.exists()) {
+            downloadJSC(jsc_url, jsc_file)
+        }
+    }
+}
+
+task unzipJSC(type: Copy, dependsOn: download) {
+    from jsc_file.name.endsWith(".aar") ? jsc_file : tarTree(jsc_file)
+    into jsc_dir
+    include "**/*${aar_name}*.aar", '**/include/*.h'
+    includeEmptyDirs false
+    eachFile {
+        if(it.name.endsWith('.aar')) {
+            it.path = it.name
+            it.name = "${aar_name}.aar"
+        }
+        else if(it.name.endsWith('.h')){
+            it.path= 'include/' + it.name
+        }
+    }
+    inputs.file(jsc_file)
+    outputs.file(aar_file)
+    outputs.upToDateWhen {
+        aar_file.exists()
+    }
+}
+
+task copyJscToJniDir(type: Copy, dependsOn: unzipJSC) {
+    def libsDir = project.android.sourceSets.main.jniLibs.srcDirs[-1]
+    from zipTree(aar_file)
+    into libsDir
+    include 'jni/**/*.so'
+    exclude '**/libweexcore.so', '**/libweexjsb.so', '**/libweexjss.so',
+            '**/libweexjssr.so', '**/libweexjst.so', '**/libc++_shared.so',
+            '**/x86_64/**'
+    includeEmptyDirs false
+    eachFile {
+        def path_list = new LinkedList<>(it.relativePath.segments.toList())
+        path_list.removeAt(0)
+        it.relativePath = new RelativePath(true, path_list[0], path_list[1])
+    }
+    inputs.file(aar_file)
+    outputs.upToDateWhen {false}
+}
+
+task copyJSCHeaderToWeexCore(type: Copy, dependsOn: unzipJSC) {
+    from new File(jsc_dir, 'include')
+    into '../../weex_core/Source/include/JSCHeaderNew/JavaScriptCore'
+    includeEmptyDirs false
+    inputs.dir(new File(jsc_dir, 'include'))
+}
+
+preBuild.dependsOn copyJscToJniDir
+clean.dependsOn cleanCopyJscToJniDir
\ No newline at end of file
diff --git a/android/sdk/buildSrc/jcenter.gradle b/android/sdk/buildSrc/jcenter.gradle
new file mode 100644
index 0000000..fb8b55a
--- /dev/null
+++ b/android/sdk/buildSrc/jcenter.gradle
@@ -0,0 +1,120 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+def siteUrl = 'https://weex.apache.org/'
+def gitUrl = 'https://github.com/apache/incubator-weex.git'
+def mailingList = 'dev@weex.apache.org'
+def description='Apache Weex is an effort undergoing incubation at The Apache Software Foundation (ASF), sponsored by the Apache Incubator. Incubation is required of all newly accepted projects until a further review indicates that the infrastructure, communications, and decision making process have stabilized in a manner consistent with other successful ASF projects. While incubation status is not necessarily a reflection of the completeness or stability of the code, it does indicate that the project has yet to be fully endorsed by the ASF.All Apache Weex releases are in the form of source code, binary/bytecode packages are produced as a convenience to users. View https://weex.apache.org/download/download.html for official Apache Release.'
+install {
+    repositories.mavenInstaller {
+        // This generates POM.xml with proper parameters
+        pom {
+            project {
+                packaging 'aar'
+                name 'Apache Incubator-Weex'
+                artifactId project.artifactName
+                groupId project.groupId
+                url siteUrl
+                version = project.weexVersion
+                licenses {
+                    license {
+                        name 'The Apache Software License, Version 2.0'
+                        url 'https://raw.githubusercontent.com/apache/incubator-weex/master/LICENSE'
+                    }
+                }
+                developers {
+                    developer {
+                        name 'Apache Weex PPMC'
+                        email mailingList
+                    }
+                }
+                scm {
+                    connection gitUrl
+                    developerConnection mailingList
+                    url siteUrl
+                }
+            }
+        }
+    }
+}
+
+bintray {
+    configurations = ['archives']
+    user = project.hasProperty('bintrayUser') ? project.property('bintrayUser') : System.getenv('BINTRAY_USER')
+    key = project.hasProperty('bintrayApiKey') ? project.property('bintrayApiKey') : System.getenv('BINTRAY_API_KEY')
+    pkg {
+        repo = 'Android'
+        name = project.artifactName
+        websiteUrl = siteUrl
+        desc = description
+        vcsUrl = gitUrl
+        licenses = ["Apache-2.0"]
+        publish = true
+        version {
+            desc = description
+            released = new Date()
+            name = project.weexVersion
+            vcsTag = project.hasProperty('vcsTag') ? project.property('vcsTag') :  project.weexVersion
+        }
+    }
+}
+
+task sourcesJar(type: Jar) {
+    from android.sourceSets.main.java.srcDirs
+    classifier = 'sources'
+}
+
+artifacts {
+    archives sourcesJar
+}
+
+if (project.gradle.startParameter.taskNames.contains('artifactoryPublish') ||
+        project.gradle.startParameter.taskNames.contains(':weex_sdk:artifactoryPublish')) {
+    apply plugin: 'maven-publish'
+    publishing {
+        publications {
+            artifactorySnapthost(MavenPublication) {
+                groupId project.groupId
+                artifactId project.artifactName
+                version project.weexVersion
+                artifact bundleReleaseAar
+            }
+        }
+        repositories {
+            maven {
+                name = 'OJOSnapshot'
+                url = 'http://oss.jfrog.org/artifactory'
+            }
+        }
+    }
+}
+
+artifactory {
+    contextUrl = 'http://oss.jfrog.org/artifactory'
+    publish {
+        repository {
+            repoKey = 'oss-snapshot-local'
+            username = bintray.user
+            password = bintray.key
+            maven = true
+        }
+        defaults {
+            publications ('artifactorySnapthost')
+        }
+    }
+}
\ No newline at end of file
diff --git a/android/sdk/buildSrc/packageName.gradle b/android/sdk/buildSrc/packageName.gradle
new file mode 100644
index 0000000..232c30d
--- /dev/null
+++ b/android/sdk/buildSrc/packageName.gradle
@@ -0,0 +1,102 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+task copyAndRenamePackage(type: Copy) {
+    if(!project.useApachePackageName) {
+        inputs.dir new File('src/main/java/org/apache/weex')
+        from new File('src/main/java/org/apache/weex')
+        into new File('src/legacyRelease/java/com/taobao/weex')
+        filter { String line ->
+            line.replaceAll(/^(package org\.apache)(\.weex.*)$/, { _, packageName, suffix ->
+                "package com.taobao${suffix}"
+            }).replaceAll(/^(import org\.apache)(\.weex.*)$/, { _, packageName, suffix ->
+                "import com.taobao${suffix}"
+            }).replaceAll(/^(import static org\.apache)(\.weex.*)$/, { _, packageName, suffix ->
+                "import static com.taobao${suffix}"
+            })
+        }
+    }
+}
+
+task copyManifest(type: Copy){
+    if(!project.useApachePackageName){
+        inputs.file new File('src/main/AndroidManifest.xml')
+        from new File('src/main/AndroidManifest.xml')
+        into new File('src/legacyRelease')
+        filter { String line ->
+            line.replaceAll(/(org\.apache)(\.weex.*)/, { _, packageName, suffix ->
+                "com.taobao${suffix}"
+            })
+        }
+    }
+}
+
+task copyProguard(type: Copy){
+    if(!project.useApachePackageName){
+        inputs.file new File('proguard-rules.pro')
+        from new File('proguard-rules.pro')
+        into new File('.')
+        rename 'proguard-rules.pro', 'proguard-rules-legacy.pro'
+        filter { String line ->
+            line.replaceAll(/(org\.apache)(\.weex.*)/, { _, packageName, suffix ->
+                "com.taobao${suffix}"
+            })
+        }
+    }
+}
+
+task(cleanCopyProguard, overwrite: true, type: Delete){
+    delete 'proguard-rules-legacy.pro'
+}
+
+task copyOtherCppFile(type: Copy){
+    if(!project.useApachePackageName) {
+        inputs.dir new File('../../weex_core')
+        from new File('../../weex_core')
+        into new File('src/legacyRelease/cpp')
+        exclude '**/*.cpp', '**/*.cc', '**/*.c', '**/*.h', '**/*.hpp'
+    }
+}
+
+task copyAndRenameCppSourceFile(type: Copy){
+    dependsOn copyOtherCppFile, copyJSCHeaderToWeexCore
+    if(!project.useApachePackageName) {
+        inputs.dir new File('../../weex_core')
+        from new File('../../weex_core')
+        into new File('src/legacyRelease/cpp')
+        include '**/*.cpp', '**/*.cc', '**/*.c', '**/*.h', '**/*.hpp'
+        filter { String line ->
+            line.replaceAll('(.*".*)(org/apache/weex)(.*".*)', { _, prefix, packageName, suffix ->
+                logger.info("Content substation in .cpp/.h files happpened, \n Input: ${line}, \n Output: ${prefix}com/taobao/weex${suffix}")
+                "${prefix}com/taobao/weex${suffix}"
+            })
+        }
+    }
+}
+
+gradle.taskGraph.beforeTask { Task task ->
+    if(task.name == 'assembleApacheRelease'){
+        throw new StopActionException('Not Supported. assembleApacheRelease is not supported, please use the following command instead.\n assembleRelease -PapachePackageName="true"')
+    }
+    else if(task.name == 'assembleLegacyRelease'){
+        throw new StopActionException('Not Supported. assembleLegacyRelease is not supported, please use the following command instead.\n assembleRelease -PapachePackageName="false"')
+    }
+}
+
+preBuild.dependsOn copyAndRenameCppSourceFile, copyAndRenamePackage, copyManifest, copyProguard
+clean.dependsOn cleanCopyAndRenamePackage, cleanCopyManifest, cleanCopyProguard, cleanCopyOtherCppFile, cleanCopyAndRenameCppSourceFile
\ No newline at end of file
diff --git a/android/sdk/buildSrc/unstripped.gradle b/android/sdk/buildSrc/unstripped.gradle
new file mode 100644
index 0000000..8a22ee0
--- /dev/null
+++ b/android/sdk/buildSrc/unstripped.gradle
@@ -0,0 +1,68 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+def processNativeLibs = { unstripped, stripped ->
+    copy{
+        from unstripped
+        into new File(project.buildDir, "unstrippedSo")
+        include '**/libweexjss.so', '**/libweexcore.so'
+        eachFile {
+            it.path = "${it.relativePath.segments[-2]}_${it.name}"
+        }
+    }
+
+    if(project.hasProperty('supportArmeabi') && "true" == project.getProperty('supportArmeabi')){
+        //Copy stripped shared library from armeabi-v7a into armeabi
+        copy{
+            from stripped
+            into project.android.sourceSets.main.jniLibs.srcDirs[-1]
+            include '**/armeabi-v7a/**'
+            exclude '**/libc++_shared.so'
+            eachFile {
+                it.path = "armeabi/${it.name}"
+            }
+        }
+
+        //Copy Unstripped shared library from armeabi-v7a into armeabi
+        copy{
+            from unstripped
+            into new File(project.buildDir, "unstrippedSo")
+            include '**/armeabi-v7a/libweexjss.so', '**/armeabi-v7a/libweexcore.so'
+            eachFile {
+                it.path = "armeabi_${it.name}"
+            }
+        }
+    }
+}
+
+afterEvaluate { project ->
+    transformNativeLibsWithStripDebugSymbolForRelease.doLast {
+        processNativeLibs transformNativeLibsWithMergeJniLibsForRelease,
+                transformNativeLibsWithStripDebugSymbolForRelease
+    }
+
+    transformNativeLibsWithStripDebugSymbolForApacheRelease.doLast {
+        processNativeLibs transformNativeLibsWithMergeJniLibsForApacheRelease,
+                transformNativeLibsWithStripDebugSymbolForApacheRelease
+    }
+
+    transformNativeLibsWithStripDebugSymbolForLegacyRelease.doLast {
+        processNativeLibs transformNativeLibsWithMergeJniLibsForLegacyRelease,
+                transformNativeLibsWithStripDebugSymbolForLegacyRelease
+    }
+}
\ No newline at end of file
diff --git a/android/sdk/build_jss_r.sh b/android/sdk/build_jss_r.sh
index 7334cd3..cf0a5a0 100755
--- a/android/sdk/build_jss_r.sh
+++ b/android/sdk/build_jss_r.sh
@@ -1,3 +1,19 @@
+# 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
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# 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.
 echo "--> # buils jsc_runtime so"
 
 
diff --git a/android/sdk/libs/arm64-v8a/libJavaScriptCore.so b/android/sdk/libs/arm64-v8a/libJavaScriptCore.so
deleted file mode 100755
index 7f33280..0000000
--- a/android/sdk/libs/arm64-v8a/libJavaScriptCore.so
+++ /dev/null
Binary files differ
diff --git a/android/sdk/libs/arm64-v8a/libWTF.so b/android/sdk/libs/arm64-v8a/libWTF.so
deleted file mode 100755
index ce8d0bc..0000000
--- a/android/sdk/libs/arm64-v8a/libWTF.so
+++ /dev/null
Binary files differ
diff --git a/android/sdk/libs/armeabi-v7a/libJavaScriptCore.so b/android/sdk/libs/armeabi-v7a/libJavaScriptCore.so
deleted file mode 100755
index d6b471c..0000000
--- a/android/sdk/libs/armeabi-v7a/libJavaScriptCore.so
+++ /dev/null
Binary files differ
diff --git a/android/sdk/libs/armeabi-v7a/libWTF.so b/android/sdk/libs/armeabi-v7a/libWTF.so
deleted file mode 100755
index 790bef2..0000000
--- a/android/sdk/libs/armeabi-v7a/libWTF.so
+++ /dev/null
Binary files differ
diff --git a/android/sdk/libs/x86/libJavaScriptCore.so b/android/sdk/libs/x86/libJavaScriptCore.so
deleted file mode 100755
index 3cdfd01..0000000
--- a/android/sdk/libs/x86/libJavaScriptCore.so
+++ /dev/null
Binary files differ
diff --git a/android/sdk/libs/x86/libWTF.so b/android/sdk/libs/x86/libWTF.so
deleted file mode 100755
index dcc6553..0000000
--- a/android/sdk/libs/x86/libWTF.so
+++ /dev/null
Binary files differ
diff --git a/android/sdk/lint.xml b/android/sdk/lint.xml
index 747992e..6a2cf16 100644
--- a/android/sdk/lint.xml
+++ b/android/sdk/lint.xml
@@ -1,4 +1,22 @@
 <?xml version="1.0" encoding="UTF-8"?>
+<!--
+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
+
+  http://www.apache.org/licenses/LICENSE-2.0
+
+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.
+-->
 <lint>
   <!-- Ignore the UselessLeaf issue in the specified file -->
   <issue id="IconLocation">
diff --git a/android/sdk/proguard-rules.pro b/android/sdk/proguard-rules.pro
index 957227f..19b57c0 100755
--- a/android/sdk/proguard-rules.pro
+++ b/android/sdk/proguard-rules.pro
@@ -34,8 +34,8 @@
 #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
 #   public *;
 #}
--keep class com.taobao.weex.bridge.** { *; }
--keep class com.taobao.weex.layout.** { *; }
--keep class com.taobao.weex.WXSDKEngine { *; }
--keep class com.taobao.weex.base.SystemMessageHandler { *; }
--dontwarn com.taobao.weex.bridge.**
+-keep class org.apache.weex.bridge.** { *; }
+-keep class org.apache.weex.layout.** { *; }
+-keep class org.apache.weex.WXSDKEngine { *; }
+-keep class org.apache.weex.base.SystemMessageHandler { *; }
+-dontwarn org.apache.weex.bridge.**
diff --git a/android/sdk/src/main/AndroidManifest.xml b/android/sdk/src/main/AndroidManifest.xml
index 5360c0c..3c06bb4 100755
--- a/android/sdk/src/main/AndroidManifest.xml
+++ b/android/sdk/src/main/AndroidManifest.xml
@@ -18,6 +18,6 @@
 under the License.
 -->
 <manifest xmlns:android="http://schemas.android.com/apk/res/android"
-          package="com.taobao.weex">
+          package="org.apache.weex">
     <uses-permission android:name="android.permission.READ_PHONE_STATE"/>
 </manifest>
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/ComponentObserver.java b/android/sdk/src/main/java/com/taobao/weex/ComponentObserver.java
deleted file mode 100644
index a2bcd09..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ComponentObserver.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex;
-
-import android.view.View;
-
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by sospartan on 14/06/2017.
- */
-
-public interface ComponentObserver {
-
-  /**
-   * Called after component is create.
-   * Notice: View is not created at this moment.
-   * @param component
-   */
-  void onCreate(WXComponent component);
-
-  /**
-   * Called before component destroy.
-   * @param component
-   */
-  void onPreDestory(WXComponent component);
-
-  /**
-   * Called when component's view is created
-   * @param component
-   * @param view
-   */
-  void onViewCreated(WXComponent component,View view);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/IWXActivityStateListener.java b/android/sdk/src/main/java/com/taobao/weex/IWXActivityStateListener.java
deleted file mode 100644
index cc2d413..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/IWXActivityStateListener.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-/**
- * Listener class for activity lifecycle
- */
-
-@Deprecated
-public interface IWXActivityStateListener {
-
-  void onActivityCreate();
-
-  void onActivityStart();
-
-  void onActivityPause();
-
-  void onActivityResume();
-
-  void onActivityStop();
-
-  void onActivityDestroy();
-
-  boolean onActivityBack();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/IWXRenderListener.java b/android/sdk/src/main/java/com/taobao/weex/IWXRenderListener.java
deleted file mode 100644
index fd78d60..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/IWXRenderListener.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import android.view.View;
-
-public interface IWXRenderListener {
-
-  /**
-   * If {@link com.taobao.weex.common.WXRenderStrategy#APPEND_ASYNC} is applied, this method
-   * will be invoked when the rendering of first view is finish.
-   * If {@link com.taobao.weex.common.WXRenderStrategy#APPEND_ONCE} is applied, this method will
-   * be invoked when the rendering of the view tree is finished.
-   */
-  void onViewCreated(WXSDKInstance instance, View view);
-
-  /**
-   * Called when the render view phase of weex has finished.
-   * It can be invoked at most once in the entire life of a {@link WXSDKInstance}
-   */
-  void onRenderSuccess(WXSDKInstance instance, int width, int height);
-
-  /**
-   * Callback method, called when refresh is finished
-   */
-  void onRefreshSuccess(WXSDKInstance instance, int width, int height);
-
-  /**
-   * Report exception occurred when weex instance is running. Exception <strong>may not</strong>
-   * cause user-noticeable failure of weex.
-   */
-  void onException(WXSDKInstance instance, String errCode, String msg);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/IWXStatisticsListener.java b/android/sdk/src/main/java/com/taobao/weex/IWXStatisticsListener.java
deleted file mode 100644
index 814edae..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/IWXStatisticsListener.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-public interface IWXStatisticsListener {
-  /**
-   * Called when weex sdk engine begin to initialize.
-   */
-   void onSDKEngineInitialize();
-
-  /**
-   * Called when begin to load js framework.
-   */
-   void onJsFrameworkStart();
-
-  /**
-   * Called when finish loading js framework.
-   */
-   void onJsFrameworkReady();
-
-  /**
-   * Called when the render view phase of first view reached.
-   */
-   void onFirstView();
-
-  /**
-   * Called when the render view phase of first screen reached.
-   */
-  void onFirstScreen();
-
-  /**
-   * Called when to start a http request.
-   */
-  void onHttpStart();
-
-  /**
-   * Called when received a http response header data.
-   */
-  void onHeadersReceived();
-
-  /**
-   * Called when to finish a http request.
-   */
-  void onHttpFinish();
-
-  /**
-   * Called when an exception occured.
-   */
-  void onException(String instanceid, String errCode, String msg);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/InitConfig.java b/android/sdk/src/main/java/com/taobao/weex/InitConfig.java
deleted file mode 100644
index 053fb82..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/InitConfig.java
+++ /dev/null
@@ -1,249 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex;
-
-import android.support.annotation.NonNull;
-import com.taobao.weex.adapter.ClassLoaderAdapter;
-import com.taobao.weex.adapter.IDrawableLoader;
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.adapter.IWXImgLoaderAdapter;
-import com.taobao.weex.adapter.IWXJSExceptionAdapter;
-import com.taobao.weex.adapter.IWXJsFileLoaderAdapter;
-import com.taobao.weex.adapter.IWXJscProcessManager;
-import com.taobao.weex.adapter.IWXSoLoaderAdapter;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.appfram.storage.IWXStorageAdapter;
-import com.taobao.weex.appfram.websocket.IWebSocketAdapterFactory;
-import com.taobao.weex.performance.IApmGenerator;
-import java.util.LinkedList;
-import java.util.List;
-
-/**
- * Created by sospartan on 5/31/16.
- */
-public class InitConfig {
-  private IWXHttpAdapter httpAdapter;
-  private IDrawableLoader drawableLoader;
-  private IWXImgLoaderAdapter imgAdapter;
-  private IWXUserTrackAdapter utAdapter;
-  private IWXStorageAdapter storageAdapter;
-  private IWXSoLoaderAdapter soLoader;
-  private URIAdapter mURIAdapter;
-  private IWebSocketAdapterFactory webSocketAdapterFactory;
-  private IWXJSExceptionAdapter mJSExceptionAdapter;
-  private String framework;
-  private ClassLoaderAdapter classLoaderAdapter;
-  private IApmGenerator apmGenerater;
-  private IWXJsFileLoaderAdapter jsFileLoaderAdapter;
-  private IWXJscProcessManager jscProcessManager;
-  private List<String> nativeLibraryList;
-
-  public IWXHttpAdapter getHttpAdapter() {
-    return httpAdapter;
-  }
-
-  public IWXImgLoaderAdapter getImgAdapter() {
-    return imgAdapter;
-  }
-
-  public IDrawableLoader getDrawableLoader() {
-    return drawableLoader;
-  }
-
-  public IWXUserTrackAdapter getUtAdapter() {
-    return utAdapter;
-  }
-
-  public IWXSoLoaderAdapter getIWXSoLoaderAdapter() {
-    return soLoader;
-  }
-
-  public String getFramework() {
-    return framework;
-  }
-
-  public IWXStorageAdapter getStorageAdapter() {
-    return storageAdapter;
-  }
-
-  public URIAdapter getURIAdapter() {
-    return mURIAdapter;
-  }
-
-  public IWebSocketAdapterFactory getWebSocketAdapterFactory() {
-    return webSocketAdapterFactory;
-  }
-
-  public ClassLoaderAdapter getClassLoaderAdapter() {
-    return classLoaderAdapter;
-  }
-
-  public IApmGenerator getApmGenerater() {
-    return apmGenerater;
-  }
-
-  public IWXJsFileLoaderAdapter getJsFileLoaderAdapter() {
-    return jsFileLoaderAdapter;
-  }
-
-  public InitConfig setClassLoaderAdapter(ClassLoaderAdapter classLoaderAdapter) {
-    this.classLoaderAdapter = classLoaderAdapter;
-    return this;
-  }
-
-  public IWXJSExceptionAdapter getJSExceptionAdapter() {
-    return mJSExceptionAdapter;
-  }
-  public IWXJscProcessManager getJscProcessManager() {
-    return jscProcessManager;
-  }
-
-  @NonNull Iterable<String> getNativeLibraryList() {
-    if(nativeLibraryList == null){
-      nativeLibraryList = new LinkedList<>();
-    }
-    return nativeLibraryList;
-  }
-
-  private InitConfig() {
-  }
-
-  public static class Builder{
-    IWXHttpAdapter httpAdapter;
-    IWXImgLoaderAdapter imgAdapter;
-    IDrawableLoader drawableLoader;
-    IWXUserTrackAdapter utAdapter;
-    IWXStorageAdapter storageAdapter;
-    IWXSoLoaderAdapter soLoader;
-    URIAdapter mURIAdapter;
-    IWXJSExceptionAdapter mJSExceptionAdapter;
-    String framework;
-    IWebSocketAdapterFactory webSocketAdapterFactory;
-    ClassLoaderAdapter classLoaderAdapter;
-    IApmGenerator apmGenerater;
-    private IWXJsFileLoaderAdapter jsFileLoaderAdapter;
-    private List<String> nativeLibraryList = new LinkedList<>();
-
-    public IWXJscProcessManager getJscProcessManager() {
-      return jscProcessManager;
-    }
-
-    public Builder setJscProcessManager(IWXJscProcessManager jscProcessManager) {
-      this.jscProcessManager = jscProcessManager;
-      return this;
-    }
-
-    IWXJscProcessManager jscProcessManager;
-
-    public Builder(){
-
-    }
-
-    public Builder setHttpAdapter(IWXHttpAdapter httpAdapter) {
-      this.httpAdapter = httpAdapter;
-      return this;
-    }
-
-    public Builder setImgAdapter(IWXImgLoaderAdapter imgAdapter) {
-      this.imgAdapter = imgAdapter;
-      return this;
-    }
-
-    public Builder setDrawableLoader(IDrawableLoader drawableLoader){
-      this.drawableLoader=drawableLoader;
-      return this;
-    }
-
-    public Builder setUtAdapter(IWXUserTrackAdapter utAdapter) {
-      this.utAdapter = utAdapter;
-      return this;
-    }
-
-    public Builder setStorageAdapter(IWXStorageAdapter storageAdapter) {
-      this.storageAdapter = storageAdapter;
-      return this;
-    }
-
-    public Builder setURIAdapter(URIAdapter URIAdapter) {
-      mURIAdapter = URIAdapter;
-      return this;
-    }
-
-    public Builder setJSExceptionAdapter(IWXJSExceptionAdapter JSExceptionAdapter) {
-      mJSExceptionAdapter = JSExceptionAdapter;
-      return this;
-    }
-
-    public Builder setSoLoader(IWXSoLoaderAdapter loader) {
-      this.soLoader = loader;
-      return this;
-    }
-
-    public Builder setFramework(String framework){
-      this.framework=framework;
-      return this;
-    }
-
-    public Builder setWebSocketAdapterFactory(IWebSocketAdapterFactory factory) {
-      this.webSocketAdapterFactory = factory;
-      return this;
-    }
-
-    public Builder setClassLoaderAdapter(ClassLoaderAdapter classLoaderAdapter) {
-      this.classLoaderAdapter = classLoaderAdapter;
-      return this;
-    }
-
-    public Builder setApmGenerater(IApmGenerator apmGenerater){
-      this.apmGenerater =apmGenerater;
-      return this;
-    }
-
-    public Builder setJsFileLoaderAdapter(IWXJsFileLoaderAdapter jsFileLoaderAdapter) {
-      this.jsFileLoaderAdapter = jsFileLoaderAdapter;
-      return this;
-    }
-
-    public Builder addNativeLibrary(String name){
-      nativeLibraryList.add(name);
-      return this;
-    }
-
-    public InitConfig build(){
-      InitConfig config =  new InitConfig();
-      config.httpAdapter = this.httpAdapter;
-      config.imgAdapter = this.imgAdapter;
-      config.drawableLoader = this.drawableLoader;
-      config.utAdapter = this.utAdapter;
-      config.storageAdapter = this.storageAdapter;
-      config.soLoader=this.soLoader;
-      config.framework=this.framework;
-      config.mURIAdapter = this.mURIAdapter;
-      config.webSocketAdapterFactory = this.webSocketAdapterFactory;
-      config.mJSExceptionAdapter=this.mJSExceptionAdapter;
-      config.classLoaderAdapter = this.classLoaderAdapter;
-      config.apmGenerater = this.apmGenerater;
-      config.jsFileLoaderAdapter = this.jsFileLoaderAdapter;
-      config.jscProcessManager = this.jscProcessManager;
-      config.nativeLibraryList = this.nativeLibraryList;
-      return config;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/RenderContainer.java b/android/sdk/src/main/java/com/taobao/weex/RenderContainer.java
deleted file mode 100644
index cec6eaf..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/RenderContainer.java
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.os.Build;
-import android.util.AttributeSet;
-import android.view.View;
-
-
-import com.taobao.weex.render.WXAbstractRenderContainer;
-
-/**
- * Created by sospartan on 08/10/2016.
- */
-
-public class RenderContainer extends WXAbstractRenderContainer implements WeexFrameRateControl.VSyncListener{
-  private WeexFrameRateControl mFrameRateControl;
-
-  public RenderContainer(Context context) {
-    super(context);
-    mFrameRateControl = new WeexFrameRateControl(this);
-  }
-
-  public RenderContainer(Context context, AttributeSet attrs) {
-    super(context, attrs);
-    mFrameRateControl = new WeexFrameRateControl(this);
-  }
-
-  public RenderContainer(Context context, AttributeSet attrs, int defStyleAttr) {
-    super(context, attrs, defStyleAttr);
-    mFrameRateControl = new WeexFrameRateControl(this);
-  }
-
-  @TargetApi(Build.VERSION_CODES.LOLLIPOP)
-  public RenderContainer(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
-    super(context, attrs, defStyleAttr, defStyleRes);
-    mFrameRateControl = new WeexFrameRateControl(this);
-  }
-
-
-
-  @Override
-  public void onAttachedToWindow() {
-    super.onAttachedToWindow();
-    if (mFrameRateControl != null) {
-      mFrameRateControl.start();
-    }
-  }
-
-  @Override
-  protected void onDetachedFromWindow() {
-    super.onDetachedFromWindow();
-    if (mFrameRateControl != null) {
-      mFrameRateControl.stop();
-    }
-  }
-  @Override
-  public void dispatchWindowVisibilityChanged(int visibility) {
-    super.dispatchWindowVisibilityChanged(visibility);
-    if (visibility == View.GONE) {
-      if (mFrameRateControl != null) {
-        mFrameRateControl.stop();
-      }
-    } else if (visibility == View.VISIBLE) {
-      if (mFrameRateControl != null) {
-        mFrameRateControl.start();
-      }
-    }
-  }
-
-  @Override
-  public void OnVSync() {
-    if (mSDKInstance != null && mSDKInstance.get() != null) {
-      mSDKInstance.get().OnVSync();
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/Script.java b/android/sdk/src/main/java/com/taobao/weex/Script.java
deleted file mode 100644
index e18bb76..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/Script.java
+++ /dev/null
@@ -1,55 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex;
-
-import android.text.TextUtils;
-
-public class Script {
-    private String mContent;
-    private byte[] mBinary;
-
-    public Script(String content) {
-        mContent = content;
-    }
-
-    public Script(byte[] binary) {
-        mBinary = binary;
-    }
-
-    public String getContent() {
-        return mContent;
-    }
-
-    public byte[] getBinary() {
-        return mBinary;
-    }
-
-    public int length() {
-        if (mContent != null) {
-            return mContent.length();
-        } else if (mBinary != null){
-            return mBinary.length;
-        }
-        return 0;
-    }
-
-    public boolean isEmpty() {
-        return TextUtils.isEmpty(mContent) && (mBinary == null || mBinary.length == 0);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/WXEnvironment.java b/android/sdk/src/main/java/com/taobao/weex/WXEnvironment.java
deleted file mode 100644
index dbf6473..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/WXEnvironment.java
+++ /dev/null
@@ -1,693 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex;
-
-import static android.content.Context.MODE_PRIVATE;
-
-import android.annotation.SuppressLint;
-import android.app.Application;
-import android.content.Context;
-import android.content.SharedPreferences;
-import android.content.pm.ApplicationInfo;
-import android.content.pm.PackageInfo;
-import android.content.pm.PackageManager;
-import android.graphics.Typeface;
-import android.os.Environment;
-import android.telephony.TelephonyManager;
-import android.text.TextUtils;
-import com.taobao.weex.common.WXConfig;
-import com.taobao.weex.utils.FontDO;
-import com.taobao.weex.utils.LogLevel;
-import com.taobao.weex.utils.TypefaceUtil;
-import com.taobao.weex.utils.WXFileUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXSoInstallMgrSdk;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import dalvik.system.PathClassLoader;
-import java.io.BufferedReader;
-import java.io.File;
-import java.io.FileReader;
-import java.io.IOException;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-import java.util.HashMap;
-import java.util.Locale;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-
-public class WXEnvironment {
-
-  public static final String OS = "android";
-  public static String SYS_VERSION = android.os.Build.VERSION.RELEASE;
-  static{
-    if(SYS_VERSION != null && SYS_VERSION.toUpperCase(Locale.ROOT).equals("P")){
-        SYS_VERSION = "9.0.0";
-    }
-    if(SYS_VERSION != null && SYS_VERSION.toUpperCase(Locale.ROOT).equals("Q")){
-       SYS_VERSION = "10.0.0";
-    }
-  }
-  public static final String SYS_MODEL = android.os.Build.MODEL;
-  public static final String EAGLE = "eagle";
-  public static final String ENVIRONMENT = "environment";
-  public static final String WEEX_CURRENT_KEY = "wx_current_url";
-  /*********************
-   * Global config
-   ***************************/
-
-  public static String JS_LIB_SDK_VERSION = BuildConfig.buildJavascriptFrameworkVersion;
-
-  public static String WXSDK_VERSION = BuildConfig.buildVersion;
-  public static Application sApplication;
-  public static final String DEV_Id = getDevId();
-  @Deprecated
-  public static int sDefaultWidth = 750;
-  public volatile static boolean JsFrameworkInit = false;
-
-  public static final String SETTING_EXCLUDE_X86SUPPORT = "env_exclude_x86";
-
-  public static boolean SETTING_FORCE_VERTICAL_SCREEN = false;
-
-  /**
-   * auto adjust device width for when screen size change.
-   * */
-  public static boolean AUTO_ADJUST_ENV_DEVICE_WIDTH = true;
-
-  public static boolean AUTO_UPDATE_APPLICATION_SCREEN_SIZE = true;
-
-  public static volatile boolean sUseRunTimeApi = false;
-
-  /**
-   * Debug model
-   */
-  public static boolean sDebugMode = false;
-  public static final boolean sForceEnableDevTool = true;
-  public static String sDebugWsUrl = "";
-  public static boolean sDebugServerConnectable = false;
-  public static boolean sRemoteDebugMode = false;
-  public static String sRemoteDebugProxyUrl = "";
-  public static boolean sDebugNetworkEventReporterEnable = false;//debugtool network switch
-  public static long sJSLibInitTime = 0;
-
-  public static long sSDKInitStart = 0;// init start timestamp
-  public static long sSDKInitInvokeTime = 0;//time cost to invoke init method
-  public static long sSDKInitExecuteTime = 0;//time cost to execute init job
-  /** from init to sdk-ready **/
-  public static long sSDKInitTime =0;
-
-  public static long sJSFMStartListenerTime=0;
-
-  public static volatile boolean isWsFixMode = true;
-
-  /**
-   * component and modules ready
-   * */
-  public static long sComponentsAndModulesReadyTime = 0;
-
-  public static boolean sInAliWeex = false;
-
-  public static LogLevel sLogLevel = LogLevel.DEBUG;
-  private static boolean isApkDebug = true;
-  public static boolean isPerf = false;
-  private static boolean sDebugFlagInit = false;
-
-  private static boolean openDebugLog = true;
-
-  private static String sGlobalFontFamily;
-
-  public static final String CORE_SO_NAME = "weexcore";
-  public static final String CORE_JSS_SO_NAME = "weexjss";
-  public static final String CORE_JSB_SO_NAME = "weexjsb";
-  public static final String CORE_JST_SO_NAME = "weexjst";
-  public static final String CORE_JSC_SO_NAME = "JavaScriptCore";
-  private static  String CORE_JSS_SO_PATH = null;
-
-  public static  String CORE_JSS_RUNTIME_SO_PATH = null;
-
-  private static String CORE_JSS_ICU_PATH = null;
-
-  private static String CORE_JSC_SO_PATH = null;
-
-  public static String CORE_JSB_SO_PATH = null;
-
-  private static String COPY_SO_DES_DIR = null;
-
-  private static String LIB_LD_PATH = null;
-
-  private static Map<String, String> options = new ConcurrentHashMap<>();
-  static {
-    options.put(WXConfig.os, OS);
-    options.put(WXConfig.osName, OS);
-  }
-
-
-  public static synchronized WXDefaultSettings getWXDefaultSettings() {
-    if (mWXDefaultSettings == null && getApplication() != null) {
-      mWXDefaultSettings = new WXDefaultSettings(getApplication());
-    }
-    return mWXDefaultSettings;
-  }
-
-  public static synchronized String getDefaultSettingValue(String key, String defaultValue) {
-    WXDefaultSettings wxDefaultSettings = getWXDefaultSettings();
-    if (wxDefaultSettings == null || TextUtils.isEmpty(key)) {
-      return defaultValue;
-    }
-    return wxDefaultSettings.getValue(key, defaultValue);
-  }
-
-  public static synchronized void writeDefaultSettingsValue(String key, String value) {
-    WXDefaultSettings wxDefaultSettings = getWXDefaultSettings();
-    if (wxDefaultSettings == null
-            || TextUtils.isEmpty(key)
-            || TextUtils.isEmpty(value)) {
-      return;
-    }
-    wxDefaultSettings.saveValue(key, value);
-  }
-
-  private static WXDefaultSettings mWXDefaultSettings;
-
-  /**
-   * dynamic
-   */
-  public static boolean sDynamicMode = false;
-  public static String sDynamicUrl = "";
-
-  /**
-   * Fetch system information.
-   * @return map contains system information.
-   */
-  public static Map<String, String> getConfig() {
-    Map<String, String> configs = new HashMap<>();
-    configs.put(WXConfig.os, OS);
-    configs.put(WXConfig.appVersion, getAppVersionName());
-    configs.put(WXConfig.cacheDir, getAppCacheFile());
-    configs.put(WXConfig.devId, DEV_Id);
-    configs.put(WXConfig.sysVersion, SYS_VERSION);
-    configs.put(WXConfig.sysModel, SYS_MODEL);
-    configs.put(WXConfig.weexVersion, String.valueOf(WXSDK_VERSION));
-
-    try {
-      configs.put(WXConfig.layoutDirection, isLayoutDirectionRTL() ? "rtl" : "ltr");
-    } catch (Exception e) {
-      configs.put(WXConfig.layoutDirection, "ltr");
-    }
-
-    try {
-      if (isApkDebugable()) {
-        addCustomOptions(WXConfig.debugMode, "true");
-      }
-      addCustomOptions(WXConfig.scale, Float.toString(sApplication.getResources().getDisplayMetrics().density));
-      addCustomOptions(WXConfig.androidStatusBarHeight, Float.toString(WXViewUtils.getStatusBarHeight(sApplication)));
-    }catch (NullPointerException e){
-      //There is little chance of NullPointerException as sApplication may be null.
-      WXLogUtils.e("WXEnvironment scale Exception: ", e);
-    }
-    configs.putAll(getCustomOptions());
-    if(configs.get(WXConfig.appName)==null && sApplication!=null){
-      configs.put(WXConfig.appName, sApplication.getPackageName());
-    }
-    return configs;
-  }
-
-  /**
-   * Get the version of the current app.
-   */
-  public static String getAppVersionName() {
-    String versionName = "";
-    PackageManager manager;
-    PackageInfo info = null;
-    try {
-      manager = sApplication.getPackageManager();
-      info = manager.getPackageInfo(sApplication.getPackageName(), 0);
-      versionName = info.versionName;
-    } catch (Exception e) {
-      WXLogUtils.e("WXEnvironment getAppVersionName Exception: ", e);
-    }
-    return versionName;
-  }
-
-  /**
-   *
-   * @return string cache file
-   */
-  private static String getAppCacheFile() {
-    String cache = "";
-    try {
-      cache = sApplication.getApplicationContext().getCacheDir().getPath();
-    } catch (Exception e) {
-      WXLogUtils.e("WXEnvironment getAppCacheFile Exception: ", e);
-    }
-    return cache;
-  }
-
-
-  /**
-   * Use {@link #addCustomOptions(String, String)} to add custom options.
-   * Use {@link #getCustomOptions(String)} to get custom options
-   * @return
-   */
-  @Deprecated
-  public static Map<String, String> getCustomOptions() {
-    return options;
-  }
-
-  public static void addCustomOptions(String key, String value) {
-    options.put(key, value);
-  }
-
-  public static String getCustomOptions(String key){
-    return options.get(key);
-  }
-
-
-  @SuppressLint("SdCardPath")
-  public static String copySoDesDir() {
-    try {
-      if (TextUtils.isEmpty(COPY_SO_DES_DIR)) {
-        if (sApplication == null) {
-          WXLogUtils.e("sApplication is null, so copy path will be null");
-          return null;
-        }
-
-        String dirName = "/cache/weex/libs";
-        File desDir = null;
-        String cachePath = WXEnvironment.getApplication().getApplicationContext().getCacheDir().getPath();
-
-        if (TextUtils.isEmpty(cachePath)) {
-          desDir = new File(cachePath, dirName);
-        } else {
-          String pkgName = sApplication.getPackageName();
-          String toPath = "/data/data/" + pkgName + dirName;
-          desDir = new File(toPath);
-        }
-
-        if (!desDir.exists()) {
-          desDir.mkdirs();
-        }
-        COPY_SO_DES_DIR = desDir.getAbsolutePath();
-      }
-    } catch (Throwable e) {
-      WXLogUtils.e(WXLogUtils.getStackTrace(e));
-    }
-    return COPY_SO_DES_DIR;
-
-  }
-
-  @Deprecated
-  /**
-   * Use {@link #isHardwareSupport()} if you want to see whether current hardware support Weex.
-   */
-  public static boolean isSupport() {
-    boolean isInitialized = WXSDKEngine.isInitialized();
-    if(!isInitialized){
-      WXLogUtils.e("WXSDKEngine.isInitialized():" + isInitialized);
-    }
-    return isHardwareSupport() && isInitialized;
-  }
-
-  public static boolean isLayoutDirectionRTL() {
-    // support RTL
-    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR1) {
-      return sApplication.getApplicationContext().getResources().getBoolean(R.bool.weex_is_right_to_left);
-    }
-    return false;
-  }
-  /**
-   * Tell whether Weex can run on current hardware.
-   * @return true if weex can run on current hardware, otherwise false.
-   * Weex has removed the restrictions on the tablet, please use {@link #isCPUSupport()}
-   */
-  @Deprecated
-  public static boolean isHardwareSupport() {
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("isTableDevice:" + WXUtils.isTabletDevice());
-    }
-    return isCPUSupport();
-  }
-
-  /**
-   * Determine whether Weex supports the current CPU architecture
-   * @return true when support
-   */
-  public static boolean isCPUSupport(){
-    boolean excludeX86 = "true".equals(getCustomOptions().get(SETTING_EXCLUDE_X86SUPPORT));
-    boolean isX86AndExcluded = WXSoInstallMgrSdk.isX86() && excludeX86;
-    boolean isCPUSupport = WXSoInstallMgrSdk.isCPUSupport() && !isX86AndExcluded;
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("WXEnvironment.sSupport:" + isCPUSupport
-              + "isX86AndExclueded: "+ isX86AndExcluded);
-    }
-    return isCPUSupport;
-  }
-
-  public static boolean isApkDebugable() {
-    return isApkDebugable(sApplication);
-  }
-
-  public static boolean isApkDebugable(Application application) {
-    if (application == null) {
-      return false;
-    }
-
-    if (isPerf) {
-      return false;
-    }
-
-    if (sDebugFlagInit){
-      return isApkDebug;
-    }
-    try {
-      String debugModeConfig = getCustomOptions().get(WXConfig.debugMode);
-      if (TextUtils.isEmpty(debugModeConfig)){
-        ApplicationInfo info = application.getApplicationInfo();
-        isApkDebug = (info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0;
-      }else {
-        isApkDebug = Boolean.valueOf(debugModeConfig);
-      }
-    } catch (Exception e) {
-      /**
-       * Don't call WXLogUtils.e here,will cause stackoverflow
-       */
-      e.printStackTrace();
-      isApkDebug = false;
-    }
-    sDebugFlagInit = true;
-    return isApkDebug;
-  }
-
-  public static boolean isPerf() {
-    return isPerf;
-  }
-
-  @SuppressLint("HardwareIds")
-  private static String getDevId() {
-    String ret = "";
-    if(sApplication != null){
-      try{
-        ret = ((TelephonyManager) sApplication
-            .getSystemService(Context.TELEPHONY_SERVICE)).getDeviceId();
-      }catch (SecurityException | NullPointerException e){
-        WXLogUtils.e(WXLogUtils.getStackTrace(e));
-      }
-    }
-    return ret;
-  }
-
-  public static Application getApplication() {
-    return sApplication;
-  }
-
-  public void initMetrics() {
-    if (sApplication == null) {
-      return;
-    }
-  }
-
-  public static String getDiskCacheDir(Context context) {
-    if (context == null) {
-      return null;
-    }
-    String cachePath = null;
-    try {
-      if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState())
-              || !Environment.isExternalStorageRemovable()) {
-        cachePath = context.getExternalCacheDir().getPath();
-      } else {
-        cachePath = context.getCacheDir().getPath();
-      }
-    } catch (Exception e) {
-      e.printStackTrace();
-    }
-    return cachePath;
-  }
-
-  public static String getFilesDir(Context context) {
-    if (context == null) {
-      return "";
-    }
-    File filesDir = context.getFilesDir();
-    String path = "";
-    if (filesDir != null) {
-      path = filesDir.getPath();
-    } else {
-      path = WXEnvironment.getApplication().getApplicationInfo().dataDir;
-      path += File.separator;
-      path += "files";
-    }
-
-    return path;
-  }
-
-  public static String getCrashFilePath(Context context) {
-    if (context == null) {
-        return "";
-    }
-
-    File dir = context.getDir("crash", Context.MODE_PRIVATE);
-    if (dir == null)
-        return "";
-
-    String crashDir = dir.getAbsolutePath();
-
-    return crashDir;
-  }
-
-  public static String getGlobalFontFamilyName() {
-    return sGlobalFontFamily;
-  }
-
-  public static void setGlobalFontFamily(String fontFamilyName, Typeface typeface) {
-    WXLogUtils.d("GlobalFontFamily", "Set global font family: " + fontFamilyName);
-    sGlobalFontFamily = fontFamilyName;
-    if (!TextUtils.isEmpty(fontFamilyName)) {
-      if (typeface == null) {
-        TypefaceUtil.removeFontDO(fontFamilyName);
-      } else {
-        FontDO nativeFontDO = new FontDO(fontFamilyName, typeface);
-        TypefaceUtil.putFontDO(nativeFontDO);
-        WXLogUtils.d("TypefaceUtil", "Add new font: " + fontFamilyName);
-      }
-    }
-  }
-
-  public static boolean isOpenDebugLog() {
-    return openDebugLog;
-  }
-
-  public static void setOpenDebugLog(boolean openDebugLog) {
-    WXEnvironment.openDebugLog = openDebugLog;
-  }
-
-  public static void  setApkDebugable(boolean debugable){
-    isApkDebug  = debugable;
-    if(!isApkDebug){
-      openDebugLog = false;
-    }
-  }
-
-  public static String getCacheDir() {
-    final Application application = getApplication();
-    if (application == null || application.getApplicationContext() == null)
-      return null;
-    return application.getApplicationContext().getCacheDir().getPath();
-  }
-
-  public static String extractSo() {
-    File sourceFile = new File(getApplication().getApplicationContext().getApplicationInfo().sourceDir);
-    final String soDesPath = copySoDesDir();
-    if (sourceFile.exists() && !TextUtils.isEmpty(soDesPath)) {
-      try {
-        WXFileUtils.extractSo(sourceFile.getAbsolutePath(), soDesPath);
-      } catch (IOException e) {
-        WXLogUtils.e("extractSo error " + e.getMessage());
-//        e.printStackTrace();
-        return null;
-      }
-      return soDesPath;
-    }
-    return null;
-  }
-
-  private static String findIcuPath() {
-    File file = new File("/proc/self/maps");
-    BufferedReader reader = null;
-    try {
-      reader = new BufferedReader(new FileReader(file));
-      String tempString = null;
-      while ((tempString = reader.readLine()) != null) {
-        if (tempString.contains("icudt")) {
-
-          int i = tempString.indexOf('/');
-
-          String substring = tempString.substring(i);
-          return substring.trim();
-        }
-      }
-      reader.close();
-    } catch (IOException e) {
-      e.printStackTrace();
-    } finally {
-      if (reader != null) {
-        try {
-          reader.close();
-        } catch (IOException e1) {
-        }
-      }
-    }
-
-    return null;
-  }
-
-
-  public static String findSoPath(String libName) {
-    String soPath = ((PathClassLoader) (WXEnvironment.class.getClassLoader())).findLibrary(libName);
-    if (!TextUtils.isEmpty(soPath)) {
-      File soFile = new File(soPath);
-      if (soFile.exists()) {
-        WXLogUtils.e(libName + "'s Path is" + soPath);
-        return soFile.getAbsolutePath();
-      } else {
-        WXLogUtils.e(libName + "'s Path is " + soPath + " but file does not exist");
-      }
-    }
-
-    String realName = "lib" + libName + ".so";
-    String cacheDir = getCacheDir();
-    if (TextUtils.isEmpty(cacheDir)) {
-      WXLogUtils.e("cache dir is null");
-      return "";
-    }
-
-
-    if (cacheDir.indexOf("/cache") > 0) {
-      soPath = new File(cacheDir.replace("/cache", "/lib"), realName).getAbsolutePath();
-    }
-
-
-    final File soFile = new File(soPath);
-    if (soFile.exists()) {
-      WXLogUtils.e(libName + "use lib so");
-      return soPath;
-    } else {
-      //unzip from apk file
-      final String extractSoPath = extractSo();
-      if (!TextUtils.isEmpty(extractSoPath)) {
-        return new File(extractSoPath, realName).getAbsolutePath();
-      }
-    }
-    return soPath;
-  }
-
-  public static String getLibJScRealPath() {
-    if(TextUtils.isEmpty(CORE_JSC_SO_PATH)) {
-      CORE_JSC_SO_PATH = findSoPath(CORE_JSC_SO_NAME);
-      WXLogUtils.e("findLibJscRealPath " + CORE_JSC_SO_PATH);
-    }
-    return CORE_JSC_SO_PATH;
-  }
-
-  public static String getLibJssRealPath() {
-    if (WXEnvironment.sUseRunTimeApi && !TextUtils.isEmpty(CORE_JSS_RUNTIME_SO_PATH)){
-      WXLogUtils.d("test-> findLibJssRuntimeRealPath " + CORE_JSS_RUNTIME_SO_PATH);
-      return CORE_JSS_RUNTIME_SO_PATH;
-    }
-
-    if(TextUtils.isEmpty(CORE_JSS_SO_PATH)) {
-      CORE_JSS_SO_PATH = findSoPath(CORE_JSS_SO_NAME);
-      WXLogUtils.d("test-> findLibJssRealPath " + CORE_JSS_SO_PATH);
-    }
-
-    return CORE_JSS_SO_PATH;
-  }
-
-  public static String getLibJssIcuPath() {
-    if(TextUtils.isEmpty(CORE_JSS_ICU_PATH)){
-      CORE_JSS_ICU_PATH = findIcuPath();
-    }
-
-    return CORE_JSS_ICU_PATH;
-  }
-
-  public static String getLibLdPath() {
-    if (TextUtils.isEmpty(LIB_LD_PATH)) {
-      ClassLoader classLoader = WXEnvironment.class.getClassLoader();
-      try {
-        Method getLdLibraryPath = classLoader.getClass().getMethod("getLdLibraryPath", new Class[0]);
-        LIB_LD_PATH = (String) getLdLibraryPath.invoke(classLoader, new Object[0]);
-      } catch (IllegalAccessException e) {
-        e.printStackTrace();
-      } catch (InvocationTargetException e) {
-        e.printStackTrace();
-      } catch (NoSuchMethodException e) {
-        e.printStackTrace();
-      }
-    }
-
-    if(TextUtils.isEmpty(LIB_LD_PATH)) {
-      try {
-        String property = System.getProperty("java.library.path");
-        String libJScRealPath = getLibJScRealPath();
-        if(!TextUtils.isEmpty(libJScRealPath)) {
-          LIB_LD_PATH = new File(libJScRealPath).getParent() + ":" + property;
-        }
-      } catch (Exception e) {
-        e.printStackTrace();
-      }
-    }
-
-    WXLogUtils.d("getLibLdPath is " + LIB_LD_PATH);
-    return LIB_LD_PATH;
-  }
-
-  public static class WXDefaultSettings {
-    private String configName = "weex_default_settings";
-    private SharedPreferences sharedPreferences = null;
-    public WXDefaultSettings(Application application) {
-      if(application != null) {
-        sharedPreferences = application.getSharedPreferences(configName, MODE_PRIVATE);
-      }
-    }
-
-    public synchronized String getValue(String key, String defaultValue) {
-      if(sharedPreferences == null || TextUtils.isEmpty(key)) {
-        WXLogUtils.i("get default settings " + key + " return default value :" + defaultValue);
-        return defaultValue;
-      }
-
-      String result = sharedPreferences.getString(key, defaultValue);
-      WXLogUtils.i("get default settings " + key + " : " + result);
-      return result;
-    }
-
-    public synchronized void saveValue(String key, String value) {
-      if (sharedPreferences == null
-              || TextUtils.isEmpty(key)
-              || TextUtils.isEmpty(value)) {
-        return;
-      }
-      WXLogUtils.i("save default settings " + key + ":" + value);
-      SharedPreferences.Editor editor = sharedPreferences.edit();
-      editor.putString(key, value);
-      editor.apply();
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/WXGlobalEventModule.java b/android/sdk/src/main/java/com/taobao/weex/WXGlobalEventModule.java
deleted file mode 100644
index b487ba2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/WXGlobalEventModule.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.common.WXModule;
-
-import java.util.Map;
-
-/**
- * Created by lixinke on 16/8/25.
- */
-public class WXGlobalEventModule extends WXModule {
-
-
-  @JSMethod
-  public void addEventListener(String eventName, String callback) {
-    mWXSDKInstance.addEventListener(eventName,callback);
-  }
-
-  public void removeEventListener(String eventName, String callback) {
-    mWXSDKInstance.removeEventListener(eventName,callback);
-  }
-
-  @JSMethod
-  public void removeEventListener(String eventName){
-    mWXSDKInstance.removeEventListener(eventName);
-  }
-
-
-  @Override
-  public void addEventListener(String eventName, String callback, Map<String, Object> options) {
-    super.addEventListener(eventName, callback, options);
-    addEventListener(eventName,callback);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/WXGlobalEventReceiver.java b/android/sdk/src/main/java/com/taobao/weex/WXGlobalEventReceiver.java
deleted file mode 100644
index 82e8363..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/WXGlobalEventReceiver.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.HashMap;
-
-public class WXGlobalEventReceiver extends BroadcastReceiver {
-
-  public static final String EVENT_NAME = "eventName";
-  public static final String EVENT_PARAMS = "eventParams";
-  public static final String EVENT_ACTION = "wx_global_action";
-  public static final String EVENT_WX_INSTANCEID = "wx_instanceid";
-
-  private WXSDKInstance mWXSDKInstance;
-
-  public WXGlobalEventReceiver() {
-  }
-
-  public WXGlobalEventReceiver(WXSDKInstance instance) {
-    mWXSDKInstance = instance;
-  }
-
-  @Override
-  public void onReceive(Context context, Intent intent) {
-    String eventName = intent.getStringExtra(EVENT_NAME);
-    String params = intent.getStringExtra(EVENT_PARAMS);
-    HashMap<String, Object> maps = null;
-    try {
-      maps = com.alibaba.fastjson.JSON.parseObject(params, HashMap.class);
-      mWXSDKInstance.fireGlobalEventCallback(eventName, maps);
-    } catch (Exception e) {
-      WXLogUtils.e("global-receive",e);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/WXHttpListener.java b/android/sdk/src/main/java/com/taobao/weex/WXHttpListener.java
deleted file mode 100644
index 15d9cf2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/WXHttpListener.java
+++ /dev/null
@@ -1,307 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex;
-
-import android.net.Uri;
-import android.text.TextUtils;
-
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXPerformance;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.common.WXResponse;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.tracing.WXTracing;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.tools.LogDetail;
-
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * load bundle js listener
- */
-public class WXHttpListener implements IWXHttpAdapter.OnHttpListener {
-
-    private String pageName;
-    private Map<String, Object> options;
-    private String jsonInitData;
-    private WXRenderStrategy flag;
-    private WXSDKInstance instance;
-    private long startRequestTime;
-    private int traceId;
-    private WXPerformance mWXPerformance;
-    private WXInstanceApm mApmForInstance;
-    private IWXUserTrackAdapter mUserTrackAdapter;
-    public boolean isPreDownLoadMode = false;
-    private boolean isInstanceReady =false;
-    private boolean isResponseHasWait = false;
-    private WXResponse mResponse;
-    private LogDetail mLogDetail;
-
-    private String mBundleUrl;
-
-    public WXHttpListener(WXSDKInstance instance) {
-        if(instance != null) {
-            mLogDetail = instance.mTimeCalculator.createLogDetail("downloadBundleJS");
-        }
-        this.instance = instance;
-        this.traceId = WXTracing.nextId();
-        this.mWXPerformance = instance.getWXPerformance();
-        this.mApmForInstance = instance.getApmForInstance();
-        this.mUserTrackAdapter = WXSDKManager.getInstance().getIWXUserTrackAdapter();
-        if (WXTracing.isAvailable()) {
-            WXTracing.TraceEvent event = WXTracing.newEvent("downloadBundleJS", instance.getInstanceId(), -1);
-            event.iid = instance.getInstanceId();
-            event.tname = "Network";
-            event.ph = "B";
-            event.traceId = traceId;
-            event.submit();
-        }
-    }
-
-    public WXHttpListener(WXSDKInstance instance, String bundleUrl) {
-        this(instance);
-        this.startRequestTime = System.currentTimeMillis();
-        this.mBundleUrl = bundleUrl;
-    }
-
-    public WXHttpListener(WXSDKInstance instance, String pageName, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag, long startRequestTime) {
-        this(instance);
-        this.pageName = pageName;
-        this.options = options;
-        this.jsonInitData = jsonInitData;
-        this.flag = flag;
-        this.startRequestTime = startRequestTime;
-        this.mBundleUrl = instance.getBundleUrl();
-    }
-
-    public void setSDKInstance(WXSDKInstance instance) {
-        this.instance = instance;
-    }
-
-    protected WXSDKInstance getInstance() {
-        return instance;
-    }
-
-    @Override
-    public void onHttpStart() {
-        if (this.instance != null
-                && this.instance.getWXStatisticsListener() != null) {
-            this.instance.getWXStatisticsListener().onHttpStart();
-            if(mLogDetail != null) {
-                mLogDetail.taskStart();
-            }
-        }
-    }
-
-    @Override
-    public void onHeadersReceived(int statusCode, Map<String,List<String>> headers) {
-        if (this.instance != null
-                && this.instance.getWXStatisticsListener() != null) {
-            this.instance.getWXStatisticsListener().onHeadersReceived();
-            this.instance.onHttpStart();
-        }
-        if(this.instance != null
-                && this.instance.responseHeaders != null
-                && headers != null){
-            this.instance.responseHeaders.putAll(headers);
-        }
-    }
-
-    @Override
-    public void onHttpUploadProgress(int uploadProgress) {
-
-    }
-
-    @Override
-    public void onHttpResponseProgress(int loadedLength) {
-        instance.getApmForInstance().extInfo.put(WXInstanceApm.VALUE_BUNDLE_LOAD_LENGTH,loadedLength);
-    }
-
-    @Override
-    public void onHttpFinish(WXResponse response) {
-        if(mLogDetail != null) {
-            mLogDetail.taskEnd();
-        }
-        if (this.instance != null
-                && this.instance.getWXStatisticsListener() != null) {
-            this.instance.getWXStatisticsListener().onHttpFinish();
-        }
-
-        if (WXTracing.isAvailable()) {
-            WXTracing.TraceEvent event = WXTracing.newEvent("downloadBundleJS", instance.getInstanceId(), -1);
-            event.traceId = traceId;
-            event.tname = "Network";
-            event.ph = "E";
-            event.extParams = new HashMap<>();
-            if (response != null && response.originalData != null) {
-                event.extParams.put("BundleSize", response.originalData.length);
-            }
-            event.submit();
-        }
-
-        mWXPerformance.networkTime = System.currentTimeMillis() - startRequestTime;
-        if(null!= response && response.extendParams!=null){
-            mApmForInstance.updateRecordInfo(response.extendParams);
-            Object actualNetworkTime=response.extendParams.get("actualNetworkTime");
-            mWXPerformance.actualNetworkTime=actualNetworkTime instanceof Long?(long)actualNetworkTime:0;
-
-            Object pureNetworkTime=response.extendParams.get("pureNetworkTime");
-            mWXPerformance.pureNetworkTime=pureNetworkTime instanceof Long?(long)pureNetworkTime:0;
-
-            Object connectionType=response.extendParams.get("connectionType");
-            mWXPerformance.connectionType=connectionType instanceof String?(String)connectionType:"";
-
-            Object packageSpendTime=response.extendParams.get("packageSpendTime");
-            mWXPerformance.packageSpendTime=packageSpendTime instanceof Long ?(long)packageSpendTime:0;
-
-            Object syncTaskTime=response.extendParams.get("syncTaskTime");
-            mWXPerformance.syncTaskTime=syncTaskTime instanceof Long ?(long)syncTaskTime:0;
-
-            Object requestType=response.extendParams.get("requestType");
-            mWXPerformance.requestType=requestType instanceof String?(String)requestType:"none";
-
-            Object cacheType = response.extendParams.get(WXPerformance.Dimension.cacheType.toString());
-            if(cacheType instanceof String){
-                mWXPerformance.cacheType = (String) cacheType;
-            }
-
-            Object zCacheInfo = response.extendParams.get("zCacheInfo");
-            mWXPerformance.zCacheInfo = zCacheInfo instanceof String?(String)zCacheInfo:"";
-
-            if(isNet(mWXPerformance.requestType) && mUserTrackAdapter!=null){
-                WXPerformance performance=new WXPerformance(instance.getInstanceId());
-                if(!TextUtils.isEmpty(mBundleUrl)){
-                    try {
-                        performance.args= Uri.parse(mBundleUrl).buildUpon().clearQuery().toString();
-                    } catch (Exception e) {
-                        performance.args=pageName;
-                    }
-                }
-                if(!"200".equals(response.statusCode)){
-                    performance.errCode= WXErrorCode.WX_ERR_JSBUNDLE_DOWNLOAD.getErrorCode();
-                    performance.appendErrMsg(response.errorCode);
-                    performance.appendErrMsg("|");
-                    performance.appendErrMsg(response.errorMsg);
-
-                }else if("200".equals(response.statusCode) && (response.originalData==null || response.originalData.length<=0)){
-                    performance.errCode=WXErrorCode.WX_ERR_JSBUNDLE_DOWNLOAD.getErrorCode();
-                    performance.appendErrMsg(response.statusCode);
-                    performance.appendErrMsg("|template is null!");
-                }else {
-                    performance.errCode=WXErrorCode.WX_SUCCESS.getErrorCode();
-                }
-
-                if (mUserTrackAdapter != null) {
-                    mUserTrackAdapter.commit(instance.getContext(), null, IWXUserTrackAdapter.JS_DOWNLOAD, performance, null);
-                }
-            }
-        }
-
-        if (isPreDownLoadMode){
-            if (isInstanceReady){
-                WXLogUtils.d("test->", "DownLoad didHttpFinish on http" );
-                didHttpFinish(response);
-            }else {
-                WXLogUtils.d("test->", "DownLoad end before activity created" );
-                mResponse = response;
-                isResponseHasWait = true;
-            }
-        }else {
-            didHttpFinish(response);
-        }
-
-    }
-
-    public void onInstanceReady(){
-        if (!isPreDownLoadMode){
-            return;
-        }
-        this.isInstanceReady = true;
-        if (isResponseHasWait){
-            WXLogUtils.d("test->", "preDownLoad didHttpFinish on ready" );
-            this.didHttpFinish(mResponse);
-        }
-
-    }
-
-    private void didHttpFinish(WXResponse response){
-        String wxErrorCode = WXInstanceApm.VALUE_ERROR_CODE_DEFAULT;
-        if (response!=null && response.originalData!=null && TextUtils.equals("200", response.statusCode)) {
-            mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_END);
-            onSuccess(response);
-
-            // check content-type
-        } else if (TextUtils.equals(WXErrorCode.WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR.getErrorCode(),
-                response.statusCode)) {
-            WXLogUtils.e("user intercept: WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR");
-            wxErrorCode = WXErrorCode.WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR.getErrorCode();
-            instance.onRenderError(wxErrorCode,
-                    "|response.errorMsg==" + response.errorMsg +
-                            "|instance bundleUrl = \n" + instance.getBundleUrl() +
-                            "|instance requestUrl = \n" + Uri.decode(WXSDKInstance.requestUrl)
-            );
-            onFail(response);
-
-            // check content-length
-        } else if (response!=null && response.originalData!=null && TextUtils.equals("-206", response.statusCode)) {
-            WXLogUtils.e("user intercept: WX_DEGRAD_ERR_NETWORK_CHECK_CONTENT_LENGTH_FAILED");
-            wxErrorCode =  WXErrorCode.WX_DEGRAD_ERR_NETWORK_CHECK_CONTENT_LENGTH_FAILED.getErrorCode();
-            instance.onRenderError(wxErrorCode ,
-                    WXErrorCode.WX_DEGRAD_ERR_NETWORK_CHECK_CONTENT_LENGTH_FAILED.getErrorCode() +
-                            "|response.errorMsg==" + response.errorMsg
-            );
-            onFail(response);
-        }
-        else {
-            wxErrorCode = WXErrorCode.WX_DEGRAD_ERR_NETWORK_BUNDLE_DOWNLOAD_FAILED.getErrorCode();
-            instance.onRenderError(wxErrorCode,
-                    response.errorMsg);
-            onFail(response);
-        }
-        if (!WXInstanceApm.VALUE_ERROR_CODE_DEFAULT.equals(wxErrorCode)){
-            mApmForInstance.addProperty(WXInstanceApm.KEY_PROPERTIES_ERROR_CODE,wxErrorCode);
-        }
-    }
-
-    private boolean isNet(String requestType){
-
-        return "network".equals(requestType) || "2g".equals(requestType) || "3g".equals(requestType)
-                || "4g".equals(requestType) || "wifi".equals(requestType) || "other".equals(requestType)
-                || "unknown".equals(requestType);
-    }
-
-    public void onSuccess(WXResponse response) {
-        if (flag==WXRenderStrategy.DATA_RENDER_BINARY){
-            instance.render(pageName, response.originalData, options, jsonInitData);
-        }else {
-            String template = new String(response.originalData);
-            instance.render(pageName, template, options, jsonInitData, flag);
-        }
-    }
-
-    public void onFail(WXResponse response) {
-
-    }
-}
-
-
diff --git a/android/sdk/src/main/java/com/taobao/weex/WXSDKEngine.java b/android/sdk/src/main/java/com/taobao/weex/WXSDKEngine.java
deleted file mode 100644
index d9ef522..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/WXSDKEngine.java
+++ /dev/null
@@ -1,603 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex;
-
-import static com.taobao.weex.WXEnvironment.CORE_SO_NAME;
-
-import android.app.Application;
-import android.content.Context;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.support.v4.content.LocalBroadcastManager;
-import android.text.TextUtils;
-import com.taobao.weex.adapter.IDrawableLoader;
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.adapter.IWXImgLoaderAdapter;
-import com.taobao.weex.adapter.IWXJSExceptionAdapter;
-import com.taobao.weex.adapter.IWXJsFileLoaderAdapter;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.appfram.clipboard.WXClipboardModule;
-import com.taobao.weex.appfram.navigator.IActivityNavBarSetter;
-import com.taobao.weex.appfram.navigator.INavigator;
-import com.taobao.weex.appfram.navigator.WXNavigatorModule;
-import com.taobao.weex.appfram.pickers.WXPickersModule;
-import com.taobao.weex.appfram.storage.IWXStorageAdapter;
-import com.taobao.weex.appfram.storage.WXStorageModule;
-import com.taobao.weex.appfram.websocket.WebSocketModule;
-import com.taobao.weex.bridge.ModuleFactory;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.bridge.WXModuleManager;
-import com.taobao.weex.bridge.WXServiceManager;
-import com.taobao.weex.common.Destroyable;
-import com.taobao.weex.common.TypeModuleFactory;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXException;
-import com.taobao.weex.common.WXInstanceWrap;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.http.WXStreamModule;
-import com.taobao.weex.performance.WXStateRecord;
-import com.taobao.weex.ui.ExternalLoaderComponentHolder;
-import com.taobao.weex.ui.IExternalComponentGetter;
-import com.taobao.weex.ui.IExternalModuleGetter;
-import com.taobao.weex.ui.IFComponentHolder;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import com.taobao.weex.ui.WXComponentRegistry;
-import com.taobao.weex.ui.animation.WXAnimationModule;
-import com.taobao.weex.ui.component.Textarea;
-import com.taobao.weex.ui.component.WXA;
-import com.taobao.weex.ui.component.WXBasicComponentType;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXDiv;
-import com.taobao.weex.ui.component.WXEmbed;
-import com.taobao.weex.ui.component.WXHeader;
-import com.taobao.weex.ui.component.WXImage;
-import com.taobao.weex.ui.component.WXIndicator;
-import com.taobao.weex.ui.component.WXInput;
-import com.taobao.weex.ui.component.WXLoading;
-import com.taobao.weex.ui.component.WXLoadingIndicator;
-import com.taobao.weex.ui.component.WXRefresh;
-import com.taobao.weex.ui.component.WXScroller;
-import com.taobao.weex.ui.component.WXSlider;
-import com.taobao.weex.ui.component.WXSliderNeighbor;
-import com.taobao.weex.ui.component.WXSwitch;
-import com.taobao.weex.ui.component.WXText;
-import com.taobao.weex.ui.component.WXVideo;
-import com.taobao.weex.ui.component.WXWeb;
-import com.taobao.weex.ui.component.list.HorizontalListComponent;
-import com.taobao.weex.ui.component.list.SimpleListComponent;
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.ui.component.list.WXListComponent;
-import com.taobao.weex.ui.component.list.template.WXRecyclerTemplateList;
-import com.taobao.weex.ui.component.richtext.WXRichText;
-import com.taobao.weex.ui.config.AutoScanConfigRegister;
-import com.taobao.weex.ui.module.WXDeviceInfoModule;
-import com.taobao.weex.ui.module.ConsoleLogModule;
-import com.taobao.weex.ui.module.WXLocaleModule;
-import com.taobao.weex.ui.module.WXMetaModule;
-import com.taobao.weex.ui.module.WXModalUIModule;
-import com.taobao.weex.ui.module.WXTimerModule;
-import com.taobao.weex.ui.module.WXWebViewModule;
-import com.taobao.weex.utils.LogLevel;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXSoInstallMgrSdk;
-import com.taobao.weex.utils.batch.BatchOperationHelper;
-import com.taobao.weex.utils.cache.RegisterCache;
-import java.io.Serializable;
-import java.util.HashMap;
-import java.util.Map;
-
-public class WXSDKEngine implements Serializable {
-
-  public static final String JS_FRAMEWORK_RELOAD="js_framework_reload";
-  private static final String V8_SO_NAME = CORE_SO_NAME;
-  private volatile static boolean mIsInit = false;
-  private volatile static boolean mIsSoInit = false;
-  private static final Object mLock = new Object();
-  private static final String TAG = "WXSDKEngine";
-
-  /**
-   * Deprecated. Use {@link #initialize(Application, InitConfig)} instead.
-   */
-  @Deprecated
-  public static void init(Application application) {
-    init(application, null);
-  }
-
-  /**
-   * Deprecated. Use {@link #initialize(Application, InitConfig)} instead.
-   */
-  @Deprecated
-  public static void init(Application application, IWXUserTrackAdapter utAdapter) {
-    init(application, utAdapter, null);
-  }
-
-  /**
-   * Deprecated. Use {@link #initialize(Application, InitConfig)} instead.
-   */
-  @Deprecated
-  public static void init(Application application, IWXUserTrackAdapter utAdapter, String framework) {
-    initialize(application,
-            new InitConfig.Builder()
-                    .setUtAdapter(utAdapter)
-                    .build()
-    );
-  }
-
-
-  public static boolean isInitialized(){
-    synchronized(mLock) {
-
-      return mIsInit && WXEnvironment.JsFrameworkInit;
-    }
-  }
-
-  public static boolean isSoInitialized(){
-    synchronized(mLock) {
-      return mIsSoInit;
-    }
-  }
-
-  /**
-   *
-   * @param application
-   * @param config initial configurations or null
-   */
-  public static void initialize(Application application,InitConfig config){
-    synchronized (mLock) {
-      if (mIsInit) {
-        return;
-      }
-      long start = System.currentTimeMillis();
-      WXEnvironment.sSDKInitStart = start;
-      if(WXEnvironment.isApkDebugable(application)){
-        WXEnvironment.sLogLevel = LogLevel.DEBUG;
-      }else{
-        WXEnvironment.sLogLevel = LogLevel.WARN;
-      }
-      doInitInternal(application,config);
-      registerApplicationOptions(application);
-      WXEnvironment.sSDKInitInvokeTime = System.currentTimeMillis()-start;
-      WXLogUtils.renderPerformanceLog("SDKInitInvokeTime", WXEnvironment.sSDKInitInvokeTime);
-      mIsInit = true;
-    }
-  }
-
-  private static void registerApplicationOptions(final Application application) {
-
-    if (application == null) {
-      WXLogUtils.e(TAG, "RegisterApplicationOptions application is null");
-      return;
-    }
-
-    Resources resources = application.getResources();
-    registerCoreEnv("screen_width_pixels", String.valueOf(resources.getDisplayMetrics().widthPixels));
-    registerCoreEnv("screen_height_pixels", String.valueOf(resources.getDisplayMetrics().heightPixels));
-
-    int resourceId = resources.getIdentifier("status_bar_height", "dimen", "android");
-    if (resourceId > 0) {
-      int statusBarHeight = resources.getDimensionPixelSize(resourceId);
-      registerCoreEnv("status_bar_height", String.valueOf(statusBarHeight));
-    }
-  }
-
-  private static void doInitInternal(final Application application,final InitConfig config){
-    WXEnvironment.sApplication = application;
-    if(application == null){
-      WXLogUtils.e(TAG, " doInitInternal application is null");
-      WXExceptionUtils.commitCriticalExceptionRT(null,
-              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
-              "doInitInternal",
-              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT.getErrorMsg() + "WXEnvironment sApplication is null",
-              null);
-    }
-    WXEnvironment.JsFrameworkInit = false;
-
-    WXBridgeManager.getInstance().postWithName(new Runnable() {
-      @Override
-      public void run() {
-        long start = System.currentTimeMillis();
-        WXSDKManager sm = WXSDKManager.getInstance();
-        sm.onSDKEngineInitialize();
-        if(config != null ) {
-          sm.setInitConfig(config);
-        }
-        WXSoInstallMgrSdk.init(application,
-                sm.getIWXSoLoaderAdapter(),
-                sm.getWXStatisticsListener());
-        final IWXUserTrackAdapter userTrackAdapter= config!=null?config.getUtAdapter():null;
-        final int version = 1;
-        mIsSoInit = WXSoInstallMgrSdk.initSo(V8_SO_NAME, version, userTrackAdapter);
-        WXSoInstallMgrSdk.copyJssRuntimeSo();
-        if(config!=null) {
-          for (String libraryName : config.getNativeLibraryList()) {
-            WXSoInstallMgrSdk.initSo(libraryName, version, userTrackAdapter);
-          }
-        }
-        if (!mIsSoInit) {
-          WXExceptionUtils.commitCriticalExceptionRT(null,
-                  WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
-                  "doInitInternal",
-                  WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT.getErrorMsg() + "isSoInit false",
-                  null);
-          return;
-        }
-        sm.initScriptsFramework(config!=null?config.getFramework():null);
-
-        WXEnvironment.sSDKInitExecuteTime = System.currentTimeMillis() - start;
-        WXLogUtils.renderPerformanceLog("SDKInitExecuteTime", WXEnvironment.sSDKInitExecuteTime);
-      }
-    },null,"doInitWeexSdkInternal");
-    WXStateRecord.getInstance().startJSThreadWatchDog();
-    register();
-  }
-
-  @Deprecated
-  public static void init(Application application, String framework, IWXUserTrackAdapter utAdapter, IWXImgLoaderAdapter imgLoaderAdapter, IWXHttpAdapter httpAdapter) {
-    initialize(application,
-            new InitConfig.Builder()
-                    .setUtAdapter(utAdapter)
-                    .setHttpAdapter(httpAdapter)
-                    .setImgAdapter(imgLoaderAdapter)
-                    .build()
-    );
-  }
-
-  public static void setJSExcetptionAdapter(IWXJSExceptionAdapter excetptionAdapter){
-    WXSDKManager.getInstance().setIWXJSExceptionAdapter(excetptionAdapter);
-  }
-
-  private static void register() {
-    BatchOperationHelper batchHelper = new BatchOperationHelper(WXBridgeManager.getInstance());
-    try {
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXText.class,
-                      new WXText.Creator()
-              ),
-              false,
-              WXBasicComponentType.TEXT
-      );
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXDiv.class,
-                      new WXDiv.Ceator()
-              ),
-              false,
-              WXBasicComponentType.CONTAINER,
-              WXBasicComponentType.DIV,
-              WXBasicComponentType.HEADER,
-              WXBasicComponentType.FOOTER
-      );
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXImage.class,
-                      new WXImage.Creator()
-              ),
-              false,
-              WXBasicComponentType.IMAGE,
-              WXBasicComponentType.IMG
-      );
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXScroller.class,
-                      new WXScroller.Creator()
-              ),
-              false,
-              WXBasicComponentType.SCROLLER
-      );
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXSlider.class,
-                      new WXSlider.Creator()
-              ),
-              true,
-              WXBasicComponentType.SLIDER,
-              WXBasicComponentType.CYCLE_SLIDER
-      );
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXSliderNeighbor.class,
-                      new WXSliderNeighbor.Creator()
-              ),
-              true,
-              WXBasicComponentType.SLIDER_NEIGHBOR
-      );
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXCell.class,
-                      new WXCell.Creator()
-              ),
-              true,
-              WXBasicComponentType.CELL);
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXListComponent.class,
-                      new WXListComponent.Creator()
-              ),
-              true,
-              WXBasicComponentType.LIST,
-              WXBasicComponentType.VLIST,
-              WXBasicComponentType.RECYCLER,
-              WXBasicComponentType.WATERFALL);
-
-      registerComponent(
-              new SimpleComponentHolder(
-                      WXRichText.class,
-                      new WXRichText.Creator()
-              ),
-              false,
-              WXBasicComponentType.RICHTEXT
-      );
-
-      String simpleList = "simplelist";
-      registerComponent(SimpleListComponent.class,false,simpleList);
-      registerComponent(WXRecyclerTemplateList.class, false,WXBasicComponentType.RECYCLE_LIST);
-      registerComponent(HorizontalListComponent.class,false,WXBasicComponentType.HLIST);
-      registerComponent(WXBasicComponentType.CELL_SLOT, WXCell.class, true);
-      registerComponent(WXBasicComponentType.INDICATOR, WXIndicator.class, true);
-      registerComponent(WXBasicComponentType.VIDEO, WXVideo.class, false);
-      registerComponent(WXBasicComponentType.INPUT, WXInput.class, false);
-      registerComponent(WXBasicComponentType.TEXTAREA, Textarea.class,false);
-      registerComponent(WXBasicComponentType.SWITCH, WXSwitch.class, false);
-      registerComponent(WXBasicComponentType.A, WXA.class, false);
-      registerComponent(WXBasicComponentType.EMBED, WXEmbed.class, true);
-      registerComponent(WXBasicComponentType.WEB, WXWeb.class);
-      registerComponent(WXBasicComponentType.REFRESH, WXRefresh.class);
-      registerComponent(WXBasicComponentType.LOADING, WXLoading.class);
-      registerComponent(WXBasicComponentType.LOADING_INDICATOR, WXLoadingIndicator.class);
-      registerComponent(WXBasicComponentType.HEADER, WXHeader.class);
-
-      registerModule("modal", WXModalUIModule.class);
-      registerModule("instanceWrap", WXInstanceWrap.class);
-      registerModule("animation", WXAnimationModule.class);
-      registerModule("webview", WXWebViewModule.class);
-      registerModule("navigator", WXNavigatorModule.class);
-      registerModule("stream", WXStreamModule.class);
-      registerModule("timer", WXTimerModule.class);
-      registerModule("storage", WXStorageModule.class);
-      registerModule("clipboard", WXClipboardModule.class);
-      registerModule("globalEvent",WXGlobalEventModule.class);
-      registerModule("picker", WXPickersModule.class);
-      registerModule("meta", WXMetaModule.class);
-      registerModule("webSocket", WebSocketModule.class);
-      registerModule("locale", WXLocaleModule.class);
-      registerModule("deviceInfo", WXDeviceInfoModule.class);
-      registerModule("sdk-console-log", ConsoleLogModule.class);
-    } catch (WXException e) {
-      WXLogUtils.e("[WXSDKEngine] register:", e);
-    }
-
-    if(RegisterCache.getInstance().enableAutoScan()) {
-      AutoScanConfigRegister.doScanConfig();
-    }
-
-    batchHelper.flush();
-  }
-
-  /**
-   *
-   * Register component. The registration is singleton in {@link WXSDKEngine} level
-   * @param type name of component. Same as type field in the JS.
-   * @param clazz the class of the {@link WXComponent} to be registered.
-   * @param appendTree true for appendTree flag
-   * @return true for registration success, false for otherwise.
-   * @throws WXException Throws exception if type conflicts.
-   */
-  public static boolean registerComponent(String type, Class<? extends WXComponent> clazz, boolean appendTree) throws WXException {
-    return registerComponent(clazz, appendTree,type);
-  }
-
-  public static boolean registerComponent(String type, IExternalComponentGetter componentGetter, boolean appendTree) throws WXException {
-    return registerComponent(new ExternalLoaderComponentHolder(type,componentGetter), appendTree,type);
-  }
-
-  /**
-   *
-   * Register component. The registration is singleton in {@link WXSDKEngine} level
-   * @param clazz the class of the {@link WXComponent} to be registered.
-   * @param appendTree true for appendTree flag
-   * @return true for registration success, false for otherwise.
-   * @param names names(alias) of component. Same as type field in the JS.
-   * @throws WXException Throws exception if type conflicts.
-   */
-  public static boolean registerComponent(Class<? extends WXComponent> clazz, boolean appendTree,String ... names) throws WXException {
-    if(clazz == null){
-      return false;
-    }
-    SimpleComponentHolder holder = new SimpleComponentHolder(clazz);
-    return registerComponent(holder,appendTree,names);
-  }
-
-
-  public static boolean registerComponent(IFComponentHolder holder, boolean appendTree, String ... names) throws WXException {
-    boolean result =  true;
-    try {
-      for (String name : names) {
-        Map<String, Object> componentInfo = new HashMap<>();
-        if (appendTree) {
-          componentInfo.put("append", "tree");
-        }
-        result = result && WXComponentRegistry.registerComponent(name, holder, componentInfo);
-      }
-      return result;
-    } catch (Throwable e) {
-      e.printStackTrace();
-      return result;
-    }
-  }
-
-  /**
-   * Register module. This is a wrapper method for
-   * {@link #registerModule(String, Class, boolean)}. The module register here only need to
-   * be singleton in {@link WXSDKInstance} level.
-   * @param moduleName  module name
-   * @param moduleClass module to be registered.
-   * @return true for registration success, false for otherwise.
-   * {@link WXModuleManager#registerModule(String, ModuleFactory, boolean)}
-   */
-  public static <T extends WXModule> boolean registerModule(String moduleName, Class<T> moduleClass,boolean global) throws WXException {
-    return moduleClass != null && registerModule(moduleName, new TypeModuleFactory<>(moduleClass), global);
-  }
-
-  /**
-   * Register module. This is a wrapper method for
-   * {@link #registerModule(String, Class, boolean)}. The module register here only need to
-   * be singleton in {@link WXSDKInstance} level.
-   * @param moduleName  module name
-   * @param factory module factory to be registered. You can override {@link DestroyableModuleFactory#buildInstance()} to customize module creation.
-   * @return true for registration success, false for otherwise.
-   * {@link WXModuleManager#registerModule(String, ModuleFactory, boolean)}
-   */
-  public static <T extends WXModule> boolean registerModuleWithFactory(String moduleName, DestroyableModuleFactory factory, boolean global) throws WXException {
-    return registerModule(moduleName, factory,global);
-  }
-
-
-  public static <T extends WXModule> boolean registerModuleWithFactory(String moduleName, IExternalModuleGetter factory, boolean global) throws WXException {
-    return registerModule(moduleName, factory.getExternalModuleClass(moduleName,WXEnvironment.getApplication()),global);
-  }
-
-  public static <T extends WXModule> boolean registerModule(String moduleName, ModuleFactory factory, boolean global) throws WXException {
-    return WXModuleManager.registerModule(moduleName, factory,global);
-  }
-
-  public static boolean registerModule(String moduleName, Class<? extends WXModule> moduleClass) throws WXException {
-    return registerModule(moduleName, moduleClass,false);
-  }
-
-  public static boolean registerService(String name, String serviceScript, Map<String, Object> options) {
-    return WXServiceManager.registerService(name, serviceScript, options);
-  }
-
-  public static boolean unRegisterService(String name) {
-    return WXServiceManager.unRegisterService(name);
-  }
-
-  /**
-   * module implement {@link Destroyable}
-   */
-  public static abstract class DestroyableModule extends WXModule implements Destroyable {}
-
-  public static  abstract  class DestroyableModuleFactory<T extends DestroyableModule> extends TypeModuleFactory<T> {
-    public DestroyableModuleFactory(Class<T> clz) {
-      super(clz);
-    }
-  }
-
-  public static void callback(String instanceId, String funcId, Map<String, Object> data) {
-    WXSDKManager.getInstance().callback(instanceId, funcId, data);
-  }
-
-  /**
-   * Model switch, only applicable for developer model
-   * @param debug
-   */
-  public static void restartBridge(boolean debug) {
-    WXEnvironment.sDebugMode = debug;
-    WXSDKManager.getInstance().restartBridge();
-  }
-
-  public static boolean registerComponent(String type, Class<? extends WXComponent> clazz) throws WXException {
-    return WXComponentRegistry.registerComponent(type, new SimpleComponentHolder(clazz),new HashMap<String, Object>());
-  }
-
-  public static boolean registerComponent(Map<String, Object> componentInfo, Class<? extends WXComponent> clazz) throws WXException {
-    if(componentInfo == null){
-      return false;
-    }
-    String type = (String)componentInfo.get("type");
-    if(TextUtils.isEmpty(type)){
-      return false;
-    }
-    return WXComponentRegistry.registerComponent(type,new SimpleComponentHolder(clazz), componentInfo);
-  }
-
-  public static void addCustomOptions(String key, String value) {
-    WXEnvironment.addCustomOptions(key, value);
-  }
-
-  public static IWXUserTrackAdapter getIWXUserTrackAdapter() {
-    return WXSDKManager.getInstance().getIWXUserTrackAdapter();
-  }
-
-  public static IWXImgLoaderAdapter getIWXImgLoaderAdapter() {
-    return WXSDKManager.getInstance().getIWXImgLoaderAdapter();
-  }
-
-  public static IDrawableLoader getDrawableLoader() {
-    return WXSDKManager.getInstance().getDrawableLoader();
-  }
-
-  public static IWXHttpAdapter getIWXHttpAdapter() {
-    return WXSDKManager.getInstance().getIWXHttpAdapter();
-  }
-
-  public static IWXStorageAdapter getIWXStorageAdapter() {
-    return WXSDKManager.getInstance().getIWXStorageAdapter();
-  }
-
-
-  public static IWXJsFileLoaderAdapter getIWXJsFileLoaderAdapter() {
-    return WXSDKManager.getInstance().getIWXJsFileLoaderAdapter();
-  }
-
-  public static IActivityNavBarSetter getActivityNavBarSetter() {
-    return WXSDKManager.getInstance().getActivityNavBarSetter();
-  }
-
-  public static INavigator getNavigator() {
-    return WXSDKManager.getInstance().getNavigator();
-  }
-
-  public static  void setNavigator(INavigator navigator) {
-    WXSDKManager.getInstance().setNavigator(navigator);
-  }
-
-  public static void setActivityNavBarSetter(IActivityNavBarSetter activityNavBarSetter) {
-    WXSDKManager.getInstance().setActivityNavBarSetter(activityNavBarSetter);
-  }
-
-  public static void reload(final Context context,String framework, boolean remoteDebug) {
-    WXEnvironment.sRemoteDebugMode = remoteDebug;
-    WXBridgeManager.getInstance().restart();
-    WXBridgeManager.getInstance().initScriptsFramework(framework);
-
-    WXServiceManager.reload();
-    WXModuleManager.reload();
-    WXComponentRegistry.reload();
-    WXSDKManager.getInstance().postOnUiThread(new Runnable() {
-      @Override
-      public void run() {
-        LocalBroadcastManager.getInstance(context).sendBroadcast(new Intent(JS_FRAMEWORK_RELOAD));
-      }
-    }, 0);
-  }
-  public static void reload(final Context context, boolean remoteDebug) {
-    reload(context,null,remoteDebug);
-  }
-
-  public static void reload() {
-    reload(WXEnvironment.getApplication(), WXEnvironment.sRemoteDebugMode);
-  }
-
-  public static void registerCoreEnv(String key, String value) {
-    WXBridgeManager.getInstance().registerCoreEnv(key, value);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/WXSDKInstance.java b/android/sdk/src/main/java/com/taobao/weex/WXSDKInstance.java
deleted file mode 100644
index 22293e6..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/WXSDKInstance.java
+++ /dev/null
@@ -1,2500 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex;
-
-import static com.taobao.weex.common.WXErrorCode.WX_ERR_RELOAD_PAGE;
-import static com.taobao.weex.http.WXHttpUtil.KEY_USER_AGENT;
-
-import android.app.Activity;
-import android.app.AlertDialog;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.net.Uri;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.support.annotation.WorkerThread;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-import android.util.Log;
-import android.view.Menu;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ScrollView;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.adapter.IDrawableLoader;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.adapter.IWXImgLoaderAdapter;
-import com.taobao.weex.adapter.IWXJscProcessManager;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.appfram.websocket.IWebSocketAdapter;
-import com.taobao.weex.bridge.EventResult;
-import com.taobao.weex.bridge.NativeInvokeHelper;
-import com.taobao.weex.bridge.SimpleJSCallback;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.bridge.WXModuleManager;
-import com.taobao.weex.bridge.WXParams;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.Destroyable;
-import com.taobao.weex.common.OnWXScrollListener;
-import com.taobao.weex.common.RenderTypes;
-import com.taobao.weex.common.WXConfig;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.common.WXPerformance;
-import com.taobao.weex.common.WXRefreshData;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.common.WXRequest;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.http.WXHttpUtil;
-import com.taobao.weex.instance.InstanceOnFireEventInterceptor;
-import com.taobao.weex.jsEngine.JSContext;
-import com.taobao.weex.jsEngine.JSEngine;
-import com.taobao.weex.layout.ContentBoxMeasurement;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.performance.WXStateRecord;
-import com.taobao.weex.performance.WhiteScreenUtils;
-import com.taobao.weex.render.WXAbstractRenderContainer;
-import com.taobao.weex.tracing.WXTracing;
-import com.taobao.weex.ui.action.GraphicActionAddElement;
-import com.taobao.weex.ui.component.NestedContainer;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXEmbed;
-import com.taobao.weex.ui.flat.FlatGUIContext;
-import com.taobao.weex.ui.view.WXScrollView;
-import com.taobao.weex.utils.Trace;
-import com.taobao.weex.utils.WXDeviceUtils;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXFileUtils;
-import com.taobao.weex.utils.WXJsonUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXReflectionUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import com.taobao.weex.utils.cache.RegisterCache;
-import com.taobao.weex.utils.tools.LogDetail;
-import com.taobao.weex.utils.tools.TimeCalculator;
-import java.io.Serializable;
-import java.lang.ref.WeakReference;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-import java.util.PriorityQueue;
-import java.util.concurrent.ConcurrentHashMap;
-
-
-/**
- * Each instance of WXSDKInstance represents an running weex instance.
- * It can be a pure weex view, or mixed with native view
- */
-public class WXSDKInstance implements IWXActivityStateListener,View.OnLayoutChangeListener {
-
-  private static  final  String SOURCE_TEMPLATE_BASE64_MD5 = "templateSourceBase64MD5";
-
-  /**
-   * Devtool protocol
-   */
-  public static String ACTION_DEBUG_INSTANCE_REFRESH = "DEBUG_INSTANCE_REFRESH";
-  public static String ACTION_INSTANCE_RELOAD = "INSTANCE_RELOAD";
-
-  //Performance
-  public boolean mEnd = false;
-  public boolean mHasCreateFinish = false;
-  public static final String BUNDLE_URL = "bundleUrl";
-  private IWXUserTrackAdapter mUserTrackAdapter;
-  private IWXRenderListener mRenderListener;
-  private IWXStatisticsListener mStatisticsListener;
-  /** package **/ Context mContext;
-  private final String mInstanceId;
-  private WXAbstractRenderContainer mRenderContainer;
-  private WXComponent mRootComp;
-  private boolean mRendered;
-  private WXRefreshData mLastRefreshData;
-  private NestedInstanceInterceptor mNestedInstanceInterceptor;
-  private String mBundleUrl = "";
-  public static String requestUrl = "requestUrl";
-  private boolean isDestroy=false;
-  private boolean hasException = false;
-  private boolean isRenderSuccess = false;
-  private boolean createInstanceHeartBeat = false;
-  private Map<String,Serializable> mUserTrackParams;
-  private NativeInvokeHelper mNativeInvokeHelper;
-  private boolean isCommit=false;
-  private WXGlobalEventReceiver mGlobalEventReceiver=null;
-  private boolean trackComponent;
-  private boolean enableLayerType = true;
-  private boolean mNeedValidate = false;
-  private boolean mNeedReLoad = false;
-  private boolean mUseScroller = false;
-  private int mInstanceViewPortWidth = 750;
-  private boolean enableFullScreenHeight = false;
-  private WXInstanceApm mApmForInstance;
-  private @NonNull
-  FlatGUIContext mFlatGUIContext =new FlatGUIContext();
-
-  private Map<String,String> mContainerInfo;
-
-  public boolean isNewFsEnd = false;
-  private List<JSONObject> componentsInfoExceedGPULimit  = new LinkedList<>();
-
-  /**
-   * bundle type
-   */
-  public WXBridgeManager.BundType bundleType;
-  public long mRenderStartNanos;
-  public int mExecJSTraceId = WXTracing.nextId();
-
-  private boolean isViewDisAppear = false;
-
-  /**
-   *for network tracker
-   */
-  public String mwxDims[] = new String [5];
-  public long measureTimes[] = new long [5];
-
-  public WeakReference<String> templateRef;
-  public Map<String,List<String>> responseHeaders = new HashMap<>();
-
-  /**
-   * Render strategy.
-   */
-  private WXRenderStrategy mRenderStrategy = WXRenderStrategy.APPEND_ASYNC;
-
-  private boolean mDisableSkipFrameworkInit = false;
-
-  /**
-   * Render start time
-   */
-  public long mRenderStartTime;
-  /**
-   * Refresh start time
-   */
-  private long mRefreshStartTime;
-  private WXPerformance mWXPerformance;
-  private ScrollView mScrollView;
-  private WXScrollView.WXScrollViewListener mWXScrollViewListener;
-
-  private List<OnWXScrollListener> mWXScrollListeners;
-
-  private List<String> mLayerOverFlowListeners;
-
-  private List<ActionBarHandler> mWXActionbarHandlers;
-
-  private List<OnBackPressedHandler> mWXBackPressedHandlers;
-
-  private List<OnActivityResultHandler> mWXOnActivityResultHandlers;
-
-  private WXSDKInstance mParentInstance;
-
-  private String mRenderType = RenderTypes.RENDER_TYPE_NATIVE;
-
-  private boolean mPageDirty = true;
-  private boolean mFixMultiThreadBug = false;
-
-  public TimeCalculator mTimeCalculator;
-  /**
-   * Default Width And Viewport is 750,
-   * when screen width change, we adjust viewport to adapter screen change
-   * */
-  private boolean mAutoAdjustDeviceWidth = WXEnvironment.AUTO_ADJUST_ENV_DEVICE_WIDTH;
-
-  public  List<JSONObject> getComponentsExceedGPULimit(){return componentsInfoExceedGPULimit;}
-  @RestrictTo(Scope.LIBRARY)
-  public void setComponentsInfoExceedGPULimit(JSONObject component){
-    if(component!= null && !component.isEmpty()){
-      componentsInfoExceedGPULimit.add(component);
-    }
-  }
-
-  public List<String> getLayerOverFlowListeners() {
-    return mLayerOverFlowListeners;
-  }
-
-  public void addLayerOverFlowListener(String ref) {
-    if (mLayerOverFlowListeners == null)
-      mLayerOverFlowListeners = new ArrayList<>();
-    mLayerOverFlowListeners.add(ref);
-  }
-
-  public void removeLayerOverFlowListener(String ref) {
-    if (mLayerOverFlowListeners != null)
-      mLayerOverFlowListeners.remove(ref);
-  }
-
-  /**
-   * whether we are in preRender mode
-   * */
-  private volatile boolean isPreRenderMode;
-
-  private boolean mCurrentGround = false;
-  private ComponentObserver mComponentObserver;
-  private Map<String, GraphicActionAddElement> inactiveAddElementAction = new ArrayMap<>();
-
-  private Map<Long, ContentBoxMeasurement> mContentBoxMeasurements = new ArrayMap<>();
-
-  private List<InstanceOnFireEventInterceptor> mInstanceOnFireEventInterceptorList;
-
-
-  /**
-   * network handler
-   */
-  public interface ImageNetworkHandler {
-    public String fetchLocal(String url);
-  }
-
-  public interface StreamNetworkHandler {
-    public String fetchLocal(String url);
-  }
-
-  public interface CustomFontNetworkHandler {
-    public String fetchLocal(String url);
-  }
-
-  private ImageNetworkHandler mImageNetworkHandler;
-
-  private StreamNetworkHandler mStreamNetworkHandler;
-
-  private CustomFontNetworkHandler mCustomFontNetworkHandler;
-
-  public ImageNetworkHandler getImageNetworkHandler() {
-    return mImageNetworkHandler;
-  }
-
-  public void setImageNetworkHandler(ImageNetworkHandler imageNetworkHandler) {
-    this.mImageNetworkHandler = imageNetworkHandler;
-  }
-
-  public StreamNetworkHandler getStreamNetworkHandler() {
-    return mStreamNetworkHandler;
-  }
-
-  public void setStreamNetworkHandler(StreamNetworkHandler streamNetworkHandler) {
-    this.mStreamNetworkHandler = streamNetworkHandler;
-  }
-
-  public CustomFontNetworkHandler getCustomFontNetworkHandler() {
-    return mCustomFontNetworkHandler;
-  }
-
-  public void setCustomFontNetworkHandler(CustomFontNetworkHandler customFontNetworkHandler) {
-    this.mCustomFontNetworkHandler = customFontNetworkHandler;
-  }
-
-
-  /**
-   *  ActionBar Handler
-   */
-
-  public interface ActionBarHandler {
-    boolean onSupportNavigateUp();
-  }
-
-  public interface OnBackPressedHandler {
-    boolean onBackPressed();
-  }
-
-  public static abstract class OnActivityResultHandler {
-    private String id;
-
-    public OnActivityResultHandler(String id) {
-      this.id = id;
-    }
-
-    public abstract boolean onActivityResult(int requestCode, int resultCode, Intent data, String id);
-
-    public boolean onActivityResult(int requestCode, int resultCode, Intent data) {
-      return onActivityResult(requestCode, resultCode, data, id);
-    }
-  }
-
-  /**
-   * set make weexCore run in single process mode
-   * @param flag true means weexCore run in single process mode or multi process mode
-   */
-  public void setUseSingleProcess(boolean flag) {
-    WXBridgeManager.getInstance().setUseSingleProcess(flag);
-  }
-
-  /**
-   * set open SandBox
-   * @param flag
-   */
-  public void setUseSandBox(boolean flag) {
-    WXBridgeManager.getInstance().setSandBoxContext(flag);
-  }
-
-  public PriorityQueue<WXEmbed> hiddenEmbeds;
-
-  private int maxHiddenEmbedsNum = -1; //max hidden embed num, -1 standard for ulimit
-
-  public int getMaxHiddenEmbedsNum() {
-    return maxHiddenEmbedsNum;
-  }
-
-  public void setMaxHiddenEmbedsNum(int maxHiddenEmbedsNum) {
-    this.maxHiddenEmbedsNum = maxHiddenEmbedsNum;
-  }
-
-  @WorkerThread
-  @RestrictTo(Scope.LIBRARY)
-  public void addInActiveAddElementAction(String ref, GraphicActionAddElement action){
-    inactiveAddElementAction.put(ref, action);
-  }
-
-  @WorkerThread
-  @RestrictTo(Scope.LIBRARY)
-  public void removeInActiveAddElmentAction(String ref){
-    inactiveAddElementAction.remove(ref);
-  }
-
-  @WorkerThread
-  @RestrictTo(Scope.LIBRARY)
-  public GraphicActionAddElement getInActiveAddElementAction(String ref){
-    return inactiveAddElementAction.get(ref);
-  }
-
-  /**
-   * If anchor is created manually(etc. define a layout xml resource ),
-   * be aware do not add it to twice when {@link IWXRenderListener#onViewCreated(WXSDKInstance, View)}.
-   * @param a
-   */
-  public void setRenderContainer(RenderContainer a){
-     setWXAbstractRenderContainer(a);
-  }
-
-  public void setWXAbstractRenderContainer(WXAbstractRenderContainer a){
-    if(a != null) {
-      a.setSDKInstance(this);
-      a.addOnLayoutChangeListener(this);
-    }
-
-    mRenderContainer = a;
-    if (mRenderContainer != null && mRenderContainer.getLayoutParams() != null
-            && mRenderContainer.getLayoutParams().width == ViewGroup.LayoutParams.WRAP_CONTENT) {
-      WXBridgeManager.getInstance().post(new Runnable() {
-        @Override
-        public void run() {
-          WXBridgeManager.getInstance().setRenderContentWrapContentToCore(true, getInstanceId());
-        }
-      });
-    } else {
-      WXBridgeManager.getInstance().post(new Runnable() {
-        @Override
-        public void run() {
-          WXBridgeManager.getInstance().setRenderContentWrapContentToCore(false, getInstanceId());
-        }
-      });
-    }
-  }
-
-  private int mMaxDeepLayer;
-
-  public boolean isTrackComponent() {
-    return trackComponent;
-  }
-
-  public void setTrackComponent(boolean trackComponent) {
-    this.trackComponent = trackComponent;
-  }
-
-  /**
-   * Tell whether it is enabled to change the layerType
-   * {@link android.view.View#setLayerType(int, Paint)}
-   * @return True for enable to change the layerType of component, false otherwise. The default
-   * is True
-   */
-  public boolean isLayerTypeEnabled() {
-    return enableLayerType;
-  }
-
-  /**
-   * Enable the ability of changing layerType. e.g. {@link android.view.View#setLayerType(int, Paint)}
-   * Disable the ability of changing layerType will have tremendous <strong>performance
-   * punishment</strong>.
-   *
-   * <strong>Do not</strong> set this to false unless you know exactly what you are doing.
-   * @param enable True for enable to change the layerType of component, false otherwise. The default
-   * is True
-   */
-  public void enableLayerType(boolean enable) {
-    enableLayerType = enable;
-  }
-
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  public @NonNull
-  FlatGUIContext getFlatUIContext(){
-    return mFlatGUIContext;
-  }
-
-  public boolean isNeedValidate() {
-    return mNeedValidate;
-  }
-
-  public boolean isNeedReLoad() {
-    return mNeedReLoad;
-  }
-
-  public void setNeedLoad(boolean load) {
-    mNeedReLoad = load;
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  public void  setEnableFullScreenHeight(boolean fullScreenHeight){enableFullScreenHeight = fullScreenHeight;}
-
-  @RestrictTo(Scope.LIBRARY)
-  public boolean isFullScreenHeightEnabled(){return enableFullScreenHeight;}
-
-  public boolean isUseScroller() {
-    return mUseScroller;
-  }
-
-  public void setUseScroller(boolean use) {
-    mUseScroller = use;
-  }
-
-  public void setInstanceViewPortWidth(int instanceViewPortWidth) {
-    setInstanceViewPortWidth(instanceViewPortWidth,false);
-
-  }
-  public void setInstanceViewPortWidth(int instanceViewPortWidth,boolean fromMetaModule){
-    this.mInstanceViewPortWidth = instanceViewPortWidth;
-    this.mAutoAdjustDeviceWidth = false;
-    if(!fromMetaModule){
-      WXBridgeManager.getInstance().setViewPortWidth(getInstanceId(), mInstanceViewPortWidth);
-    }
-  }
-  public void resetDeviceDisplayOfPage(){
-    WXBridgeManager.getInstance().setDeviceDisplayOfPage(getInstanceId(), WXViewUtils.getScreenWidth(getContext()), WXViewUtils.getScreenHeight(getContext()));
-  }
-  public void setPageKeepRawCssStyles(){
-    WXBridgeManager.getInstance().setPageArgument(getInstanceId(),"reserveCssStyles","true");
-  }
-  public void reloadPageLayout(){
-    WXBridgeManager.getInstance().reloadPageLayout(getInstanceId());
-  }
-
-  public void setAutoAdjustDeviceWidth(boolean autoAdjustViewPort){
-    this.mAutoAdjustDeviceWidth = autoAdjustViewPort;
-  }
-
-  public boolean isAutoAdjustDeviceWidth(){
-    return mAutoAdjustDeviceWidth;
-  }
-
-  private void setDeviceDisplay(float deviceWith, float deviceHeight, float scale){
-    WXBridgeManager.getInstance().setDeviceDisplay(getInstanceId(), deviceWith, deviceHeight, scale);
-  }
-
-
-
-  public int getInstanceViewPortWidth(){
-    return mInstanceViewPortWidth;
-  }
-
-  public interface OnInstanceVisibleListener{
-    void onAppear();
-    void onDisappear();
-  }
-  private List<OnInstanceVisibleListener> mVisibleListeners = new ArrayList<>();
-
-  public WXSDKInstance(Context context) {
-    mInstanceId = WXSDKManager.getInstance().generateInstanceId();
-    init(context);
-  }
-
-  //for preInit
-  public WXSDKInstance(){
-    mInstanceId = WXSDKManager.getInstance().generateInstanceId();
-    mWXPerformance = new WXPerformance(mInstanceId);
-    mApmForInstance = new WXInstanceApm(mInstanceId);
-    WXSDKManager.getInstance().getAllInstanceMap().put(mInstanceId,this);
-    mTimeCalculator = new TimeCalculator(this);
-    initFixMultiThreadFlag();
-  }
-
-
-  private void initFixMultiThreadFlag() {
-    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
-    if (adapter != null) {
-      String config = adapter.getConfig("android_weex_ext_config", "fixMultiThreadBug", "true");
-      mFixMultiThreadBug = Boolean.parseBoolean(config);
-    }
-  }
-
-  /**
-   * For unittest only.
-   */
-  @RestrictTo(Scope.TESTS)
-  WXSDKInstance(Context context,String id) {
-    mInstanceId = id;
-    init(context);
-  }
-
-  public WXComponent getRootComponent() {
-    return mRootComp;
-  }
-
-  public void setNestedInstanceInterceptor(NestedInstanceInterceptor interceptor){
-    mNestedInstanceInterceptor = interceptor;
-  }
-
-  public final WXSDKInstance createNestedInstance(NestedContainer container){
-    WXSDKInstance sdkInstance = newNestedInstance();
-    if(mNestedInstanceInterceptor != null){
-      mNestedInstanceInterceptor.onCreateNestInstance(sdkInstance,container);
-    }
-    if(sdkInstance != null){
-        sdkInstance.setComponentObserver(this.getComponentObserver());
-    }
-    return sdkInstance;
-  }
-
-  protected WXSDKInstance newNestedInstance() {
-    return new WXSDKInstance(mContext);
-  }
-  public boolean isHasException() {
-    return hasException;
-  }
-
-  public void setHasException(boolean hasException) {
-    this.hasException = hasException;
-  }
-
-  public void createInstanceFuncHeartBeat() {
-    WXLogUtils.d("createInstanceFuncHeartBeat: " + mInstanceId);
-    this.createInstanceHeartBeat = true;
-    getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_END_EXCUTE_BUNDLE);
-  }
-
-  public void addOnInstanceVisibleListener(OnInstanceVisibleListener l){
-    mVisibleListeners.add(l);
-  }
-
-  public void removeOnInstanceVisibleListener(OnInstanceVisibleListener l){
-    mVisibleListeners.remove(l);
-  }
-
-  public void init(Context context) {
-    initFixMultiThreadFlag();
-    RegisterCache.getInstance().idle(true);
-    mContext = context;
-    mContainerInfo = new HashMap<>(4);
-    mNativeInvokeHelper = new NativeInvokeHelper(mInstanceId);
-
-    if (null == mWXPerformance){
-      mWXPerformance = new WXPerformance(mInstanceId);
-    }
-    if (null == mApmForInstance){
-      mApmForInstance = new WXInstanceApm(mInstanceId);
-    }
-
-    mWXPerformance.WXSDKVersion = WXEnvironment.WXSDK_VERSION;
-    mWXPerformance.JSLibInitTime = WXEnvironment.sJSLibInitTime;
-
-    mUserTrackAdapter=WXSDKManager.getInstance().getIWXUserTrackAdapter();
-
-    WXSDKManager.getInstance().getAllInstanceMap().put(mInstanceId,this);
-
-    mContainerInfo.put(WXInstanceApm.KEY_PAGE_PROPERTIES_CONTAINER_NAME, context instanceof Activity
-            ? context.getClass().getSimpleName()
-            :"unKnowContainer"
-    );
-    mContainerInfo.put(WXInstanceApm.KEY_PAGE_PROPERTIES_INSTANCE_TYPE,"page");
-
-    // WXBridgeManager.getInstance().checkJsEngineMultiThread();
-    mDisableSkipFrameworkInit = isDisableSkipFrameworkInDataRender();
-
-    if(mTimeCalculator == null) {
-      mTimeCalculator = new TimeCalculator(this);
-    }
-  }
-
-  /**
-   * Set a Observer for component.
-   * This observer will be called in each component, should not doing
-   * anything will impact render performance.
-   *
-   * @param observer
-   */
-  public void setComponentObserver(ComponentObserver observer){
-    mComponentObserver = observer;
-  }
-
-  public ComponentObserver getComponentObserver(){
-    return mComponentObserver;
-  }
-
-  public NativeInvokeHelper getNativeInvokeHelper() {
-    return mNativeInvokeHelper;
-  }
-
-  @Deprecated
-  public void setBizType(String bizType) {
-    if (!TextUtils.isEmpty(bizType)) {
-      mWXPerformance.bizType = bizType;
-    }
-  }
-
-  public ScrollView getScrollView() {
-    return mScrollView;
-  }
-
-  public void setRootScrollView(ScrollView scrollView) {
-    mScrollView = scrollView;
-    if (mWXScrollViewListener != null && mScrollView instanceof WXScrollView) {
-      ((WXScrollView) mScrollView).addScrollViewListener(mWXScrollViewListener);
-    }
-  }
-
-  @Deprecated
-  public void registerScrollViewListener(WXScrollView.WXScrollViewListener scrollViewListener) {
-    mWXScrollViewListener = scrollViewListener;
-  }
-
-  @Deprecated
-  public WXScrollView.WXScrollViewListener getScrollViewListener() {
-    return mWXScrollViewListener;
-  }
-
-  @Deprecated
-  public void setIWXUserTrackAdapter(IWXUserTrackAdapter adapter) {
-  }
-
-  public void setContainerInfo(String key,String val){
-    mContainerInfo.put(key,val);
-  }
-
-  public Map<String, String> getContainerInfo() {
-    return mContainerInfo;
-  }
-
-  /**
-   * Render template asynchronously, use {@link WXRenderStrategy#APPEND_ASYNC} as render strategy
-   * @param template bundle js
-   * @param options  os   iphone/android/ipad
-   *                 weexversion    Weex version(like 1.0.0)
-   *                 appversion     App version(like 1.0.0)
-   *                 devid        Device id(like Aqh9z8dRJNBhmS9drLG5BKCmXhecHUXIZoXOctKwFebH)
-   *                 sysversion    Device system version(like 5.4.4、7.0.4, should be used with os)
-   *                 sysmodel     Device model(like iOS:"MGA82J/A", android:"MI NOTE LTE")
-   *                 Time    UNIX timestamp, UTC+08:00
-   *                 TTID(Optional)
-   *                 MarkertId
-   *                 Appname(Optional)  tm,tb,qa
-   *                 Bundleurl(Optional)  template url
-   * @param jsonInitData Initial data for rendering
-   */
-  public void render(String template, Map<String, Object> options, String jsonInitData) {
-    render(template, options, jsonInitData, WXRenderStrategy.APPEND_ASYNC);
-  }
-
-  /**
-   * Render template asynchronously
-   * @param template bundle js
-   * @param options  os   iphone/android/ipad
-   *                 weexversion    Weex version(like 1.0.0)
-   *                 appversion     App version(like 1.0.0)
-   *                 devid        Device id(like Aqh9z8dRJNBhmS9drLG5BKCmXhecHUXIZoXOctKwFebH)
-   *                 sysversion    Device system version(like 5.4.4、7.0.4, should be used with os)
-   *                 sysmodel     Device model(like iOS:"MGA82J/A", android:"MI NOTE LTE")
-   *                 Time    UNIX timestamp, UTC+08:00
-   *                 TTID(Optional)
-   *                 MarkertId
-   *                 Appname(Optional)  tm,tb,qa
-   *                 Bundleurl(Optional)  template url
-   * @param jsonInitData Initial data for rendering
-   * @param flag     RenderStrategy {@link WXRenderStrategy}
-   */
-  @Deprecated
-  public void render(String template, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag) {
-    render(WXPerformance.DEFAULT, template, options, jsonInitData, flag);
-  }
-
-  /**
-   * Render template asynchronously
-   *
-   * @param pageName, used for performance log.
-   * @param template bundle js
-   * @param options  os   iphone/android/ipad
-   *                 weexversion    Weex version(like 1.0.0)
-   *                 appversion     App version(like 1.0.0)
-   *                 devid        Device id(like Aqh9z8dRJNBhmS9drLG5BKCmXhecHUXIZoXOctKwFebH)
-   *                 sysversion    Device system version(like 5.4.4、7.0.4, should be used with os)
-   *                 sysmodel     Device model(like iOS:"MGA82J/A", android:"MI NOTE LTE")
-   *                 Time    UNIX timestamp, UTC+08:00
-   *                 TTID(Optional)
-   *                 MarkertId
-   *                 Appname(Optional)  tm,tb,qa
-   *                 Bundleurl(Optional)  template url
-   * @param jsonInitData Initial data for rendering
-   * @param flag     RenderStrategy {@link WXRenderStrategy}
-   */
-  public void render(String pageName, String template, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag) {
-    render(pageName, new Script(template), options, jsonInitData, flag);
-  }
-
-  public void render(String pageName, Script template, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag) {
-    mWXPerformance.beforeInstanceRender(mInstanceId);
-
-    if(WXEnvironment.isApkDebugable() && WXPerformance.DEFAULT.equals(pageName)){
-
-      if (getUIContext() != null) {
-        new AlertDialog.Builder(getUIContext())
-                .setTitle("Error: Missing pageName")
-                .setMessage("We highly recommend you to set pageName. Call" +
-                        "\nWXSDKInstance#render(String pageName, String template, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag)\n" +
-                        "to fix it.")
-                .show();
-      }
-
-      return;
-    }
-    renderInternal(pageName,template,options,jsonInitData,flag);
-  }
-
-  /**
-   * Render binary template asynchronously in DATA_RENDER_BINARY strategy.
-   */
-  public void render(String pageName, byte[] template, Map<String, Object> options, String jsonInitData) {
-    render(pageName, new Script(template), options, jsonInitData, WXRenderStrategy.DATA_RENDER_BINARY);
-  }
-
-  private void ensureRenderArchor(){
-    if(mRenderContainer == null){
-      if (getContext() != null) {
-        setRenderContainer(new RenderContainer(getContext()));
-        mRenderContainer.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT));
-        mRenderContainer.setBackgroundColor(Color.TRANSPARENT);
-        mRenderContainer.setSDKInstance(this);
-        mRenderContainer.addOnLayoutChangeListener(this);
-      }
-    }
-  }
-
-  private void renderInternal(String pageName,
-                              String template,
-                              Map<String, Object> options,
-                              String jsonInitData,
-                              WXRenderStrategy flag) {
-    if (mRendered || TextUtils.isEmpty(template)) {
-      return;
-    }
-    renderInternal(pageName, new Script(template), options, jsonInitData, flag);
-  }
-
-  private boolean isPreInit = false;
-  public boolean isPreInitMode(){
-    return isPreInit;
-  }
-
-  private boolean isPreDownLoad =false;
-  public boolean isPreDownLoad(){
-    return isPreDownLoad;
-  }
-
-  public void onInstanceReady(){
-    WXLogUtils.d("test->","onInstanceReady");
-    mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_CONTAINER_READY);
-    if (!isPreInit && !isPreDownLoad){
-      return;
-    }
-    mApmForInstance.onInstanceReady(isPreDownLoad);
-    if (isPreDownLoad){
-        mHttpListener.onInstanceReady();
-    }
-  }
-
-  public void preInit(String pageName,
-                      String script,
-                      Map<String, Object> options,
-                      String jsonInitData,
-                      WXRenderStrategy flag){
-    isPreInit = true;
-    mRenderStrategy = flag;
-    Map<String, Object> renderOptions = options;
-    if (renderOptions == null) {
-      renderOptions = new HashMap<>();
-    }
-    //mApmForInstance.doInit();
-    mApmForInstance.isReady = false;
-    WXSDKManager.getInstance().createInstance(this, new Script(script), renderOptions, jsonInitData);
-  }
-
-  public void preDownLoad(String url,
-                          Map<String, Object> options,
-                          String jsonInitData,
-                          WXRenderStrategy flag){
-    this.isPreDownLoad =true;
-    mRenderStrategy = flag;
-    mApmForInstance.isReady = false;
-    renderByUrl(url,url,options,jsonInitData,flag);
-  }
-
-
-  private void renderInternal(String pageName,
-                              Script template,
-                              Map<String, Object> options,
-                              String jsonInitData,
-                              WXRenderStrategy flag){
-    if (mRendered || template == null || template.isEmpty()) {
-      return;
-    }
-
-    LogDetail logDetail = mTimeCalculator.createLogDetail("renderInternal");
-    mRenderStrategy = flag;
-
-    //some case ,from render(template),but not render (url)
-    if (!mApmForInstance.hasInit()){
-      mApmForInstance.doInit();
-    }
-    mApmForInstance.setPageName(pageName);
-    mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_RENDER_ORGIGIN);
-    mApmForInstance.doDelayCollectData();
-
-    mWXPerformance.pageName = (TextUtils.isEmpty(pageName) ? "defaultBundleUrl":pageName);
-    if (TextUtils.isEmpty(mBundleUrl)) {
-      mBundleUrl = mWXPerformance.pageName;
-    }
-
-    if (WXTracing.isAvailable()) {
-      WXTracing.TraceEvent traceEvent = WXTracing.newEvent("executeBundleJS", mInstanceId, -1);
-      traceEvent.traceId = mExecJSTraceId;
-      traceEvent.iid = mInstanceId;
-      traceEvent.tname = "JSThread";
-      traceEvent.ph = "B";
-      traceEvent.submit();
-      mRenderStartNanos = System.nanoTime();
-    }
-
-    ensureRenderArchor();
-
-    Map<String, Object> renderOptions = options;
-    if (renderOptions == null) {
-      renderOptions = new HashMap<>();
-    }
-
-    if (WXEnvironment.sDynamicMode && !TextUtils.isEmpty(WXEnvironment.sDynamicUrl) && renderOptions.get("dynamicMode") == null) {
-      renderOptions.put("dynamicMode", "true");
-      renderByUrl(pageName, WXEnvironment.sDynamicUrl, renderOptions, jsonInitData, flag);
-      return;
-    }
-
-    TimeCalculator timeCalculator = new TimeCalculator(this);
-
-    mWXPerformance.JSTemplateSize = template.length() / 1024f;
-    mApmForInstance.addStats(WXInstanceApm.KEY_PAGE_STATS_BUNDLE_SIZE,mWXPerformance.JSTemplateSize);
-    mRenderStartTime = System.currentTimeMillis();
-    WXSDKManager.getInstance().setCrashInfo(WXEnvironment.WEEX_CURRENT_KEY,pageName);
-    if(mAutoAdjustDeviceWidth && WXDeviceUtils.isAutoResize(mContext)){
-         if(WXEnvironment.AUTO_UPDATE_APPLICATION_SCREEN_SIZE) {
-             WXViewUtils.updateApplicationScreen(mContext);
-         }
-         WXParams params = WXBridgeManager.getInstance().getInitParams();
-         if(params != null && !TextUtils.equals(params.getDeviceWidth(), String.valueOf(WXViewUtils.getScreenWidth(mContext)))){
-           params.setDeviceWidth(String.valueOf(WXViewUtils.getScreenWidth(mContext)));
-           params.setDeviceHeight(String.valueOf(WXViewUtils.getScreenHeight(mContext)));
-           float density = WXEnvironment.sApplication.getResources().getDisplayMetrics().density;
-           WXEnvironment.addCustomOptions(WXConfig.scale, Float.toString(density));
-           String statusBarHeight =  null;
-           if(WXViewUtils.getStatusBarHeight(mContext) > 0 ){
-             statusBarHeight = String.valueOf(WXViewUtils.getStatusBarHeight(mContext));
-           }
-           WXBridgeManager.getInstance().updateInitDeviceParams(params.getDeviceWidth(),
-                                                                params.getDeviceHeight(),
-                                                                Float.toString(density), statusBarHeight);
-           setDeviceDisplay(WXViewUtils.getScreenWidth(mContext),
-                            WXViewUtils.getScreenHeight(mContext),
-                            WXViewUtils.getScreenDensity(mContext));
-         }
-    }
-    logDetail.taskStart();
-    if (isPreInitMode()){
-      getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_START);
-      WXBridgeManager.getInstance().loadJsBundleInPreInitMode(getInstanceId(),template.getContent());
-    } else {
-      WXSDKManager.getInstance().createInstance(this, template, renderOptions, jsonInitData);
-    }
-    logDetail.taskEnd();
-    mRendered = true;
-
-    final IWXJscProcessManager wxJscProcessManager = WXSDKManager.getInstance().getWXJscProcessManager();
-
-    if(wxJscProcessManager != null && wxJscProcessManager.shouldReboot()) {
-      WXSDKManager.getInstance().postOnUiThread(new Runnable() {
-        @Override
-        public void run() {
-          checkWhiteScreen();
-          if(isDestroy || hasException || isRenderSuccess) {
-            return;
-          }
-
-          // there is no need to reboot js engine if render by eagle
-          if(isDataRender()) {
-            return;
-          }
-
-          View containerView = getContainerView();
-          if(containerView instanceof ViewGroup) {
-            if(0 == ((ViewGroup) containerView).getChildCount()) {
-              if(wxJscProcessManager.withException(WXSDKInstance.this)) {
-                onJSException(String.valueOf(WX_ERR_RELOAD_PAGE),"jsc reboot","jsc reboot");
-              }
-              if(!createInstanceHeartBeat) {
-                  WXBridgeManager.getInstance().callReportCrashReloadPage(mInstanceId, null);
-                  WXLogUtils.e("callReportCrashReloadPage with jsc reboot");
-              }
-            }
-          }
-        }
-      }, wxJscProcessManager.rebootTimeout());
-    }
-  }
-
-
-  private void checkWhiteScreen(){
-    if (isDestroy ||!WhiteScreenUtils.doWhiteScreenCheck()){
-      return;
-    }
-
-    boolean isWS = WhiteScreenUtils.isWhiteScreen(this);
-    if (!isWS){
-      return;
-    }
-    WXErrorCode errorCode = createInstanceHeartBeat?WXErrorCode.WX_ERROR_WHITE_SCREEN:WXErrorCode.WHITE_SCREEN_RESPONSE_TIMEOUT;
-    if (WXBridgeManager.getInstance().isRebootExceedLimit()){
-      errorCode = WXErrorCode.WHITE_SCREEN_REBOOT_EXCEED_LIMIT;
-    }
-    Map<String,String> args = new HashMap<>(1);
-    String vieTreeMsg = WhiteScreenUtils.takeViewTreeSnapShot(this);
-    args.put("viewTree",null == vieTreeMsg?"null viewTreeMsg":vieTreeMsg);
-    args.put("weexCoreThreadStackTrace",WXBridgeManager.getInstance().getWeexCoreThreadStackTrace());
-
-    for (Map.Entry<String,String> entry: WXStateRecord.getInstance().getStateInfo().entrySet()){
-      args.put(entry.getKey(),entry.getValue());
-    }
-    WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),errorCode,"checkEmptyScreen",errorCode.getErrorMsg(),args);
-  }
-
-
-  public boolean skipFrameworkInit(){
-    return isDataRender() && !mDisableSkipFrameworkInit;
-  }
-
-  private boolean isDataRender() {
-    return getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY || getRenderStrategy() == WXRenderStrategy.DATA_RENDER;
-  }
-
-  private void renderByUrlInternal(String pageName,
-                                   final String url,
-                                   Map<String, Object> options,
-                                   final String jsonInitData,
-                                   WXRenderStrategy flag) {
-
-
-    LogDetail logDetail = mTimeCalculator.createLogDetail("renderByUrlInternal");
-    logDetail.taskStart();
-    ensureRenderArchor();
-    pageName = wrapPageName(pageName, url);
-    mBundleUrl = url;
-    mRenderStrategy = flag;
-    if(WXSDKManager.getInstance().getValidateProcessor()!=null) {
-      mNeedValidate = WXSDKManager.getInstance().getValidateProcessor().needValidate(mBundleUrl);
-    }
-
-    Map<String, Object> renderOptions = options;
-    if (renderOptions == null) {
-      renderOptions = new HashMap<>();
-    }
-    if (!renderOptions.containsKey(BUNDLE_URL)) {
-      renderOptions.put(BUNDLE_URL, url);
-    }
-
-    getWXPerformance().pageName = pageName;
-
-    mApmForInstance.doInit();
-    mApmForInstance.setPageName(pageName);
-
-    Uri uri = Uri.parse(url);
-    if (uri != null && TextUtils.equals(uri.getScheme(), "file")) {
-      mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_START);
-      String template = WXFileUtils.loadFileOrAsset(assembleFilePath(uri), mContext);
-      mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_END);
-      render(pageName,template , renderOptions, jsonInitData, flag);
-      return;
-    }
-
-    boolean is_wlasm = false;
-    if (uri != null && uri.getPath()!=null) {
-      if(uri.getPath().endsWith(".wlasm")){
-        is_wlasm =  true;
-      }
-    }
-    if (is_wlasm){
-      flag = WXRenderStrategy.DATA_RENDER_BINARY;
-    }
-
-    IWXHttpAdapter adapter = WXSDKManager.getInstance().getIWXHttpAdapter();
-
-    WXRequest wxRequest = new WXRequest();
-    wxRequest.url = rewriteUri(Uri.parse(url),URIAdapter.BUNDLE).toString();
-    if(wxRequest != null && !TextUtils.isEmpty(wxRequest.url)){
-      requestUrl = wxRequest.url;
-    }else {
-      requestUrl = pageName;
-    }
-
-    if (wxRequest.paramMap == null) {
-      wxRequest.paramMap = new HashMap<String, String>();
-    }
-    wxRequest.instanceId = getInstanceId();
-    wxRequest.paramMap.put(KEY_USER_AGENT, WXHttpUtil.assembleUserAgent(mContext,WXEnvironment.getConfig()));
-    wxRequest.paramMap.put("isBundleRequest","true");
-    mHttpListener = new WXHttpListener(this, pageName, renderOptions, jsonInitData, flag, System.currentTimeMillis());
-    mHttpListener.isPreDownLoadMode = isPreDownLoad;
-    mHttpListener.setSDKInstance(this);
-    mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_START);
-    adapter.sendRequest(wxRequest, (IWXHttpAdapter.OnHttpListener) mHttpListener);
-    logDetail.taskEnd();
-  }
-
-  private WXHttpListener mHttpListener = null;
-
-  /**
-   * Use {@link #render(String, String, Map, String, WXRenderStrategy)} instead.
-   * @param pageName
-   * @param template
-   * @param options
-   * @param jsonInitData
-   * @param width
-   * @param height
-   * @param flag
-   */
-  @Deprecated
-  public void render(String pageName, String template, Map<String, Object> options, String jsonInitData, int width, int height, WXRenderStrategy flag) {
-    render(pageName,template,options,jsonInitData,flag);
-  }
-
-  /**
-   * Render template asynchronously, use {@link WXRenderStrategy#APPEND_ASYNC} as render strategy
-   * @param template bundle js
-   */
-  public void render(String template) {
-    render(WXPerformance.DEFAULT, template, null, null, mRenderStrategy);
-  }
-
-  /**
-   * Use {@link #render(String)} instead.
-   * @param template
-   * @param width
-   * @param height
-   */
-  @Deprecated
-  public void render(String template, int width, int height) {
-    render(template);
-  }
-
-  /**
-   * Use {@link #renderByUrl(String, String, Map, String, WXRenderStrategy)} instead.
-   * @param pageName
-   * @param url
-   * @param options
-   * @param jsonInitData
-   * @param width
-   * @param height
-   * @param flag
-   */
-  @Deprecated
-  public void renderByUrl(String pageName, final String url, Map<String, Object> options, final String jsonInitData, final int width, final int height, final WXRenderStrategy flag){
-    renderByUrl(pageName,url,options,jsonInitData,flag);
-  }
-
-  public void renderByUrl(String pageName, final String url, Map<String, Object> options, final String jsonInitData, final WXRenderStrategy flag) {
-    renderByUrlInternal(pageName,url,options,jsonInitData,flag);
-  }
-
-  private String wrapPageName(String pageName, String url) {
-    if(TextUtils.equals(pageName, WXPerformance.DEFAULT)){
-      pageName = url;
-      WXExceptionUtils.degradeUrl = pageName;
-      try {
-        Uri uri=Uri.parse(url);
-        if(uri!=null){
-          Uri.Builder builder=new Uri.Builder();
-          builder.scheme(uri.getScheme());
-          builder.authority(uri.getAuthority());
-          builder.path(uri.getPath());
-          pageName=builder.toString();
-        }
-      } catch (Exception e) {
-      }
-    }
-    return pageName;
-  }
-
-  private String assembleFilePath(Uri uri) {
-    if(uri!=null && uri.getPath()!=null){
-      return uri.getPath().replaceFirst("/","");
-    }
-    return "";
-  }
-
-  public void reloadPage(boolean reloadThis) {
-
-    WXSDKEngine.reload();
-
-    if (reloadThis) {
-      if (mContext != null)  {
-        Intent intent = new Intent();
-        intent.setAction(ACTION_INSTANCE_RELOAD);
-        intent.putExtra("url", mBundleUrl);
-        mContext.sendBroadcast(intent);
-      }
-      // mRendered = false;
-      //    destroy();
-      // renderInternal(mPackage, mTemplate, mOptions, mJsonInitData, mFlag);
-      // refreshInstance("{}");
-    } else {
-      IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
-      if (adapter != null) {
-        boolean degrade = Boolean.parseBoolean(adapter
-                .getConfig("android_weex_ext_config",
-                        "degrade_to_h5_if_not_reload",
-                        "true"));
-        WXLogUtils.e("degrade : " + degrade);
-        if(degrade) {
-          onJSException(String.valueOf(WX_ERR_RELOAD_PAGE.getErrorCode()),"Do not reloadPage", "Do not reloadPage degradeToH5");
-          WXLogUtils.e("Do not reloadPage degradeToH5");
-        }
-      }
-    }
-  }
-
-  /**
-   * Refresh instance asynchronously.
-   * @param data the new data
-   */
-  public void refreshInstance(Map<String, Object> data) {
-    if (data == null) {
-      return;
-    }
-    refreshInstance(WXJsonUtils.fromObjectToJSONString(data));
-  }
-
-  /**
-   * Refresh instance asynchronously.
-   * @param jsonData the new data
-   */
-  public void refreshInstance(String jsonData) {
-    if (jsonData == null) {
-      return;
-    }
-    mRefreshStartTime = System.currentTimeMillis();
-    //cancel last refresh message
-    if (mLastRefreshData != null) {
-      mLastRefreshData.isDirty = true;
-    }
-
-    mLastRefreshData = new WXRefreshData(jsonData, false);
-
-    WXSDKManager.getInstance().refreshInstance(mInstanceId, mLastRefreshData);
-  }
-
-  public WXRenderStrategy getRenderStrategy() {
-    return mRenderStrategy;
-  }
-
-  public Context getUIContext() {
-    return mContext;
-  }
-
-  public String getInstanceId() {
-    return mInstanceId;
-  }
-
-  public Context getContext() {
-    return mContext;
-  }
-
-  public int getWeexHeight() {
-    return mRenderContainer == null ? 0: mRenderContainer.getHeight();
-  }
-
-  public int getWeexWidth() {
-    return mRenderContainer == null ? 0: mRenderContainer.getWidth();
-  }
-
-
-  public IWXImgLoaderAdapter getImgLoaderAdapter() {
-    return WXSDKManager.getInstance().getIWXImgLoaderAdapter();
-  }
-
-  public IDrawableLoader getDrawableLoader() {
-    return WXSDKManager.getInstance().getDrawableLoader();
-  }
-
-  public URIAdapter getURIAdapter(){
-    return WXSDKManager.getInstance().getURIAdapter();
-  }
-
-  public Uri rewriteUri(Uri uri,String type){
-    return getURIAdapter().rewrite(this,type,uri);
-  }
-
-  public IWXHttpAdapter getWXHttpAdapter() {
-    return WXSDKManager.getInstance().getIWXHttpAdapter();
-  }
-
-  public IWXStatisticsListener getWXStatisticsListener() {
-    return mStatisticsListener;
-  }
-
-  public @Nullable
-  IWebSocketAdapter getWXWebSocketAdapter() {
-    return WXSDKManager.getInstance().getIWXWebSocketAdapter();
-  }
-
-  @Deprecated
-  public void reloadImages() {
-    if (mScrollView == null) {
-      return;
-    }
-  }
-
-
-  public boolean isPreRenderMode() {
-    return this.isPreRenderMode;
-  }
-
-  public void setPreRenderMode(final boolean isPreRenderMode) {
-    WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(new Runnable() {
-      @Override
-      public void run() {
-        WXSDKInstance.this.isPreRenderMode = isPreRenderMode;
-      }
-    },0);
-  }
-
-  public void setContext(@NonNull Context context) {
-    this.mContext = context;
-  }
-
-  /********************************
-   * begin register listener
-   ********************************************************/
-  public void registerRenderListener(IWXRenderListener listener) {
-    mRenderListener = listener;
-  }
-
-  @Deprecated
-  public void registerActivityStateListener(IWXActivityStateListener listener) {
-
-  }
-
-  public void registerStatisticsListener(IWXStatisticsListener listener) {
-    mStatisticsListener = listener;
-  }
-
-  /**set render start time*/
-  public void setRenderStartTime(long renderStartTime) {
-    this.mRenderStartTime = renderStartTime;
-  }
-
-  /********************************
-   * end register listener
-   ********************************************************/
-
-
-  /********************************
-   *  begin hook Activity life cycle callback
-   ********************************************************/
-
-  @Override
-  public void onActivityCreate() {
-
-    // module listen Activity onActivityCreate
-    WXModuleManager.onActivityCreate(getInstanceId());
-
-    if(mRootComp != null) {
-      mRootComp.onActivityCreate();
-    }else{
-        if (WXEnvironment.isApkDebugable()){
-            WXLogUtils.w("Warning :Component tree has not build completely,onActivityCreate can not be call!");
-        }
-    }
-
-    mGlobalEventReceiver=new WXGlobalEventReceiver(this);
-    try {
-      getContext().registerReceiver(mGlobalEventReceiver, new IntentFilter(WXGlobalEventReceiver.EVENT_ACTION));
-    } catch (Throwable e) {
-      // Huawei may throw a exception if register more than 500 BroadcastReceivers
-      WXLogUtils.e(e.getMessage());
-      mGlobalEventReceiver = null;
-    }
-
-  }
-
-  @Override
-  public void onActivityStart() {
-
-    // module listen Activity onActivityCreate
-    WXModuleManager.onActivityStart(getInstanceId());
-    if(mRootComp != null) {
-      mRootComp.onActivityStart();
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("Warning :Component tree has not build completely,onActivityStart can not be call!");
-
-        }
-    }
-
-  }
-
-  public boolean onCreateOptionsMenu(Menu menu) {
-
-    WXModuleManager.onCreateOptionsMenu(getInstanceId(),menu);
-    if(mRootComp != null) {
-      mRootComp.onCreateOptionsMenu(menu);
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("Warning :Component tree has not build completely,onActivityStart can not be call!");
-
-        }
-    }
-    return true;
-  }
-
-  @Override
-  public void onActivityPause() {
-    onViewDisappear();
-    if(!isCommit){
-      if(mUseScroller){
-        mWXPerformance.useScroller=1;
-      }
-      mWXPerformance.maxDeepViewLayer=getMaxDeepLayer();
-      mWXPerformance.wxDims = mwxDims;
-      mWXPerformance.measureTimes = measureTimes;
-      if (mUserTrackAdapter != null) {
-        mUserTrackAdapter.commit(mContext, null, IWXUserTrackAdapter.LOAD, mWXPerformance, getUserTrackParams());
-      }
-      isCommit=true;
-    }
-    // module listen Activity onActivityPause
-    WXModuleManager.onActivityPause(getInstanceId());
-    if(mRootComp != null) {
-      mRootComp.onActivityPause();
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("Warning :Component tree has not build completely,onActivityPause can not be call!");
-        }
-    }
-
-    if (!mCurrentGround) {
-      WXLogUtils.i("Application to be in the backround");
-      Intent intent = new Intent(WXGlobalEventReceiver.EVENT_ACTION);
-      intent.putExtra(WXGlobalEventReceiver.EVENT_NAME, Constants.Event.PAUSE_EVENT);
-      intent.putExtra(WXGlobalEventReceiver.EVENT_WX_INSTANCEID, getInstanceId());
-      /**
-       *  Fix NPE just like {@link #onActivityResume()}
-       */
-      if (null != mContext){
-        mContext.sendBroadcast(intent);
-      }else {
-        try {
-          WXEnvironment.getApplication().sendBroadcast(intent);
-        } catch (Exception e){
-          WXLogUtils.e("weex",e);
-        }
-      }
-      this.mCurrentGround = true;
-    }
-
-    //component appear
-    if((WXEnvironment.isApkDebugable() || WXEnvironment.isPerf()) && mApmForInstance != null){
-        WXLogUtils.e("PerformanceData " + mApmForInstance.toPerfString());
-    }
-  }
-
-
-  @Override
-  public void onActivityResume() {
-
-    // notify onActivityResume callback to module
-    WXModuleManager.onActivityResume(getInstanceId());
-
-    if(mRootComp != null) {
-      mRootComp.onActivityResume();
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("Warning :Component tree has not build completely, onActivityResume can not be call!");
-        }
-    }
-
-    if (mCurrentGround) {
-      WXLogUtils.i("Application  to be in the foreground");
-      Intent intent = new Intent(WXGlobalEventReceiver.EVENT_ACTION);
-      intent.putExtra(WXGlobalEventReceiver.EVENT_NAME, Constants.Event.RESUME_EVENT);
-      intent.putExtra(WXGlobalEventReceiver.EVENT_WX_INSTANCEID, getInstanceId());
-      //todo tmp solution for gray version
-      if (null != mContext){
-        mContext.sendBroadcast(intent);
-      }else {
-        WXEnvironment.getApplication().sendBroadcast(intent);
-      }
-      this.mCurrentGround = false;
-    }
-
-    onViewAppear();
-  }
-
-  @Override
-  public void onActivityStop() {
-
-    // notify onActivityResume callback to module
-    WXModuleManager.onActivityStop(getInstanceId());
-
-    if(mRootComp != null) {
-      mRootComp.onActivityStop();
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("Warning :Component tree has not build completely, onActivityStop can not be call!");
-        }
-    }
-
-  }
-
-  @Override
-  public void onActivityDestroy() {
-    WXModuleManager.onActivityDestroy(getInstanceId());
-
-    if(mRootComp != null) {
-      mRootComp.onActivityDestroy();
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("Warning :Component tree has not build completely, onActivityDestroy can not be call!");
-        }
-    }
-    this.mTimeCalculator.println();
-    destroy();
-  }
-
-  @Override
-  public boolean onActivityBack() {
-
-    WXModuleManager.onActivityBack(getInstanceId());
-
-    if(mRootComp != null) {
-      return mRootComp.onActivityBack();
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("Warning :Component tree has not build completely, onActivityBack can not be call!");
-        }
-    }
-
-    return false;
-  }
-
-  public boolean onSupportNavigateUp() {
-    if (mWXActionbarHandlers != null) {
-      for (ActionBarHandler handler : mWXActionbarHandlers) {
-        if (handler.onSupportNavigateUp()) {
-          return true;
-        }
-      }
-    }
-    return false;
-  }
-
-  public boolean onBackPressed() {
-    if(mWXBackPressedHandlers != null) {
-      for (OnBackPressedHandler handler : mWXBackPressedHandlers) {
-        if(handler.onBackPressed()) {
-          return true;
-        }
-      }
-    }
-
-    WXComponent comp = getRootComponent();
-    if(comp != null) {
-      WXEvent events= comp.getEvents();
-      boolean hasNativeBackHook = events.contains(Constants.Event.NATIVE_BACK);
-      if (hasNativeBackHook) {
-        EventResult result = comp.fireEventWait(Constants.Event.NATIVE_BACK, null);
-        if (WXUtils.getBoolean(result.getResult(), false)) {
-          return true;
-        }
-      }
-
-      boolean hasBackPressed = events.contains(Constants.Event.CLICKBACKITEM);
-      if (hasBackPressed) {
-        fireEvent(comp.getRef(), Constants.Event.CLICKBACKITEM,null, null);
-      }
-      return hasBackPressed;
-    }
-    return false;
-  }
-
-  public void onActivityResult(int requestCode, int resultCode, Intent data){
-    WXModuleManager.onActivityResult(getInstanceId(),requestCode,resultCode,data);
-
-    if(mRootComp != null) {
-      mRootComp.onActivityResult(requestCode,resultCode,data);
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("Warning :Component tree has not build completely, onActivityResult can not be call!");
-        }
-    }
-
-
-    if (mWXOnActivityResultHandlers != null && !mWXOnActivityResultHandlers.isEmpty()) {
-      for (OnActivityResultHandler onActivityResultHandler : mWXOnActivityResultHandlers) {
-        if (onActivityResultHandler.onActivityResult(requestCode, resultCode, data)) {
-          break;
-        }
-      }
-    }
-
-  }
-
-
-  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
-
-    WXModuleManager.onRequestPermissionsResult(getInstanceId(),requestCode,permissions,grantResults);
-
-    if(mRootComp != null) {
-       mRootComp.onRequestPermissionsResult(requestCode,permissions,grantResults);
-    }else{
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w(
-                "Warning :Component tree has not build completely, onRequestPermissionsResult can not be call!");
-        }
-    }
-  }
-
-  /********************************
-   *  end hook Activity life cycle callback
-   ********************************************************/
-
-  public void onViewDisappear(){
-    isViewDisAppear = false;
-    mApmForInstance.onDisAppear();
-    WXComponent comp = getRootComponent();
-    if(comp != null) {
-      fireEvent(comp.getRef(), Constants.Event.VIEWDISAPPEAR, null, null);
-      //call disappear of nested instances
-      for(OnInstanceVisibleListener instance:mVisibleListeners){
-        instance.onDisappear();
-      }
-    }
-  }
-
-  public boolean isViewDisAppear(){
-    return isViewDisAppear;
-  }
-
-  public void onViewAppear(){
-    isViewDisAppear = true;
-    mApmForInstance.onAppear();
-    WXComponent comp = getRootComponent();
-    if(comp != null) {
-      fireEvent( comp.getRef(), Constants.Event.VIEWAPPEAR,null, null);
-      for(OnInstanceVisibleListener instance:mVisibleListeners){
-        instance.onAppear();
-      }
-    }
-  }
-
-
-  public void onCreateFinish() {
-    if(mHasCreateFinish){
-      return;
-    }
-    if (mContext != null) {
-      onViewAppear();
-      View wxView= mRenderContainer;
-      if(mRenderListener != null) {
-        mRenderListener.onViewCreated(WXSDKInstance.this, wxView);
-      }
-      if (mStatisticsListener != null) {
-        mStatisticsListener.onFirstView();
-      }
-    }
-  }
-
-  /**
-   * call back when update finish
-   */
-  public void onUpdateFinish() {
-    if (WXEnvironment.isApkDebugable()){
-      WXLogUtils.d("Instance onUpdateSuccess");
-    }
-  }
-
-
-  public void runOnUiThread(Runnable action) {
-    WXSDKManager.getInstance().postOnUiThread(action, 0);
-  }
-
-  public void onRenderSuccess(final int width, final int height) {
-    isRenderSuccess = true;
-    if (!isNewFsEnd){
-      getApmForInstance().arriveNewFsRenderTime();
-    }
-
-    long time = System.currentTimeMillis() - mRenderStartTime;
-    long[] renderFinishTime = WXBridgeManager.getInstance().getRenderFinishTime(getInstanceId());
-
-    mWXPerformance.callBridgeTime = renderFinishTime[0];
-    mWXPerformance.cssLayoutTime = renderFinishTime[1];
-    mWXPerformance.parseJsonTime = renderFinishTime[2];
-
-    mWXPerformance.totalTime = time;
-    if(mWXPerformance.screenRenderTime<0.001){
-      mWXPerformance.screenRenderTime =  time;
-    }
-
-    if (mRenderListener != null && mContext != null) {
-      mRenderListener.onRenderSuccess(WXSDKInstance.this, width, height);
-      if (mUserTrackAdapter != null) {
-        WXPerformance performance=new WXPerformance(mInstanceId);
-        performance.errCode=WXErrorCode.WX_SUCCESS.getErrorCode();
-        performance.args=getBundleUrl();
-        mUserTrackAdapter.commit(mContext,null,IWXUserTrackAdapter.JS_BRIDGE,performance,getUserTrackParams());
-      }
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d(WXLogUtils.WEEX_PERF_TAG, mWXPerformance.toString());
-      }
-    }
-    if(WXEnvironment.isPerf()){
-      WXLogUtils.e("weex_perf",mWXPerformance.getPerfData());
-    }
-  }
-
-  public void onRefreshSuccess(final int width, final int height) {
-    if (mRenderListener != null && mContext != null) {
-      mRenderListener.onRefreshSuccess(WXSDKInstance.this, width, height);
-    }
-  }
-
-  public void onChangeElement(WXComponent component, boolean isOutOfScreen) {
-
-    if (isDestroy()  || null == mRenderContainer || mWXPerformance == null ){
-      return;
-    }
-    if (null == component || component.isIgnoreInteraction){
-        return;
-    }
-
-    if (mRenderContainer.hasConsumeEvent()) {
-      return;
-    }
-
-    long lastElementChangeTime = System.currentTimeMillis();
-
-    long lazyLoadTime;
-
-    if (mHasCreateFinish){
-      lazyLoadTime = lastElementChangeTime - mWXPerformance.renderTimeOrigin;
-      if (lazyLoadTime > 8000) {
-        //force record detail performance data
-        return;
-      }
-    }
-
-    if (component.mIsAddElementToTree) {
-      getWXPerformance().localInteractionViewAddCount++;
-      if (!isOutOfScreen)
-        getWXPerformance().interactionViewAddLimitCount++;
-      component.mIsAddElementToTree = false;
-    }
-
-    if (!isOutOfScreen) {
-      mApmForInstance.arriveInteraction(component);
-    }
-  }
-
-  public void onRenderError(final String errCode, final String msg) {
-    WXStateRecord.getInstance().recordException(getInstanceId(),"onRenderError,"+errCode+","+msg);
-    if (mRenderListener != null && mContext != null) {
-      WXLogUtils.e("onRenderError "+errCode +","+msg);
-      runOnUiThread(new Runnable() {
-
-        @Override
-        public void run() {
-          if (mRenderListener != null && mContext != null) {
-            mRenderListener.onException(WXSDKInstance.this, errCode, msg);
-          }
-        }
-      });
-    }
-  }
-
-  public void onJSException(final String errCode, final String function, final String exception) {
-    WXStateRecord.getInstance().recordException(getInstanceId(),"onJSException,"+errCode+","+function+"|"+exception);
-    hasException = true;
-    if (mRenderListener != null && mContext != null) {
-      WXLogUtils.e("onJSException "+errCode +","+exception);
-      runOnUiThread(new Runnable() {
-
-        @Override
-        public void run() {
-          if (mRenderListener != null && mContext != null) {
-            StringBuilder builder = new StringBuilder();
-            builder.append(function);
-            builder.append(exception);
-            mRenderListener.onException(WXSDKInstance.this, errCode, builder.toString());
-          }
-        }
-      });
-    }
-  }
-
-
-  @Override
-  public final void onLayoutChange(View v, int left, int top, int right, int bottom, int oldLeft, int
-          oldTop, int oldRight, int oldBottom) {
-    if (left != oldLeft || top != oldTop || right != oldRight || bottom != oldBottom) {
-      onLayoutChange(v);
-    }
-  }
-
-  /**
-   * Subclass should override this method to get notifications of layout change of GodView.
-   * @param godView the godView.
-   */
-  public void onLayoutChange(View godView) {
-
-  }
-
-  private boolean mCreateInstance =true;
-  public void firstScreenCreateInstanceTime(long time) {
-    if(mCreateInstance) {
-      mWXPerformance.firstScreenJSFExecuteTime = time -mRenderStartTime;
-      mCreateInstance =false;
-    }
-  }
-
-  public void callJsTime(final long time){
-    if (!mEnd){
-      mWXPerformance.fsCallJsTotalTime+=time;
-      mWXPerformance.fsCallJsTotalNum++;
-    }
-  }
-
-  public void onComponentCreate(WXComponent component,long createTime) {
-      mWXPerformance.mActionAddElementCount++;
-      mWXPerformance.mActionAddElementSumTime += createTime;
-      if (!mEnd){
-        mWXPerformance.fsComponentCreateTime+=createTime;
-        mWXPerformance.fsComponentCount++;
-      }
-      mWXPerformance.componentCount++;
-      mWXPerformance.componentCreateTime+=createTime;
-  }
-
-  public void callActionAddElementTime(long time) {
-      mWXPerformance.mActionAddElementSumTime += time;
-  }
-
-  public void onOldFsRenderTimeLogic(){
-      if (mEnd){
-        return;
-      }
-      mEnd = true;
-      if (mStatisticsListener != null && mContext != null) {
-        runOnUiThread(new Runnable() {
-        @Override
-        public void run() {
-            if (mStatisticsListener != null && mContext != null) {
-              Trace.beginSection("onFirstScreen");
-              mStatisticsListener.onFirstScreen();
-              Trace.endSection();
-            }
-          }
-        });
-      }
-      mApmForInstance.arriveFSRenderTime();
-      mWXPerformance.fsRenderTime = System.currentTimeMillis();
-      mWXPerformance.screenRenderTime = System.currentTimeMillis() - mRenderStartTime;
-  }
-
-  public WXSDKInstance getParentInstance() {
-    return mParentInstance;
-  }
-
-  public void setParentInstance(WXSDKInstance mParentInstance) {
-    this.mParentInstance = mParentInstance;
-  }
-
-  private void destroyView(View rootView) {
-    try {
-      if (rootView instanceof ViewGroup) {
-        ViewGroup cViewGroup = ((ViewGroup) rootView);
-        for (int index = 0; index < cViewGroup.getChildCount(); index++) {
-          destroyView(cViewGroup.getChildAt(index));
-        }
-
-        cViewGroup.removeViews(0, ((ViewGroup) rootView).getChildCount());
-        // Ensure that the viewgroup's status to be normal
-        WXReflectionUtils.setValue(rootView, "mChildrenCount", 0);
-
-      }
-      if(rootView instanceof Destroyable){
-        ((Destroyable)rootView).destroy();
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("WXSDKInstance destroyView Exception: ", e);
-    }
-  }
-
-  public synchronized void destroy() {
-    if(!isDestroy()) {
-      if(mParentInstance != null){
-         mParentInstance = null;
-      }
-      mApmForInstance.onEnd();
-
-
-      if(mRendered) {
-        WXSDKManager.getInstance().destroyInstance(mInstanceId);
-      }
-
-      try {
-        if (mGlobalEventReceiver != null) {
-          getContext().unregisterReceiver(mGlobalEventReceiver);
-          mGlobalEventReceiver = null;
-        }
-      }catch (IllegalArgumentException e){
-        WXLogUtils.w(WXLogUtils.getStackTrace(e));
-      }
-
-      if (mRootComp != null) {
-        mRootComp.destroy();
-        mRootComp = null;
-      }
-
-      if(mRenderContainer != null){
-        destroyView(mRenderContainer);
-      }
-
-
-      if (mGlobalEvents != null) {
-        mGlobalEvents.clear();
-      }
-
-      if (mComponentObserver != null) {
-        mComponentObserver = null;
-      }
-
-      if (mLayerOverFlowListeners != null) {
-        mLayerOverFlowListeners.clear();
-      }
-
-      if(mWXOnActivityResultHandlers != null && !mWXOnActivityResultHandlers.isEmpty()) {
-        mWXOnActivityResultHandlers.clear();
-      }
-
-      if(mWXBackPressedHandlers != null && !mWXBackPressedHandlers.isEmpty()) {
-        mWXBackPressedHandlers.clear();
-      }
-
-      if(mWXActionbarHandlers != null && !mWXActionbarHandlers.isEmpty()) {
-        mWXActionbarHandlers.clear();
-      }
-
-      getFlatUIContext().destroy();
-      mFlatGUIContext = null;
-      mInstanceOnFireEventInterceptorList = null;
-      mWXScrollListeners = null;
-      mWXActionbarHandlers = null;
-      mWXBackPressedHandlers = null;
-      mRenderContainer = null;
-      mNestedInstanceInterceptor = null;
-      mUserTrackAdapter = null;
-      mScrollView = null;
-      mContext = null;
-      mRenderListener = null;
-      isDestroy = true;
-      mStatisticsListener = null;
-      if(responseHeaders != null){
-        responseHeaders.clear();
-      }
-      if(templateRef != null){
-        templateRef = null;
-      }
-      if (null != mContentBoxMeasurements) {
-        mContentBoxMeasurements.clear();
-      }
-      mWXPerformance.afterInstanceDestroy(mInstanceId);
-
-      WXBridgeManager.getInstance().post(new Runnable() {
-        @Override
-        public void run() {
-          WXBridgeManager.getInstance().onInstanceClose(getInstanceId());
-          inactiveAddElementAction.clear();
-        }
-      });
-
-      //when report error in @WXExceptionUtils
-      // instance may had destroy and remove,
-      // so we delay remove from allInstanceMap
-      WXBridgeManager.getInstance().postDelay(new Runnable() {
-        @Override
-        public void run() {
-          WXSDKManager.getInstance().getAllInstanceMap().remove(mInstanceId);
-        }
-      },1000);
-    }
-  }
-
-  public boolean isDestroy(){
-    return isDestroy;
-  }
-
-  /**
-   * @return If you use render () the return value may be empty
-   */
-  public @Nullable String getBundleUrl() {
-    return mBundleUrl;
-  }
-
-  public View getRootView() {
-    if (mRootComp == null)
-      return null;
-    return mRootComp.getRealView();
-  }
-
-  public View getContainerView() {
-    return mRenderContainer;
-  }
-
-  @Deprecated
-  public void setBundleUrl(String url){
-    mBundleUrl = url;
-    if(WXSDKManager.getInstance().getValidateProcessor()!=null) {
-      mNeedValidate = WXSDKManager.getInstance().getValidateProcessor().needValidate(mBundleUrl);
-    }
-  }
-
-  public void onRootCreated(WXComponent root) {
-    this.mRootComp = root;
-    this.mRootComp.mDeepInComponentTree =1;
-    mRenderContainer.addView(root.getHostView());
-
-
-    setSize(mRenderContainer.getWidth(),mRenderContainer.getHeight());
-  }
-
-  /**
-   * Move fixed view to container ,except it's already moved.
-   * @param fixedChild
-   */
-  public void moveFixedView(View fixedChild){
-    if(mRenderContainer != null) {
-      ViewGroup parent;
-      if((parent = (ViewGroup) fixedChild.getParent()) != null){
-        if (parent != mRenderContainer) {
-          parent.removeView(fixedChild);
-          mRenderContainer.addView(fixedChild);
-        }
-      }else{
-        mRenderContainer.addView(fixedChild);
-      }
-    }
-  }
-
-  public void removeFixedView(View fixedChild){
-    if(mRenderContainer != null) {
-      mRenderContainer.removeView(fixedChild);
-    }
-  }
-
-  public int getRenderContainerPaddingLeft() {
-    if(mRenderContainer != null) {
-      return mRenderContainer.getPaddingLeft();
-    }
-    return 0;
-  }
-
-  public int getRenderContainerPaddingRight() {
-    if(mRenderContainer != null) {
-      return mRenderContainer.getPaddingRight();
-    }
-    return 0;
-  }
-
-  public int getRenderContainerPaddingTop() {
-    if(mRenderContainer != null) {
-      return mRenderContainer.getPaddingTop();
-    }
-    return 0;
-  }
-
-  public synchronized List<OnWXScrollListener> getWXScrollListeners() {
-    return mWXScrollListeners;
-  }
-
-  public synchronized void registerOnWXScrollListener(OnWXScrollListener wxScrollListener) {
-    if(mWXScrollListeners==null){
-      mWXScrollListeners=new ArrayList<>();
-    }
-    mWXScrollListeners.add(wxScrollListener);
-  }
-
-  public synchronized void registerActionbarHandler(ActionBarHandler actionBarHandler) {
-    if(actionBarHandler == null) {
-      return;
-    }
-    if(mWXActionbarHandlers == null) {
-      mWXActionbarHandlers = new ArrayList<>();
-    }
-
-    mWXActionbarHandlers.add(actionBarHandler);
-  }
-
-  public synchronized void unRegisterActionbarHandler(ActionBarHandler actionBarHandler) {
-    if(mWXActionbarHandlers != null && actionBarHandler != null) {
-      mWXActionbarHandlers.remove(actionBarHandler);
-    }
-  }
-
-  public synchronized void unRegisterOnActivityResultHandler(OnActivityResultHandler onActivityResultHandler) {
-    if(mWXOnActivityResultHandlers != null && onActivityResultHandler != null) {
-      mWXOnActivityResultHandlers.remove(onActivityResultHandler);
-    }
-  }
-
-  public synchronized void registerOnActivityResultHandler(OnActivityResultHandler onActivityResultHandler) {
-    if(onActivityResultHandler == null) {
-      return;
-    }
-
-    if(mWXOnActivityResultHandlers == null) {
-      mWXOnActivityResultHandlers = new ArrayList<>();
-    }
-    mWXOnActivityResultHandlers.add(onActivityResultHandler);
-  }
-
-
-  public synchronized void registerBackPressedHandler(OnBackPressedHandler backPressedHandler) {
-    if(backPressedHandler == null) {
-      return;
-    }
-
-    if(mWXBackPressedHandlers == null) {
-      mWXBackPressedHandlers = new ArrayList<>();
-    }
-
-    mWXBackPressedHandlers.add(backPressedHandler);
-  }
-
-  public synchronized void unRegisterBackPressedHandler(OnBackPressedHandler backPressedHandler) {
-    if(mWXBackPressedHandlers != null && backPressedHandler != null) {
-      mWXBackPressedHandlers.remove(backPressedHandler);
-    }
-  }
-
-  static int sScreenHeight = -1;
-  public void setSize(int width, int height) {
-    if (width > 0 && height > 0 & !isDestroy && mRendered && mRenderContainer != null) {
-        if (sScreenHeight < 0){
-            sScreenHeight = WXViewUtils.getScreenHeight(getContext());
-        }
-        if (sScreenHeight>0){
-            double screenRatio = (double)height/(double)sScreenHeight *100;
-            if(screenRatio>100){
-              screenRatio =100;
-            }
-            getApmForInstance().addStats(WXInstanceApm.KEY_PAGE_STATS_BODY_RATIO,screenRatio);
-        }
-      ViewGroup.LayoutParams layoutParams = mRenderContainer.getLayoutParams();
-      if (layoutParams != null) {
-        final float realWidth = width;
-        final float realHeight = height;
-        if (mRenderContainer.getWidth() != width || mRenderContainer.getHeight() != height) {
-          layoutParams.width = width;
-          layoutParams.height = height;
-          mRenderContainer.setLayoutParams(layoutParams);
-        }
-
-        if (mRootComp != null && layoutParams != null) {
-          final boolean isWidthWrapContent = layoutParams.width == ViewGroup.LayoutParams.WRAP_CONTENT;
-          final boolean isHeightWrapContent = layoutParams.height == ViewGroup.LayoutParams.WRAP_CONTENT;
-
-          WXBridgeManager.getInstance().post(new Runnable() {
-            @Override
-            public void run() {
-              WXBridgeManager.getInstance().setDefaultRootSize(getInstanceId(), realWidth, realHeight, isWidthWrapContent,
-                      isHeightWrapContent);
-            }
-          });
-        }
-      }
-    }
-  }
-
-  /*Global Event*/
-  private HashMap<String, List<String>> mGlobalEvents = new HashMap<>();
-
-  public void fireGlobalEventCallback(String eventName, Map<String,Object> params){
-    List<String> callbacks=mGlobalEvents.get(eventName);
-    if(callbacks!=null){
-      for(String callback:callbacks){
-        WXSDKManager.getInstance().callback(mInstanceId,callback,params,true);
-      }
-    }
-  }
-
-  /**
-   * Fire event callback on a element.
-   * @param elementRef
-   * @param type
-   * @param data
-   * @param domChanges
-   */
-  public void fireEvent(String elementRef,final String type, final Map<String, Object> data,final Map<String, Object> domChanges, List<Object> eventArgs){
-    fireEvent(elementRef, type, data, domChanges, eventArgs, null);
-  }
-
-  public void fireEvent(String elementRef,final String type, final Map<String, Object> data,final Map<String, Object> domChanges, List<Object> eventArgs, EventResult callback) {
-    onInterceptInstanceEvent(getInstanceId(), elementRef, type, data, domChanges);
-    if (null != mWXPerformance && mWXPerformance.fsCallEventTotalNum<Integer.MAX_VALUE){
-      mWXPerformance.fsCallEventTotalNum++;
-    }
-    mApmForInstance.updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_CALL_EVENT_NUM,1);
-    WXBridgeManager.getInstance().fireEventOnNode(getInstanceId(),elementRef,type,data,domChanges, eventArgs, callback);
-  }
-
-
-  /**
-   * Fire event callback on a element.
-   * @param elementRef
-   * @param type
-   * @param data
-   * @param domChanges
-   */
-  public void fireEvent(String elementRef,final String type, final Map<String, Object> data,final Map<String, Object> domChanges){
-    fireEvent(elementRef, type, data, domChanges, null);
-  }
-
-  public void fireEvent(String elementRef,final String type, final Map<String, Object> data){
-    fireEvent(elementRef,type,data,null);
-  }
-
-  public void fireEvent(String ref, String type){
-    fireEvent(ref,type,new HashMap<String, Object>());
-  }
-
-  protected void addEventListener(String eventName, String callback) {
-    if (TextUtils.isEmpty(eventName) || TextUtils.isEmpty(callback)) {
-      return;
-    }
-    List<String> callbacks = mGlobalEvents.get(eventName);
-    if (callbacks == null) {
-      callbacks = new ArrayList<>();
-      mGlobalEvents.put(eventName, callbacks);
-    }
-    callbacks.add(callback);
-  }
-  protected void removeEventListener(String eventName, String callback) {
-    if (TextUtils.isEmpty(eventName) || TextUtils.isEmpty(callback)) {
-      return;
-    }
-    List<String> callbacks = mGlobalEvents.get(eventName);
-    if (callbacks != null) {
-      callbacks.remove(callback);
-    }
-  }
-
-  protected void removeEventListener(String eventName) {
-    if (TextUtils.isEmpty(eventName)) {
-      return;
-    }
-    mGlobalEvents.remove(eventName);
-  }
-
-  /**
-   * Notifies WEEX that this event has occurred
-   * @param eventName WEEX register event
-   * @param module Events occur in this Module
-   * @param params The parameters to be notified to WEEX are required
-   */
-  public void fireModuleEvent(String eventName, WXModule module,Map<String, Object> params) {
-    if (TextUtils.isEmpty(eventName) || module == null) {
-      return;
-    }
-
-    Map<String, Object> event = new HashMap<>();
-    event.put("type", eventName);
-    event.put("module", module.getModuleName());
-    event.put("data", params);
-
-    List<String> callbacks = module.getEventCallbacks(eventName);
-    if (callbacks != null) {
-      for (String callback : callbacks) {
-        SimpleJSCallback jsCallback = new SimpleJSCallback(mInstanceId, callback);
-        if (module.isOnce(callback)) {
-          jsCallback.invoke(event);
-        } else {
-          jsCallback.invokeAndKeepAlive(event);
-        }
-      }
-    }
-  }
-
-  /**
-   * Check whether the current module registered the event
-   * @param eventName EventName register in weex
-   * @param module Events occur in this Module
-   * @return  register->true
-   */
-  public boolean checkModuleEventRegistered(String eventName,WXModule module) {
-    if (module != null) {
-      List<String> events = module.getEventCallbacks(eventName);
-      if (events != null && events.size() > 0) {
-        return true;
-      }
-    }
-    return false;
-  }
-
-  public WXPerformance getWXPerformance(){
-    return mWXPerformance;
-  }
-
-  public WXInstanceApm getApmForInstance() {
-    return mApmForInstance;
-  }
-
-  public Map<String, Serializable> getUserTrackParams() {
-    return mUserTrackParams;
-  }
-
-  public void addUserTrackParameter(String key,Serializable value){
-    if(this.mUserTrackParams == null){
-      this.mUserTrackParams = new ConcurrentHashMap<>();
-    }
-    mUserTrackParams.put(key,value);
-  }
-
-  public void clearUserTrackParameters(){
-    if(this.mUserTrackParams != null){
-      this.mUserTrackParams.clear();
-    }
-  }
-
-  public void removeUserTrackParameter(String key){
-    if(this.mUserTrackParams != null){
-      this.mUserTrackParams.remove(key);
-    }
-  }
-
-  public int getMaxDeepLayer() {
-    return mMaxDeepLayer;
-  }
-
-  public void setMaxDeepLayer(int maxDeepLayer) {
-    mMaxDeepLayer = maxDeepLayer;
-    mApmForInstance.updateMaxStats(WXInstanceApm.KEY_PAGE_STATS_MAX_DEEP_VIEW,maxDeepLayer);
-  }
-
-  public void setMaxDomDeep(int maxDomDeep){
-    mApmForInstance.updateMaxStats(WXInstanceApm.KEY_PAGE_STATS_MAX_DEEP_DOM,maxDomDeep);
-    if (null == mWXPerformance){
-      return;
-    }
-    if (mWXPerformance.maxDeepVDomLayer <= maxDomDeep){
-      mWXPerformance.maxDeepVDomLayer = maxDomDeep;
-    }
-  }
-
-  public void onHttpStart(){
-    if (!mEnd){
-      mWXPerformance.fsRequestNum++;
-    }
-  }
-
-  /**
-   * return md5, and bytes length
-   * */
-  public String getTemplateInfo() {
-    String template = getTemplate();
-    if(template == null){
-      return " template md5 null ,httpHeader:" + JSONObject.toJSONString(responseHeaders);
-    }
-    if(TextUtils.isEmpty(template)){
-      return " template md5  length 0 ,httpHeader" + JSONObject.toJSONString(responseHeaders);
-    }
-    try {
-      byte[] bts = template.getBytes("UTF-8");
-      String sourceMD5 = WXFileUtils.md5(bts);
-      String sourceBase64MD5 = WXFileUtils.base64Md5(bts);
-      ArrayList<String> sourceMD5List = new ArrayList<>();
-      ArrayList<String> sourceBase64MD5List = new ArrayList<>();
-      sourceMD5List.add(sourceMD5);
-      sourceBase64MD5List.add(sourceBase64MD5);
-      responseHeaders.put("templateSourceMD5", sourceMD5List);
-      responseHeaders.put(SOURCE_TEMPLATE_BASE64_MD5, sourceBase64MD5List);
-      return " template md5 " + sourceMD5 + " length " +   bts.length
-              + " base64 md5 " + sourceBase64MD5
-              + " response header " + JSONObject.toJSONString(responseHeaders);
-    } catch (Exception e) {
-      return "template md5 getBytes error";
-    }
-
-  }
-
-  /**
-   * check template header md5 match with header  content-md5
-   * */
-  public boolean isContentMd5Match(){
-    if(responseHeaders == null){
-      return true;
-    }
-    List<String> contentMD5s = responseHeaders.get("Content-Md5");
-    if(contentMD5s == null){
-      contentMD5s  = responseHeaders.get("content-md5");
-    }
-    if(contentMD5s == null || contentMD5s.size() <= 0){
-      return true;
-    }
-    String md5 = contentMD5s.get(0);
-
-    List<String> sourceBase64Md5 = responseHeaders.get(SOURCE_TEMPLATE_BASE64_MD5);
-    if(sourceBase64Md5 == null){
-      getTemplateInfo();
-      sourceBase64Md5 = responseHeaders.get(SOURCE_TEMPLATE_BASE64_MD5);
-    }
-    if(sourceBase64Md5 == null || sourceBase64Md5.size() == 0){
-      return  true;
-    }
-    return  md5.equals(sourceBase64Md5.get(0));
-  }
-
-  public String getTemplate() {
-    if(templateRef == null){
-      return  null;
-    }
-    return templateRef.get();
-  }
-
-  public void setTemplate(String template) {
-    this.templateRef = new WeakReference<String>(template);
-  }
-
-  public interface NestedInstanceInterceptor {
-    void onCreateNestInstance(WXSDKInstance instance, NestedContainer container);
-  }
-
-  public void OnVSync() {
-    if(mFixMultiThreadBug) {
-      if(!mPageDirty) {
-        return;
-      }
-      WXBridgeManager.getInstance().post(new Runnable() {
-        @Override
-        public void run() {
-          boolean forceLayout = WXBridgeManager.getInstance().notifyLayout(getInstanceId());
-          if(forceLayout) {
-            WXBridgeManager.getInstance().forceLayout(getInstanceId());
-          }
-        }
-      });
-    } else  {
-      boolean forceLayout = WXBridgeManager.getInstance().notifyLayout(getInstanceId());
-      if(forceLayout) {
-        WXBridgeManager.getInstance().post(new Runnable() {
-          @Override
-          public void run() {
-            WXBridgeManager.getInstance().forceLayout(getInstanceId());
-          }
-        });
-      }
-    }
-
-
-  }
-
-  public void addContentBoxMeasurement(long renderObjectPtr, ContentBoxMeasurement contentBoxMeasurement) {
-    mContentBoxMeasurements.put(renderObjectPtr, contentBoxMeasurement);
-  }
-
-  public ContentBoxMeasurement getContentBoxMeasurement(long renderObjectPtr) {
-    return mContentBoxMeasurements.get(renderObjectPtr);
-  }
-
-
-  private void onInterceptInstanceEvent(String instanceId, String elementRef, String type, Map<String, Object> data, Map<String, Object> domChanges) {
-    if(this.mInstanceOnFireEventInterceptorList == null){
-      return;
-    }
-    for(InstanceOnFireEventInterceptor instanceOnFireEventInterceptor : this.mInstanceOnFireEventInterceptorList){
-      instanceOnFireEventInterceptor.onInterceptFireEvent(instanceId, elementRef, type, data, domChanges);
-    }
-  }
-
-  public List<InstanceOnFireEventInterceptor> getInstanceOnFireEventInterceptorList(){
-    if(this.mInstanceOnFireEventInterceptorList == null){
-      this.mInstanceOnFireEventInterceptorList = new ArrayList<>();
-    }
-    return mInstanceOnFireEventInterceptorList;
-  }
-
-
-  public void addInstanceOnFireEventInterceptor(InstanceOnFireEventInterceptor instanceOnFireEventInterceptor) {
-    if(instanceOnFireEventInterceptor == null){
-      return;
-    }
-    if(!getInstanceOnFireEventInterceptorList().contains(instanceOnFireEventInterceptor)){
-      getInstanceOnFireEventInterceptorList().add(instanceOnFireEventInterceptor);
-    }
-  }
-
-  public String getRenderType() {
-    return mRenderType;
-  }
-
-  public void setRenderType(String renderType) {
-    this.mRenderType = renderType;
-  }
-
-  private static boolean isDisableSkipFrameworkInDataRender() {
-    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
-    if (adapter == null) {
-      return false;
-    }
-    String result = adapter.getConfig("wxeagle", "disable_skip_framework_init", "false");
-    return "true".equals(result);
-  }
-
-  public boolean isPageDirty() {
-    return mPageDirty;
-  }
-
-  public void setPageDirty(boolean mPageDirty) {
-    this.mPageDirty = mPageDirty;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/WXSDKManager.java b/android/sdk/src/main/java/com/taobao/weex/WXSDKManager.java
deleted file mode 100644
index c6c49d9..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/WXSDKManager.java
+++ /dev/null
@@ -1,540 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import android.os.Looper;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-
-import com.taobao.weex.adapter.ClassLoaderAdapter;
-import com.taobao.weex.adapter.DefaultUriAdapter;
-import com.taobao.weex.adapter.DefaultWXHttpAdapter;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.adapter.ICrashInfoReporter;
-import com.taobao.weex.adapter.IDrawableLoader;
-import com.taobao.weex.adapter.IWXJscProcessManager;
-import com.taobao.weex.adapter.ITracingAdapter;
-import com.taobao.weex.adapter.IWXAccessibilityRoleAdapter;
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.adapter.IWXImgLoaderAdapter;
-import com.taobao.weex.adapter.IWXJSExceptionAdapter;
-import com.taobao.weex.adapter.IWXJsFileLoaderAdapter;
-import com.taobao.weex.adapter.IWXSoLoaderAdapter;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.appfram.navigator.IActivityNavBarSetter;
-import com.taobao.weex.appfram.navigator.INavigator;
-import com.taobao.weex.appfram.storage.DefaultWXStorage;
-import com.taobao.weex.appfram.storage.IWXStorageAdapter;
-import com.taobao.weex.appfram.websocket.IWebSocketAdapter;
-import com.taobao.weex.appfram.websocket.IWebSocketAdapterFactory;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.bridge.WXModuleManager;
-import com.taobao.weex.bridge.WXValidateProcessor;
-import com.taobao.weex.common.WXRefreshData;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.common.WXWorkThreadManager;
-import com.taobao.weex.font.FontAdapter;
-import com.taobao.weex.performance.IApmGenerator;
-import com.taobao.weex.performance.IWXAnalyzer;
-import com.taobao.weex.ui.WXRenderManager;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-
-import java.io.File;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.CopyOnWriteArrayList;
-import java.util.concurrent.atomic.AtomicInteger;
-
-/**
- * Manger class for weex context.
- */
-public class WXSDKManager {
-
-  private static volatile WXSDKManager sManager;
-  private static AtomicInteger sInstanceId = new AtomicInteger(0);
-  private final WXWorkThreadManager mWXWorkThreadManager;
-  private WXBridgeManager mBridgeManager;
-  /** package **/ WXRenderManager mWXRenderManager;
-
-  private IWXUserTrackAdapter mIWXUserTrackAdapter;
-  private IWXImgLoaderAdapter mIWXImgLoaderAdapter;
-  private IWXSoLoaderAdapter mIWXSoLoaderAdapter;
-  private IDrawableLoader mDrawableLoader;
-  private IWXHttpAdapter mIWXHttpAdapter;
-  private IActivityNavBarSetter mActivityNavBarSetter;
-  private IWXAccessibilityRoleAdapter mRoleAdapter;
-  private List<IWXAnalyzer> mWXAnalyzerList;
-  private IApmGenerator mApmGenerater;
-  private IWXJsFileLoaderAdapter mWXJsFileLoaderAdapter;
-
-  private ICrashInfoReporter mCrashInfo;
-
-  private IWXJSExceptionAdapter mIWXJSExceptionAdapter;
-
-  private IWXConfigAdapter mConfigAdapter;
-  private IWXStorageAdapter mIWXStorageAdapter;
-  private IWXStatisticsListener mStatisticsListener;
-  private URIAdapter mURIAdapter;
-  private ClassLoaderAdapter mClassLoaderAdapter;
-  private IWebSocketAdapterFactory mIWebSocketAdapterFactory;
-  private ITracingAdapter mTracingAdapter;
-  private WXValidateProcessor mWXValidateProcessor;
-  private IWXJscProcessManager mWXJscProcessManager;
-  // Tell weexv8 to initialize v8, default is true.
-  private boolean mNeedInitV8 = true;
-
-  //add when instance create,rm when instance destroy, not like WXRenderManager
-  private Map<String,WXSDKInstance> mAllInstanceMap;
-
-  private List<InstanceLifeCycleCallbacks> mLifeCycleCallbacks;
-
-  private static final int DEFAULT_VIEWPORT_WIDTH = 750;
-
-  private WXSDKManager() {
-    this(new WXRenderManager());
-  }
-
-  private WXSDKManager(WXRenderManager renderManager) {
-    mWXRenderManager = renderManager;
-    mBridgeManager = WXBridgeManager.getInstance();
-    mWXWorkThreadManager = new WXWorkThreadManager();
-    mWXAnalyzerList = new CopyOnWriteArrayList<>();
-    mAllInstanceMap = new HashMap<>();
-  }
-
-  /**
-   * Used in junit test
-   */
-  static void initInstance(WXRenderManager renderManager){
-    sManager = new WXSDKManager(renderManager);
-  }
-
-  public void registerStatisticsListener(IWXStatisticsListener listener) {
-    mStatisticsListener = listener;
-  }
-
-  public IWXStatisticsListener getWXStatisticsListener() {
-    return mStatisticsListener;
-  }
-
-  public void onSDKEngineInitialize() {
-    if (mStatisticsListener != null) {
-      mStatisticsListener.onSDKEngineInitialize();
-    }
-  }
-
-  public void setNeedInitV8(boolean need) {
-    mNeedInitV8 = need;
-  }
-
-  public boolean needInitV8() {
-    return mNeedInitV8;
-  }
-
-  public void takeJSHeapSnapshot(String path) {
-    File file = new File(path);
-    if (!file.exists()) {
-      if (!file.mkdir()) {
-        return;
-      }
-    }
-
-    String name = String.valueOf(sInstanceId.get());
-    String filename = path;
-
-    if (!path.endsWith(File.separator)) {
-      filename += File.separator;
-    }
-    filename += name;
-    filename += ".heapsnapshot";
-
-    mBridgeManager.takeJSHeapSnapshot(filename);
-  }
-
-  public static WXSDKManager getInstance() {
-    if (sManager == null) {
-      synchronized (WXSDKManager.class) {
-        if(sManager == null) {
-          sManager = new WXSDKManager();
-        }
-      }
-    }
-    return sManager;
-  }
-
-  public static int getInstanceViewPortWidth(String instanceId){
-    WXSDKInstance instance = getInstance().getSDKInstance(instanceId);
-    if (instance == null) {
-      return DEFAULT_VIEWPORT_WIDTH;
-    }
-    return instance.getInstanceViewPortWidth();
-  }
-
-  static void setInstance(WXSDKManager manager){
-    sManager = manager;
-  }
-
-  public IActivityNavBarSetter getActivityNavBarSetter() {
-    return mActivityNavBarSetter;
-  }
-
-  public void setActivityNavBarSetter(IActivityNavBarSetter mActivityNavBarSetter) {
-    this.mActivityNavBarSetter = mActivityNavBarSetter;
-  }
-
-  public void restartBridge() {
-    mBridgeManager.restart();
-  }
-
-  public WXBridgeManager getWXBridgeManager() {
-    return mBridgeManager;
-  }
-
-  public WXRenderManager getWXRenderManager() {
-    return mWXRenderManager;
-  }
-  public IWXJscProcessManager getWXJscProcessManager() {
-    return mWXJscProcessManager;
-  }
-  public WXWorkThreadManager getWXWorkThreadManager() {
-    return mWXWorkThreadManager;
-  }
-
-  public void setWxConfigAdapter(IWXConfigAdapter mConfigAdapter) {
-    this.mConfigAdapter = mConfigAdapter;
-  }
-
-  public IWXConfigAdapter getWxConfigAdapter() {
-    return mConfigAdapter;
-  }
-
-  public @Nullable WXSDKInstance getSDKInstance(String instanceId) {
-    return instanceId == null? null : mWXRenderManager.getWXSDKInstance(instanceId);
-  }
-
-  public void postOnUiThread(Runnable runnable, long delayMillis) {
-    mWXRenderManager.postOnUiThread(WXThread.secure(runnable), delayMillis);
-  }
-  public Map<String, WXSDKInstance> getAllInstanceMap() {
-    return mAllInstanceMap;
-  }
-
-  public void destroy() {
-    if (mWXWorkThreadManager != null) {
-      mWXWorkThreadManager.destroy();
-    }
-    mAllInstanceMap.clear();
-  }
-
-  @Deprecated
-  public void callback(String instanceId, String funcId, Map<String, Object> data) {
-    mBridgeManager.callback(instanceId, funcId, data);
-  }
-
-  @Deprecated
-  public void callback(String instanceId, String funcId, Map<String, Object> data,boolean keepAlive) {
-    mBridgeManager.callback(instanceId, funcId, data,keepAlive);
-  }
-
-  public void initScriptsFramework(String framework) {
-    mBridgeManager.initScriptsFramework(framework);
-  }
-
-  public void registerComponents(List<Map<String, Object>> components) {
-    mBridgeManager.registerComponents(components);
-  }
-
-  public void registerModules(Map<String, Object> modules) {
-    mBridgeManager.registerModules(modules);
-  }
-
-  /**
-   * Do not direct invoke this method in Components, use {@link WXSDKInstance#fireEvent(String, String, Map, Map)} instead.
-   */
-  @Deprecated
-  public void fireEvent(final String instanceId, String ref, String type) {
-    fireEvent(instanceId, ref, type, new HashMap<String, Object>());
-  }
-
-  /**
-   * FireEvent back to JS
-   * Do not direct invoke this method in Components, use {@link WXSDKInstance#fireEvent(String, String, Map, Map)} instead.
-   */
-  @Deprecated
-  public void fireEvent(final String instanceId, String ref, String type, Map<String, Object> params){
-    fireEvent(instanceId,ref,type,params,null);
-  }
-
-  /**
-   * Do not direct invoke this method in Components, use {@link WXSDKInstance#fireEvent(String, String, Map, Map)} instead.
-   **/
-  @Deprecated
-  public void fireEvent(final String instanceId, String ref, String type, Map<String, Object> params,Map<String,Object> domChanges) {
-    if (WXEnvironment.isApkDebugable() && Looper.getMainLooper().getThread().getId() != Thread.currentThread().getId()) {
-      throw new WXRuntimeException("[WXSDKManager]  fireEvent error");
-    }
-    mBridgeManager.fireEventOnNode(instanceId, ref, type, params,domChanges);
-  }
-
-  void createInstance(WXSDKInstance instance, Script code, Map<String, Object> options, String jsonInitData) {
-    mWXRenderManager.registerInstance(instance);
-    mBridgeManager.createInstance(instance.getInstanceId(), code, options, jsonInitData);
-    if (mLifeCycleCallbacks != null) {
-      for (InstanceLifeCycleCallbacks callbacks : mLifeCycleCallbacks) {
-        callbacks.onInstanceCreated(instance.getInstanceId());
-      }
-    }
-  }
-
-  void refreshInstance(String instanceId, WXRefreshData jsonData) {
-    mBridgeManager.refreshInstance(instanceId, jsonData);
-  }
-
-  void destroyInstance(String instanceId) {
-    setCrashInfo(WXEnvironment.WEEX_CURRENT_KEY,"");
-    if (TextUtils.isEmpty(instanceId)) {
-      return;
-    }
-    if (!WXUtils.isUiThread()) {
-      throw new WXRuntimeException("[WXSDKManager] destroyInstance error");
-    }
-    if (mLifeCycleCallbacks != null) {
-      for (InstanceLifeCycleCallbacks callbacks : mLifeCycleCallbacks) {
-        callbacks.onInstanceDestroyed(instanceId);
-      }
-    }
-    mWXRenderManager.removeRenderStatement(instanceId);
-    mBridgeManager.destroyInstance(instanceId);
-    WXModuleManager.destroyInstanceModules(instanceId);
-  }
-
-  String generateInstanceId() {
-    return String.valueOf(sInstanceId.incrementAndGet());
-  }
-
-  public IWXUserTrackAdapter getIWXUserTrackAdapter() {
-    return mIWXUserTrackAdapter;
-  }
-
-  public IWXImgLoaderAdapter getIWXImgLoaderAdapter() {
-    return mIWXImgLoaderAdapter;
-  }
-
-  public IWXJsFileLoaderAdapter getIWXJsFileLoaderAdapter() {
-    return mWXJsFileLoaderAdapter;
-  }
-
-  public IDrawableLoader getDrawableLoader() {
-    return mDrawableLoader;
-  }
-
-  public IWXJSExceptionAdapter getIWXJSExceptionAdapter() {
-    return mIWXJSExceptionAdapter;
-  }
-
-  public void setIWXJSExceptionAdapter(IWXJSExceptionAdapter IWXJSExceptionAdapter) {
-    mIWXJSExceptionAdapter = IWXJSExceptionAdapter;
-  }
-
-  public @NonNull IWXHttpAdapter getIWXHttpAdapter() {
-    if (mIWXHttpAdapter == null) {
-      mIWXHttpAdapter = new DefaultWXHttpAdapter();
-    }
-    return mIWXHttpAdapter;
-  }
-
-  public IApmGenerator getApmGenerater() {
-    return mApmGenerater;
-  }
-
-  public @NonNull URIAdapter getURIAdapter() {
-    if(mURIAdapter == null){
-      mURIAdapter = new DefaultUriAdapter();
-    }
-    return mURIAdapter;
-  }
-
-  public ClassLoaderAdapter getClassLoaderAdapter() {
-    if(mClassLoaderAdapter == null){
-      mClassLoaderAdapter = new ClassLoaderAdapter();
-    }
-    return mClassLoaderAdapter;
-  }
-
-  public IWXSoLoaderAdapter getIWXSoLoaderAdapter() {
-    return mIWXSoLoaderAdapter;
-  }
-
-  public List<IWXAnalyzer> getWXAnalyzerList(){
-    return mWXAnalyzerList;
-  }
-
-  public void addWXAnalyzer(IWXAnalyzer analyzer){
-    if (!mWXAnalyzerList.contains(analyzer)) {
-      mWXAnalyzerList.add(analyzer);
-    }
-  }
-
-  public void rmWXAnalyzer(IWXAnalyzer analyzer){
-    mWXAnalyzerList.remove(analyzer);
-  }
-
-  void setInitConfig(InitConfig config){
-    this.mIWXHttpAdapter = config.getHttpAdapter();
-    this.mIWXImgLoaderAdapter = config.getImgAdapter();
-    this.mDrawableLoader = config.getDrawableLoader();
-    this.mIWXStorageAdapter = config.getStorageAdapter();
-    this.mIWXUserTrackAdapter = config.getUtAdapter();
-    this.mURIAdapter = config.getURIAdapter();
-    this.mIWebSocketAdapterFactory = config.getWebSocketAdapterFactory();
-    this.mIWXJSExceptionAdapter = config.getJSExceptionAdapter();
-    this.mIWXSoLoaderAdapter = config.getIWXSoLoaderAdapter();
-    this.mClassLoaderAdapter = config.getClassLoaderAdapter();
-    this.mApmGenerater = config.getApmGenerater();
-    this.mWXJsFileLoaderAdapter = config.getJsFileLoaderAdapter();
-    this.mWXJscProcessManager = config.getJscProcessManager();
-  }
-
-  public IWXStorageAdapter getIWXStorageAdapter(){
-    if(mIWXStorageAdapter == null){
-      if(WXEnvironment.sApplication != null){
-        mIWXStorageAdapter = new DefaultWXStorage(WXEnvironment.sApplication);
-      }else{
-        WXLogUtils.e("WXStorageModule", "No Application context found,you should call WXSDKEngine#initialize() method in your application");
-      }
-    }
-    return mIWXStorageAdapter;
-  }
-
-  /**
-   * Weex embedders can use <code>notifyTrimMemory</code> to reduce
-   * memory at a proper time.
-   *
-   * It's not a good idea to reduce memory at any time, because
-   * memory trimming is a expense operation, and V8 needs to do
-   * a full GC and all the inline caches get to be cleared.
-   *
-   * The embedder needs to make some scheduling strategies to
-   * ensure that the embedded application is just on an idle time.
-   * If the application use the same js bundle to render pages,
-   * it's not a good idea to trim memory every time of exiting
-   * pages.
-   */
-  public void notifyTrimMemory() {
-    mBridgeManager.notifyTrimMemory();
-  }
-
-  /**
-   * Weex embedders can use <code>notifySerializeCodeCache</code> to
-   * serialize code caches if the jsfm has the alility to compile 'new Function'
-   * against js bundles on the weex native side.
-   *
-   * It's a good time to serialize a code cache after exiting a weex page.
-   * Then, the next time of entering the same weex page, V8 would compile
-   * 'new Function' against the code cache deseriazed from the js bundle.
-   */
-  public void notifySerializeCodeCache() {
-    mBridgeManager.notifySerializeCodeCache();
-  }
-
-  public @Nullable
-  IWebSocketAdapter getIWXWebSocketAdapter() {
-    if (mIWebSocketAdapterFactory != null) {
-      return mIWebSocketAdapterFactory.createWebSocketAdapter();
-    }
-    return null;
-  }
-
-  public void registerValidateProcessor(WXValidateProcessor processor){
-    this.mWXValidateProcessor = processor;
-  }
-
-  public WXValidateProcessor getValidateProcessor(){
-    return mWXValidateProcessor;
-  }
-
-
-  public void setCrashInfoReporter(ICrashInfoReporter mCrashInfo) {
-    this.mCrashInfo = mCrashInfo;
-  }
-
-  public void setCrashInfo(String key, String value) {
-    if(mCrashInfo!=null){
-      mCrashInfo.addCrashInfo(key,value);
-    }
-  }
-
-  public void setTracingAdapter(ITracingAdapter adapter) {
-    this.mTracingAdapter = adapter;
-  }
-
-  public ITracingAdapter getTracingAdapter() {
-    return mTracingAdapter;
-  }
-
-  public void registerInstanceLifeCycleCallbacks(InstanceLifeCycleCallbacks callbacks) {
-    if (mLifeCycleCallbacks == null) {
-      mLifeCycleCallbacks = new ArrayList<>();
-    }
-    mLifeCycleCallbacks.add(callbacks);
-  }
-
-  public void setAccessibilityRoleAdapter(IWXAccessibilityRoleAdapter adapter) {
-    this.mRoleAdapter = adapter;
-  }
-
-  public IWXAccessibilityRoleAdapter getAccessibilityRoleAdapter() {
-    return mRoleAdapter;
-  }
-
-  public interface InstanceLifeCycleCallbacks {
-    void onInstanceDestroyed(String instanceId);
-    void onInstanceCreated(String instanceId);
-  }
-
-  private INavigator mNavigator;
-
-  public INavigator getNavigator() {
-    return mNavigator;
-  }
-
-  public void setNavigator(INavigator mNavigator) {
-    this.mNavigator = mNavigator;
-  }
-
-
-  private FontAdapter mFontAdapter;
-
-  public FontAdapter getFontAdapter(){
-      if(mFontAdapter == null){
-        synchronized (this){
-          if(mFontAdapter == null){
-              mFontAdapter = new FontAdapter();
-          }
-        }
-      }
-      return mFontAdapter;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/WeexFrameRateControl.java b/android/sdk/src/main/java/com/taobao/weex/WeexFrameRateControl.java
deleted file mode 100644
index eef4d5c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/WeexFrameRateControl.java
+++ /dev/null
@@ -1,110 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex;
-
-/**
- * Created by shiwentao on 2017/8/24.
- */
-
-import android.annotation.SuppressLint;
-import android.os.Build;
-import android.util.Log;
-import android.view.Choreographer;
-import com.taobao.weex.common.WXErrorCode;
-import java.lang.ref.WeakReference;
-
-public class WeexFrameRateControl {
-    private static final long VSYNC_FRAME = 1000 / 60;
-    private WeakReference<VSyncListener> mListener;
-    private final Choreographer mChoreographer;
-    private final Choreographer.FrameCallback mVSyncFrameCallback;
-    private final Runnable runnable;
-
-    public interface VSyncListener {
-        void OnVSync();
-    }
-
-    public WeexFrameRateControl(VSyncListener listener) {
-        mListener = new WeakReference<>(listener);
-        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.ICE_CREAM_SANDWICH_MR1) {
-            mChoreographer = Choreographer.getInstance();
-            mVSyncFrameCallback = new Choreographer.FrameCallback() {
-                @SuppressLint("NewApi")
-                @Override
-                public void doFrame(long frameTimeNanos) {
-                    VSyncListener vSyncListener;
-                    if (mListener != null && (vSyncListener=mListener.get()) != null) {
-                        try {
-                            vSyncListener.OnVSync();
-                            mChoreographer.postFrameCallback(mVSyncFrameCallback);
-                        }catch (UnsatisfiedLinkError e){
-                            if(vSyncListener instanceof WXSDKInstance){
-                                ((WXSDKInstance) vSyncListener).onRenderError(
-                                    WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-                                    Log.getStackTraceString(e));
-                            }
-                        }
-                    }
-                }
-            };
-            runnable = null;
-        } else {
-            // For API 15 or lower
-            runnable = new Runnable() {
-                @Override
-                public void run() {
-                    VSyncListener vSyncListener;
-                    if (mListener != null && (vSyncListener = mListener.get()) != null) {
-                        try {
-                            vSyncListener.OnVSync();
-                            WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(runnable, VSYNC_FRAME);
-                        }catch (UnsatisfiedLinkError e){
-                            if(vSyncListener instanceof WXSDKInstance){
-                                ((WXSDKInstance) vSyncListener).onRenderError(
-                                    WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-                                    Log.getStackTraceString(e));
-                            }
-                        }
-                    }
-                }
-            };
-            mChoreographer = null;
-            mVSyncFrameCallback = null;
-        }
-    }
-
-    @SuppressLint("NewApi")
-    public void start() {
-        if (mChoreographer != null) {
-            mChoreographer.postFrameCallback(mVSyncFrameCallback);
-        }
-        else if(runnable!=null){
-            WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(runnable, VSYNC_FRAME);
-        }
-    }
-
-    @SuppressLint("NewApi")
-    public void stop() {
-        if (mChoreographer != null) {
-            mChoreographer.removeFrameCallback(mVSyncFrameCallback);
-        }else if(runnable!=null){
-            WXSDKManager.getInstance().getWXRenderManager().removeTask(runnable);
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/ClassLoaderAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/ClassLoaderAdapter.java
deleted file mode 100644
index 7d6a854..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/ClassLoaderAdapter.java
+++ /dev/null
@@ -1,55 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import android.content.Context;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by furture on 2018/2/7.
- * class loader adapter for load auto config class.
- */
-public class ClassLoaderAdapter {
-
-    /**
-     * context is module class
-     * */
-    public Class<? extends WXModule> getModuleClass(String name, String className, Context context){
-        try {
-            return (Class<? extends WXModule>) context.getClassLoader().loadClass(className);
-        } catch (ClassNotFoundException e) {
-            throw  new RuntimeException(e);
-        }
-    }
-
-    /**
-     * context is instance context
-     */
-    public Class<? extends WXComponent> getComponentClass(String name, String className, WXSDKInstance instance) {
-        try {
-            return (Class<? extends WXComponent>) instance.getContext().getClassLoader().loadClass(className);
-        } catch (ClassNotFoundException e) {
-            throw  new RuntimeException(e);
-        }
-    }
-
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/DefaultUriAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/DefaultUriAdapter.java
deleted file mode 100644
index de77e87..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/DefaultUriAdapter.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import android.net.Uri;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKInstance;
-
-import java.util.List;
-
-
-/**
- * Default Uri adapter. Provide basic capability to handle relative path, local file path etc.
- * Created by sospartan on 21/11/2016.
- */
-public class DefaultUriAdapter implements URIAdapter {
-
-
-  @NonNull
-  @Override
-  public Uri rewrite(WXSDKInstance instance, String type, Uri uri) {
-    return rewrite(instance.getBundleUrl(), type, uri);
-  }
-
-  @NonNull
-  @Override
-  public Uri rewrite(String bundleURL, String type, Uri uri) {
-    if (TextUtils.isEmpty(bundleURL)) {
-      return uri;
-    }
-
-    Uri base = Uri.parse(bundleURL);
-    Uri.Builder resultBuilder = uri.buildUpon();
-
-    if (uri.isRelative()) {
-      //When uri is empty, means use the base url instead. Web broswer behave this way.
-      if(uri.getEncodedPath().length() == 0){
-        if(URIAdapter.IMAGE.equals(type)){
-          if(TextUtils.isEmpty(uri.toString())){
-            return uri;
-          }
-        }
-        return base;
-      } else {
-        resultBuilder = buildRelativeURI(resultBuilder, base, uri);
-        return resultBuilder.build();
-      }
-    }
-    return uri;
-  }
-
-  private Uri.Builder buildRelativeURI(Uri.Builder resultBuilder, Uri base, Uri uri) {
-    if (uri.getAuthority() != null) {
-      return resultBuilder.scheme(base.getScheme());
-    } else {
-      resultBuilder
-          .encodedAuthority(base.getEncodedAuthority())
-          .scheme(base.getScheme())
-          .path(null);
-
-      if (uri.getPath().startsWith("/")) {
-        //relative to root
-        resultBuilder.appendEncodedPath(uri.getEncodedPath().substring(1));
-      } else {
-        List<String> segments = base.getPathSegments();
-        //ignore last segment if not end with /
-        int ignoreLast = 1;
-        if (base.getPath().endsWith("/")) {
-          ignoreLast = 0;
-        }
-        for (int i = 0, len = segments.size() - ignoreLast; i < len; i++) {
-          resultBuilder.appendEncodedPath(segments.get(i));
-        }
-        resultBuilder.appendEncodedPath(uri.getEncodedPath());
-      }
-      return resultBuilder;
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/DefaultWXHttpAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/DefaultWXHttpAdapter.java
deleted file mode 100644
index 2d26765..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/DefaultWXHttpAdapter.java
+++ /dev/null
@@ -1,248 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.WXRequest;
-import com.taobao.weex.common.WXResponse;
-
-import java.io.BufferedReader;
-import java.io.ByteArrayOutputStream;
-import java.io.DataOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.InputStreamReader;
-import java.net.HttpURLConnection;
-import java.net.URL;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-
-
-public class DefaultWXHttpAdapter implements IWXHttpAdapter {
-
-  private static final IEventReporterDelegate DEFAULT_DELEGATE = new NOPEventReportDelegate();
-  private ExecutorService mExecutorService;
-
-  private void execute(Runnable runnable){
-    if(mExecutorService==null){
-      mExecutorService = Executors.newFixedThreadPool(3);
-    }
-    mExecutorService.execute(runnable);
-  }
-
-  @Override
-  public void sendRequest(final WXRequest request, final OnHttpListener listener) {
-    if (listener != null) {
-      listener.onHttpStart();
-    }
-    execute(new Runnable() {
-      @Override
-      public void run() {
-        WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(request.instanceId);
-        if (null != instance && !instance.isDestroy()){
-          instance.getApmForInstance().actionNetRequest();
-        }
-
-        boolean isNetRequestSucceed = true;
-
-        WXResponse response = new WXResponse();
-        IEventReporterDelegate reporter = getEventReporterDelegate();
-        try {
-          HttpURLConnection connection = openConnection(request, listener);
-          reporter.preConnect(connection, request.body);
-          Map<String,List<String>> headers = connection.getHeaderFields();
-          int responseCode = connection.getResponseCode();
-          if(listener != null){
-            listener.onHeadersReceived(responseCode,headers);
-          }
-          reporter.postConnect();
-
-          response.statusCode = String.valueOf(responseCode);
-          if (responseCode >= 200 && responseCode<=299) {
-            InputStream rawStream = connection.getInputStream();
-            rawStream = reporter.interpretResponseStream(rawStream);
-            response.originalData = readInputStreamAsBytes(rawStream, listener);
-          } else {
-            response.errorMsg = readInputStream(connection.getErrorStream(), listener);
-            isNetRequestSucceed = false;
-          }
-          if (listener != null) {
-            listener.onHttpFinish(response);
-          }
-        } catch (IOException|IllegalArgumentException e) {
-          isNetRequestSucceed = false;
-          e.printStackTrace();
-          response.statusCode = "-1";
-          response.errorCode="-1";
-          response.errorMsg=e.getMessage();
-          if(listener!=null){
-            listener.onHttpFinish(response);
-          }
-          if (e instanceof IOException) {
-            try {
-              reporter.httpExchangeFailed((IOException) e);
-            } catch (Throwable t) {
-              t.printStackTrace();
-            }
-          }
-        }
-        if (null != instance && !instance.isDestroy()){
-          instance.getApmForInstance().actionNetResult(isNetRequestSucceed,null);
-        }
-      }
-    });
-  }
-
-
-  /**
-   * Opens an {@link HttpURLConnection} with parameters.
-   *
-   * @param request
-   * @param listener
-   * @return an open connection
-   * @throws IOException
-   */
-  private HttpURLConnection openConnection(WXRequest request, OnHttpListener listener) throws IOException {
-    URL url = new URL(request.url);
-    HttpURLConnection connection = createConnection(url);
-    connection.setConnectTimeout(request.timeoutMs);
-    connection.setReadTimeout(request.timeoutMs);
-    connection.setUseCaches(false);
-    connection.setDoInput(true);
-
-    if (request.paramMap != null) {
-      Set<String> keySets = request.paramMap.keySet();
-      for (String key : keySets) {
-        connection.addRequestProperty(key, request.paramMap.get(key));
-      }
-    }
-
-    if ("POST".equals(request.method) || "PUT".equals(request.method) || "PATCH".equals(request.method)) {
-      connection.setRequestMethod(request.method);
-      if (request.body != null) {
-        if (listener != null) {
-          listener.onHttpUploadProgress(0);
-        }
-        connection.setDoOutput(true);
-        DataOutputStream out = new DataOutputStream(connection.getOutputStream());
-        //TODO big stream will cause OOM; Progress callback is meaningless
-        out.write(request.body.getBytes());
-        out.close();
-        if (listener != null) {
-          listener.onHttpUploadProgress(100);
-        }
-      }
-    } else if (!TextUtils.isEmpty(request.method)) {
-      connection.setRequestMethod(request.method);
-    } else {
-      connection.setRequestMethod("GET");
-    }
-
-    return connection;
-  }
-
-  private byte[] readInputStreamAsBytes(InputStream inputStream,OnHttpListener listener) throws IOException{
-    if(inputStream == null){
-      return null;
-    }
-    ByteArrayOutputStream buffer = new ByteArrayOutputStream();
-
-    int nRead;
-    int readCount = 0;
-    byte[] data = new byte[2048];
-
-    while ((nRead = inputStream.read(data, 0, data.length)) != -1) {
-      buffer.write(data, 0, nRead);
-      readCount += nRead;
-      if (listener != null) {
-        listener.onHttpResponseProgress(readCount);
-      }
-    }
-
-    buffer.flush();
-
-    return buffer.toByteArray();
-  }
-
-  private String readInputStream(InputStream inputStream, OnHttpListener listener) throws IOException {
-    if(inputStream == null){
-      return null;
-    }
-    StringBuilder builder = new StringBuilder();
-    BufferedReader localBufferedReader = new BufferedReader(new InputStreamReader(inputStream));
-    char[] data = new char[2048];
-    int len;
-    while ((len = localBufferedReader.read(data)) != -1) {
-      builder.append(data, 0, len);
-      if (listener != null) {
-        listener.onHttpResponseProgress(builder.length());
-      }
-    }
-    localBufferedReader.close();
-    return builder.toString();
-  }
-
-  /**
-   * Create an {@link HttpURLConnection} for the specified {@code url}.
-   */
-  protected HttpURLConnection createConnection(URL url) throws IOException {
-    return (HttpURLConnection) url.openConnection();
-  }
-
-  public @NonNull IEventReporterDelegate getEventReporterDelegate() {
-    return DEFAULT_DELEGATE;
-  }
-
-  public interface IEventReporterDelegate {
-    void preConnect(HttpURLConnection connection, @Nullable String body);
-    void postConnect();
-    InputStream interpretResponseStream(@Nullable InputStream inputStream);
-    void httpExchangeFailed(IOException e);
-  }
-
-  private static class NOPEventReportDelegate implements IEventReporterDelegate {
-    @Override
-    public void preConnect(HttpURLConnection connection, @Nullable String body) {
-      //do nothing
-    }
-
-    @Override
-    public void postConnect() {
-      //do nothing
-    }
-
-    @Override
-    public InputStream interpretResponseStream(@Nullable InputStream inputStream) {
-      return inputStream;
-    }
-
-    @Override
-    public void httpExchangeFailed(IOException e) {
-      //do nothing
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/DrawableStrategy.java b/android/sdk/src/main/java/com/taobao/weex/adapter/DrawableStrategy.java
deleted file mode 100644
index c6daa5a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/DrawableStrategy.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.adapter;
-
-
-public class DrawableStrategy {
-
-  public int width;
-  public int height;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/ICrashInfoReporter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/ICrashInfoReporter.java
deleted file mode 100644
index 54c15cc..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/ICrashInfoReporter.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.adapter;
-
-/**
- * Created by zhengshihan on 2017/5/23.
- */
-
-public interface ICrashInfoReporter {
-  void addCrashInfo(String key ,String value);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IDrawableLoader.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IDrawableLoader.java
deleted file mode 100644
index 080d3b5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IDrawableLoader.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.adapter;
-
-import android.graphics.drawable.Drawable;
-import android.support.annotation.Nullable;
-
-public interface IDrawableLoader {
-
-  interface DrawableTarget {
-    void setDrawable(@Nullable Drawable drawable, boolean resetBounds);
-  }
-
-  interface StaticTarget extends DrawableTarget{
-    void setDrawable(@Nullable Drawable drawable, boolean resetBounds);
-  }
-
-  interface AnimatedTarget extends DrawableTarget{
-    void setAnimatedDrawable(@Nullable Drawable drawable);
-  }
-
-  void setDrawable(String url, DrawableTarget drawableTarget, DrawableStrategy drawableStrategy);
-}
-
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/ITracingAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/ITracingAdapter.java
deleted file mode 100644
index 4acb23d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/ITracingAdapter.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import com.taobao.weex.tracing.WXTracing;
-
-/**
- * Created by moxun on 2017/7/6.
- */
-
-public interface ITracingAdapter {
-  void enable();
-  void disable();
-  void submitTracingEvent(WXTracing.TraceEvent event);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXAccessibilityRoleAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXAccessibilityRoleAdapter.java
deleted file mode 100644
index 46ca77f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXAccessibilityRoleAdapter.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.adapter;
-
-/**
- * Created by moxun on 2017/11/13.
- */
-
-public interface IWXAccessibilityRoleAdapter {
-  String getRole(String key);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXConfigAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXConfigAdapter.java
deleted file mode 100644
index 953bf2c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXConfigAdapter.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.adapter;
-
-/**
- * @author zhongcang
- * @date 2019/3/20
- */
-public interface IWXConfigAdapter {
-    String getConfig(String nameSpace,String key,String defaultValue);
-    String getConfigWhenInit(String nameSpace,String key,String defaultValue);
-    boolean checkMode(String name);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXHttpAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXHttpAdapter.java
deleted file mode 100644
index 3d6ea1f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXHttpAdapter.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-
-import com.taobao.weex.common.WXRequest;
-import com.taobao.weex.common.WXResponse;
-
-import java.util.List;
-import java.util.Map;
-
-public interface IWXHttpAdapter {
-
-  /**
-   * http request method
-   *
-   * @param request weex assemble request
-   * @param listener http response notify
-   */
-  void sendRequest(WXRequest request, OnHttpListener listener);
-
-  interface OnHttpListener {
-
-    /**
-     * start request
-     */
-    void onHttpStart();
-
-    /**
-     * headers received
-     */
-    void onHeadersReceived(int statusCode,Map<String,List<String>> headers);
-
-    /**
-     * post progress
-     * @param uploadProgress
-     */
-    void onHttpUploadProgress(int uploadProgress);
-
-    /**
-     * response loaded length (bytes), full length should read from headers (content-length)
-     * @param loadedLength
-     */
-    void onHttpResponseProgress(int loadedLength);
-
-    /**
-     * http response finish
-     * @param response
-     */
-    void onHttpFinish(WXResponse response);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXImgLoaderAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXImgLoaderAdapter.java
deleted file mode 100644
index 4b03ba8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXImgLoaderAdapter.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import android.widget.ImageView;
-
-import com.taobao.weex.common.WXImageStrategy;
-import com.taobao.weex.dom.WXImageQuality;
-
-/**
- * Interface for ImageLoader. This interface works as an adapter for various image library.
- */
-public interface IWXImgLoaderAdapter {
-
-  void setImage(String url, ImageView view, WXImageQuality quality, WXImageStrategy strategy);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJSExceptionAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJSExceptionAdapter.java
deleted file mode 100644
index 12ea4d8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJSExceptionAdapter.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import com.taobao.weex.common.WXJSExceptionInfo;
-
-public interface IWXJSExceptionAdapter {
-
-  /**
-   * report js exception
-   *
-   * @param exception {@link WXJSExceptionInfo}
-   */
-
-  void onJSException(WXJSExceptionInfo exception);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJsFileLoaderAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJsFileLoaderAdapter.java
deleted file mode 100644
index 37bbf7f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJsFileLoaderAdapter.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.adapter;
-
-public interface IWXJsFileLoaderAdapter {
-    String loadRaxApi();
-    String loadJsFramework();
-    String loadJsFrameworkForSandBox();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJscProcessManager.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJscProcessManager.java
deleted file mode 100644
index 4c8d22a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXJscProcessManager.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import com.taobao.weex.WXSDKInstance;
-
-public interface IWXJscProcessManager {
-    boolean enableBackupThread();
-    boolean enableBackUpThreadCache();
-    boolean shouldReboot();
-    long rebootTimeout();
-    boolean withException(WXSDKInstance instance);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXSoLoaderAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXSoLoaderAdapter.java
deleted file mode 100644
index fb9614a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXSoLoaderAdapter.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-/**
- * Interface for loading library.
- */
-public interface IWXSoLoaderAdapter {
-  /**
-   * A method <code>doLoadLibrary</code> that
-   * helps embedders to load a shared library with a short name.
-   * <p>
-   *
-   * Embedders would have a chance to take charge of library loading,
-   * they could load libraries with different class loaders,
-   * or load libraries from specified library pathes.
-   *
-   * @param shortName the name of the library
-   */
-  void doLoadLibrary(String shortName);
-
-  /**
-   * A method <code>doLoad</code> that
-   * helps embedders to load a shared library.
-   * <p>
-   *
-   * Embedders would have a chance to take charge of library loading,
-   * they could load libraries with different class loaders,
-   * or load libraries from specified library pathes.
-   *
-   * @param name the file to load.
-   */
-  void doLoad(String name);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXUserTrackAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/IWXUserTrackAdapter.java
deleted file mode 100644
index 915399e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/IWXUserTrackAdapter.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import android.content.Context;
-
-import com.taobao.weex.common.WXPerformance;
-
-import java.io.Serializable;
-import java.util.Map;
-
-/**
- * Interface for commit log info. This interface works as an adapter for various log library.
- */
-public interface IWXUserTrackAdapter {
-
-  String MODULE_NAME = "weex";
-
-  //Performance
-  String LOAD = "load";
-
-  //Alarm
-  String JS_FRAMEWORK = "jsFramework";
-  String JS_DOWNLOAD = "jsDownload";
-  String DOM_MODULE = "domModule";
-  String JS_BRIDGE = "jsBridge";
-  String STREAM_MODULE = "streamModule";
-  String INVOKE_MODULE = "invokeModule";
-  String INIT_FRAMEWORK = "initFramework";
-  String COUNTER = "counter";
-
-  /**
-   * monitor keys
-   */
-  String MONITOR_ERROR_CODE = "errCode";
-  String MONITOR_ARG = "arg";
-  String MONITOR_ERROR_MSG = "errMsg";
-
-  void commit(Context context, String eventId, String type, WXPerformance perf, Map<String, Serializable> params);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/adapter/URIAdapter.java b/android/sdk/src/main/java/com/taobao/weex/adapter/URIAdapter.java
deleted file mode 100644
index cdac2fd..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/adapter/URIAdapter.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import android.net.Uri;
-import android.support.annotation.NonNull;
-
-import com.taobao.weex.WXSDKInstance;
-
-/**
- * Created by sospartan on 15/11/2016.
- */
-
-public interface URIAdapter {
-
-  /**
-   * Stream request url.
-   */
-  String REQUEST = "request";
-
-  /**
-   * URI for image src.
-   */
-  String IMAGE = "image";
-
-  /**
-   * Font file URI for text @font-face .
-   */
-  String FONT = "font";
-
-  /**
-   * Video URI.
-   */
-  String VIDEO = "video";
-
-  /**
-   * URI for a 'href' attribute.
-   */
-  String LINK = "link";
-
-  /**
-   * Bundle URI for Weex instance.
-   */
-  String BUNDLE = "bundle";
-
-  /**
-   * Web page src
-   */
-  String WEB = "web";
-
-  /**
-   * Unknown URIs.
-   */
-  String OTHERS = "others";
-
-  /**
-   *
-   * @param type URI type, see {@link #IMAGE}/{@link #LINK}/{@link #FONT}/{@link #BUNDLE}/{@link #VIDEO}/{@link #OTHERS}
-   * @param uri
-   * @return
-   */
-  @NonNull Uri rewrite(WXSDKInstance instance, String type, Uri uri);
-  @NonNull Uri rewrite(String bundleURL, String type, Uri uri);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/annotation/Component.java b/android/sdk/src/main/java/com/taobao/weex/annotation/Component.java
deleted file mode 100644
index 3f3414c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/annotation/Component.java
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.annotation;
-
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-
-/**
- * Created by sospartan on 6/12/16.
- */
-@Retention(RetentionPolicy.RUNTIME)
-@Target(ElementType.TYPE)
-public @interface Component {
-  boolean lazyload() default true;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/annotation/JSMethod.java b/android/sdk/src/main/java/com/taobao/weex/annotation/JSMethod.java
deleted file mode 100644
index 443dc37..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/annotation/JSMethod.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.annotation;
-
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Inherited;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-
-/**
- * Created by sospartan on 19/10/2016.
- */
-@Retention(RetentionPolicy.RUNTIME)
-@Inherited
-@Target(ElementType.METHOD)
-public @interface JSMethod {
-  boolean uiThread() default true;
-
-  String alias() default NOT_SET;
-
-  String NOT_SET = "_";
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/clipboard/IWXClipboard.java b/android/sdk/src/main/java/com/taobao/weex/appfram/clipboard/IWXClipboard.java
deleted file mode 100644
index ccccd31..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/clipboard/IWXClipboard.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.clipboard;
-
-import android.support.annotation.Nullable;
-
-import com.taobao.weex.bridge.JSCallback;
-
-/**
- * Created by yiyuan.zhangyy(xingjiu) <br/>
- */
-interface IWXClipboard {
-    public void setString(String text);
-    public void getString(@Nullable JSCallback callback);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/clipboard/WXClipboardModule.java b/android/sdk/src/main/java/com/taobao/weex/appfram/clipboard/WXClipboardModule.java
deleted file mode 100644
index 7ded68a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/clipboard/WXClipboardModule.java
+++ /dev/null
@@ -1,148 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.clipboard;
-
-import android.content.ClipData;
-import android.content.ClipboardManager;
-import android.content.Context;
-import android.content.Intent;
-import android.content.res.AssetFileDescriptor;
-import android.net.Uri;
-import android.support.annotation.Nullable;
-
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.io.InputStreamReader;
-import java.util.HashMap;
-import java.util.Map;
-
-
-public class WXClipboardModule extends WXModule implements IWXClipboard {
-
-    private final String CLIP_KEY = "WEEX_CLIP_KEY_MAIN";
-
-    private static final String RESULT = "result";
-    private static final String DATA = "data";
-
-    private static final String RESULT_OK = "success";
-    private static final String RESULT_FAILED = "failed";
-
-    @Override
-    @JSMethod
-    public void setString(String text) {
-        if(null == text) {
-            return;
-        }
-
-        Context context = mWXSDKInstance.getContext();
-        ClipboardManager clipboard = (ClipboardManager) context.getSystemService(context.CLIPBOARD_SERVICE);
-        ClipData clip = ClipData.newPlainText(CLIP_KEY, text);
-        clipboard.setPrimaryClip(clip);
-    }
-
-    @Override
-    @JSMethod
-    public void getString(@Nullable JSCallback callback) {
-        Context context = mWXSDKInstance.getContext();
-        ClipboardManager clipboard = (ClipboardManager) context.getSystemService(Context.CLIPBOARD_SERVICE);
-
-        Map<String, Object> map = new HashMap<>(2);
-        ClipData clip = clipboard.getPrimaryClip();
-        if (clip != null && clip.getItemCount() > 0) {
-            ClipData.Item item = clip.getItemAt(0);
-            CharSequence text = coerceToText(context, item);
-
-            map.put(RESULT, text != null ? RESULT_OK : RESULT_FAILED);
-            map.put(DATA, text != null ? text : "");
-        } else {
-            map.put(RESULT, RESULT_FAILED);
-            map.put(DATA, "");
-        }
-
-        if (null != callback) {
-            callback.invoke(map);
-        }
-    }
-
-    @Nullable
-    private CharSequence coerceToText(Context context, ClipData.Item item) {
-        // Condition 1. just a simple text
-        CharSequence text = item.getText();
-        if (text != null) {
-            return text;
-        }
-
-        // Condition 2. a URI value
-        Uri uri = item.getUri();
-        if (uri != null) {
-            InputStreamReader reader = null;
-            FileInputStream stream = null;
-            try {
-                AssetFileDescriptor assetFileDescriptor = context.getContentResolver().openTypedAssetFileDescriptor(uri, "text/*", null);
-                stream = assetFileDescriptor.createInputStream();
-                reader = new InputStreamReader(stream, "UTF-8");
-
-                StringBuilder builder = new StringBuilder(128);
-                char[] buffer = new char[8192];
-                int len;
-                while ((len = reader.read(buffer)) > 0) {
-                    builder.append(buffer, 0, len);
-                }
-                return builder.toString();
-
-            } catch (FileNotFoundException e) {
-                //  ignore.
-            } catch (IOException e) {
-                WXLogUtils.w("ClippedData Failure loading text.", e);
-            } finally {
-                if (reader != null) {
-                    try {
-                        reader.close();
-                    } catch (IOException e) {
-                        // ignore
-                    }
-                }
-                if (stream != null) {
-                    try {
-                        stream.close();
-                    } catch (IOException e) {
-                        // ignore
-                    }
-                }
-            }
-
-            return uri.toString();
-        }
-
-        // Condition 3.  an intent.
-        Intent intent = item.getIntent();
-        if (intent != null) {
-            return intent.toUri(Intent.URI_INTENT_SCHEME);
-        }
-
-        // else case
-        return null;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/IActivityNavBarSetter.java b/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/IActivityNavBarSetter.java
deleted file mode 100644
index 321991d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/IActivityNavBarSetter.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.navigator;
-
-/**
- *  Define the  NavBarSetter api of the Activity
- */
-public interface IActivityNavBarSetter {
-
-  boolean push(String param);
-
-  boolean pop(String param);
-
-  boolean setNavBarRightItem(String param);
-
-  boolean clearNavBarRightItem(String param);
-
-  boolean setNavBarLeftItem(String param);
-
-  boolean clearNavBarLeftItem(String param);
-
-  boolean setNavBarMoreItem(String param);
-
-  boolean clearNavBarMoreItem(String param);
-
-  boolean setNavBarTitle(String param);
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/INavigator.java b/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/INavigator.java
deleted file mode 100644
index 65c7193..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/INavigator.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.appfram.navigator;
-import android.app.Activity;
-
-/**
- * Created by zhengshihan on 2018/8/9.
- */
-
-public interface INavigator {
-
-  boolean push(Activity activity,String param);
-
-  boolean pop(Activity activity,String param);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/WXNavigatorModule.java b/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/WXNavigatorModule.java
deleted file mode 100644
index 69c253b..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/navigator/WXNavigatorModule.java
+++ /dev/null
@@ -1,365 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.navigator;
-
-import android.app.Activity;
-import android.content.Context;
-import android.content.Intent;
-import android.net.Uri;
-import android.support.v7.app.AppCompatActivity;
-import android.text.TextUtils;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONException;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.utils.WXLogUtils;
-
-
-public class WXNavigatorModule extends WXModule {
-
-    public static final String MSG_SUCCESS = "WX_SUCCESS";
-    public static final String MSG_FAILED = "WX_FAILED";
-    public static final String MSG_PARAM_ERR = "WX_PARAM_ERR";
-
-    public static final String CALLBACK_RESULT = "result";
-    public static final String CALLBACK_MESSAGE = "message";
-
-    private final static String INSTANCE_ID = "instanceId";
-    private final static String TAG = "Navigator";
-    private final static String WEEX = "com.taobao.android.intent.category.WEEX";
-    private final static String URL = "url";
-
-    @JSMethod(uiThread = true)
-    public void open(JSONObject options, JSCallback success, JSCallback failure) {
-        if (options != null) {
-            String url = options.getString(Constants.Value.URL);
-            JSCallback callback = success;
-            JSONObject result = new JSONObject();
-            if (!TextUtils.isEmpty(url)) {
-                Uri rawUri = Uri.parse(url);
-                String scheme = rawUri.getScheme();
-                if (TextUtils.isEmpty(scheme) || Constants.Scheme.HTTP.equalsIgnoreCase(scheme) || Constants.Scheme.HTTPS.equalsIgnoreCase(scheme)) {
-                    this.push(options.toJSONString(), success);
-                } else {
-                    try {
-                        Intent intent = new Intent(Intent.ACTION_VIEW, rawUri);
-                        mWXSDKInstance.getContext().startActivity(intent);
-                        result.put(CALLBACK_RESULT, MSG_SUCCESS);
-                    } catch (Throwable e) {
-                        e.printStackTrace();
-                        result.put(CALLBACK_RESULT, MSG_FAILED);
-                        result.put(CALLBACK_MESSAGE, "Open page failed.");
-                        callback = failure;
-                    }
-                }
-            } else {
-                result.put(CALLBACK_RESULT, MSG_PARAM_ERR);
-                result.put(CALLBACK_MESSAGE, "The URL parameter is empty.");
-                callback = failure;
-            }
-
-            if(callback != null){
-                callback.invoke(result);
-            }
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void close(JSONObject options, JSCallback success, JSCallback failure) {
-        JSONObject result = new JSONObject();
-        JSCallback callback = null;
-        if (mWXSDKInstance.getContext() instanceof Activity) {
-            callback = success;
-            ((Activity) mWXSDKInstance.getContext()).finish();
-        } else {
-            result.put(CALLBACK_RESULT, MSG_FAILED);
-            result.put(CALLBACK_MESSAGE, "Close page failed.");
-            callback = failure;
-        }
-        if (callback != null) {
-            callback.invoke(result);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void push(String param, JSCallback callback) {
-
-        if (!TextUtils.isEmpty(param)) {
-            if (WXSDKEngine.getActivityNavBarSetter() != null) {
-                if (WXSDKEngine.getActivityNavBarSetter().push(param)) {
-                    if (callback != null) {
-                        callback.invoke(MSG_SUCCESS);
-                    }
-                    return;
-                }
-            }
-
-            if (mWXSDKInstance.getContext() instanceof Activity){
-                Activity activity = (Activity)mWXSDKInstance.getContext();
-
-                if (WXSDKEngine.getNavigator()!= null
-                    && WXSDKEngine.getNavigator().push(activity,param)) {
-                    if (callback != null) {
-                        callback.invoke(MSG_SUCCESS);
-                    }
-                    return;
-                }
-            }
-
-            try {
-                JSONObject jsonObject = JSON.parseObject(param);
-                String url = jsonObject.getString(URL);
-                if (!TextUtils.isEmpty(url)) {
-                    Uri rawUri = Uri.parse(url);
-                    String scheme = rawUri.getScheme();
-                    Uri.Builder builder = rawUri.buildUpon();
-                    if (TextUtils.isEmpty(scheme)) {
-                        builder.scheme(Constants.Scheme.HTTP);
-                    }
-                    Intent intent = new Intent(Intent.ACTION_VIEW, builder.build());
-                    intent.addCategory(WEEX);
-                    intent.putExtra(INSTANCE_ID, mWXSDKInstance.getInstanceId());
-                    mWXSDKInstance.getContext().startActivity(intent);
-                    if (callback != null) {
-                        callback.invoke(MSG_SUCCESS);
-                    }
-                }
-            } catch (Exception e) {
-                WXLogUtils.eTag(TAG, e);
-                if (callback != null) {
-                    callback.invoke(MSG_FAILED);
-                }
-            }
-        } else if (callback != null) {
-            callback.invoke(MSG_FAILED);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void pop(String param, JSCallback callback) {
-
-        if (WXSDKEngine.getActivityNavBarSetter() != null) {
-            if (WXSDKEngine.getActivityNavBarSetter().pop(param)) {
-                if (callback != null) {
-                    callback.invoke(MSG_SUCCESS);
-                }
-                return;
-            }
-        }
-
-        if (mWXSDKInstance.getContext() instanceof Activity) {
-            Activity activity = (Activity) mWXSDKInstance.getContext();
-            if (WXSDKEngine.getNavigator() != null) {
-                if (WXSDKEngine.getNavigator().pop(activity, param)) {
-                    if (callback != null) {
-                        callback.invoke(MSG_SUCCESS);
-                    }
-                    return;
-                }
-            }
-
-            if (callback != null) {
-                callback.invoke(MSG_SUCCESS);
-            }
-            ((Activity) mWXSDKInstance.getContext()).finish();
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void setNavBarRightItem(String param, JSCallback callback) {
-        if (!TextUtils.isEmpty(param)) {
-            if (WXSDKEngine.getActivityNavBarSetter() != null) {
-                if (WXSDKEngine.getActivityNavBarSetter().setNavBarRightItem(param)) {
-                    if (callback != null) {
-                        callback.invoke(MSG_SUCCESS);
-                    }
-                    return;
-                }
-            }
-        }
-
-        if (callback != null) {
-            callback.invoke(MSG_FAILED);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void clearNavBarRightItem(String param, JSCallback callback) {
-        if (WXSDKEngine.getActivityNavBarSetter() != null) {
-            if (WXSDKEngine.getActivityNavBarSetter().clearNavBarRightItem(param)) {
-                if (callback != null) {
-                    callback.invoke(MSG_SUCCESS);
-                }
-                return;
-            }
-        }
-        if (callback != null) {
-            callback.invoke(MSG_FAILED);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void setNavBarLeftItem(String param, JSCallback callback) {
-        if (!TextUtils.isEmpty(param)) {
-            if (WXSDKEngine.getActivityNavBarSetter() != null) {
-                if (WXSDKEngine.getActivityNavBarSetter().setNavBarLeftItem(param)) {
-                    if (callback != null) {
-                        callback.invoke(MSG_SUCCESS);
-                    }
-                    return;
-                }
-            }
-        }
-
-        if (callback != null) {
-            callback.invoke(MSG_FAILED);
-        }
-
-    }
-
-    @JSMethod(uiThread = true)
-    public void clearNavBarLeftItem(String param, JSCallback callback) {
-        if (WXSDKEngine.getActivityNavBarSetter() != null) {
-            if (WXSDKEngine.getActivityNavBarSetter().clearNavBarLeftItem(param)) {
-                if (callback != null) {
-                    callback.invoke(MSG_SUCCESS);
-                }
-                return;
-            }
-        }
-
-        if (callback != null) {
-            callback.invoke(MSG_FAILED);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void setNavBarMoreItem(String param, JSCallback callback) {
-        if (!TextUtils.isEmpty(param)) {
-            if (WXSDKEngine.getActivityNavBarSetter() != null) {
-                if (WXSDKEngine.getActivityNavBarSetter().setNavBarMoreItem(param)) {
-                    if (callback != null) {
-                        callback.invoke(MSG_SUCCESS);
-                    }
-                    return;
-                }
-            }
-        }
-
-        if (callback != null) {
-            callback.invoke(MSG_FAILED);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void clearNavBarMoreItem(String param, JSCallback callback) {
-        if (WXSDKEngine.getActivityNavBarSetter() != null) {
-            if (WXSDKEngine.getActivityNavBarSetter().clearNavBarMoreItem(param)) {
-                if (callback != null) {
-                    callback.invoke(MSG_SUCCESS);
-                }
-                return;
-            }
-        }
-
-        if (callback != null) {
-            callback.invoke(MSG_FAILED);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void setNavBarTitle(String param, JSCallback callback) {
-        if (!TextUtils.isEmpty(param)) {
-            if (WXSDKEngine.getActivityNavBarSetter() != null) {
-                if (WXSDKEngine.getActivityNavBarSetter().setNavBarTitle(param)) {
-                    if (callback != null) {
-                        callback.invoke(MSG_SUCCESS);
-                    }
-                    return;
-                }
-            }
-        }
-        if (callback != null) {
-            callback.invoke(MSG_FAILED);
-        }
-    }
-
-    @JSMethod
-    public void setNavBarHidden(String param, final String callback) {
-        String message = MSG_FAILED;
-        try {
-            JSONObject jsObj = JSON.parseObject(param);
-            int visibility = jsObj.getInteger(Constants.Name.NAV_BAR_VISIBILITY);
-            boolean success = changeVisibilityOfActionBar(mWXSDKInstance.getContext(), visibility);
-            if (success) {
-                message = MSG_SUCCESS;
-            }
-        } catch (JSONException e) {
-            WXLogUtils.e(TAG, WXLogUtils.getStackTrace(e));
-        }
-        WXBridgeManager.getInstance().callback(mWXSDKInstance.getInstanceId(), callback, message);
-    }
-
-    private boolean changeVisibilityOfActionBar(Context context, int visibility) {
-        boolean result = false;
-        boolean hasAppCompatActivity = false;
-        try {
-            Class.forName("android.support.v7.app.AppCompatActivity");
-            hasAppCompatActivity = true;
-        } catch (ClassNotFoundException e) {
-            e.printStackTrace();
-        }
-        if (hasAppCompatActivity && mWXSDKInstance.getContext() instanceof AppCompatActivity) {
-            android.support.v7.app.ActionBar actionbar = ((AppCompatActivity) mWXSDKInstance.getContext()).getSupportActionBar();
-            if (actionbar != null) {
-                switch (visibility) {
-                    case Constants.Value.NAV_BAR_HIDDEN:
-                        actionbar.hide();
-                        result = true;
-                        break;
-                    case Constants.Value.NAV_BAR_SHOWN:
-                        actionbar.show();
-                        result = true;
-                        break;
-                }
-            }
-        } else if (mWXSDKInstance.getContext() instanceof Activity) {
-            android.app.ActionBar actionbar = ((Activity) mWXSDKInstance.getContext()).getActionBar();
-            if (actionbar != null) {
-                switch (visibility) {
-                    case Constants.Value.NAV_BAR_HIDDEN:
-                        actionbar.hide();
-                        result = true;
-                        break;
-                    case Constants.Value.NAV_BAR_SHOWN:
-                        actionbar.show();
-                        result = true;
-                        break;
-                }
-            }
-        }
-        return result;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/pickers/DatePickerImpl.java b/android/sdk/src/main/java/com/taobao/weex/appfram/pickers/DatePickerImpl.java
deleted file mode 100644
index 7aca328..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/pickers/DatePickerImpl.java
+++ /dev/null
@@ -1,198 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.pickers;
-
-import android.app.AlertDialog;
-import android.app.DatePickerDialog;
-import android.app.TimePickerDialog;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-import android.widget.Button;
-import android.widget.DatePicker;
-import android.widget.TimePicker;
-
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.text.ParseException;
-import java.text.SimpleDateFormat;
-import java.util.Calendar;
-import java.util.Date;
-import java.util.Locale;
-import java.util.Map;
-
-/**
- * Created by moxun on 16/11/23.
- */
-
-public class DatePickerImpl {
-
-    private static final int DEFAULT_START_YEAR = 1900;
-    private static final int DEFAULT_END_YEAR = 2100;
-
-    private static SimpleDateFormat timeFormatter;
-    private static SimpleDateFormat dateFormatter;
-
-    public static void pickDate(@NonNull Context context, String value, String max, String min, @NonNull final OnPickListener listener, @Nullable Map<String, Object> extras) {
-        Calendar calendar = Calendar.getInstance();
-        calendar.setTime(parseDate(value));
-        final DatePickerDialog dialog = new DatePickerDialog(
-                context,
-                new DatePickerDialog.OnDateSetListener() {
-                    @Override
-                    public void onDateSet(DatePicker view, int year, int monthOfYear, int dayOfMonth) {
-                        int realMonth = monthOfYear + 1;
-                        String realMonthString = realMonth < 10 ? "0" + realMonth : String.valueOf(realMonth);
-                        String realDayString = dayOfMonth < 10 ? "0" + dayOfMonth : String.valueOf(dayOfMonth);
-                        String result = year + "-" + realMonthString + "-" + realDayString;
-                        listener.onPick(true, result);
-                    }
-                },
-                calendar.get(Calendar.YEAR),
-                calendar.get(Calendar.MONTH),
-                calendar.get(Calendar.DAY_OF_MONTH)
-        );
-
-        final DatePicker datePicker = dialog.getDatePicker();
-
-        final Calendar defaultMinDate = Calendar.getInstance(Locale.getDefault());
-        final Calendar defaultMaxDate = Calendar.getInstance(Locale.getDefault());
-
-        defaultMinDate.set(DEFAULT_START_YEAR, Calendar.JANUARY, 1);
-        defaultMaxDate.set(DEFAULT_END_YEAR, Calendar.DECEMBER, 31);
-
-        if (!TextUtils.isEmpty(min)) {
-            long minDate = parseDate(min).getTime();
-            if (datePicker.getMaxDate() >= minDate) {
-                datePicker.setMinDate(parseDate(min).getTime());
-            } else {
-                datePicker.setMinDate(defaultMinDate.getTimeInMillis());
-                datePicker.setMaxDate(defaultMaxDate.getTimeInMillis());
-            }
-        }
-        if (!TextUtils.isEmpty(max)) {
-            long maxDate = parseDate(max).getTime();
-            if (datePicker.getMinDate() <= maxDate) {
-                datePicker.setMaxDate(parseDate(max).getTime());
-            } else {
-                datePicker.setMinDate(defaultMinDate.getTimeInMillis());
-                datePicker.setMaxDate(defaultMaxDate.getTimeInMillis());
-            }
-        }
-
-        dialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
-            @Override
-            public void onCancel(DialogInterface dialog) {
-                listener.onPick(false, null);
-            }
-        });
-
-        setButtonText(dialog, DialogInterface.BUTTON_NEGATIVE, String.valueOf(extras != null ? extras.get("cancelTitle") : null));
-        setButtonText(dialog, DialogInterface.BUTTON_POSITIVE, String.valueOf(extras != null ? extras.get("confirmTitle") : null));
-
-        dialog.show();
-    }
-
-    public static void pickTime(@NonNull Context context, String value, @NonNull final OnPickListener listener, @Nullable Map<String, Object> extras) {
-        Calendar calendar = Calendar.getInstance();
-        calendar.setTime(parseTime(value));
-        TimePickerDialog dialog = new TimePickerDialog(
-                context,
-                new TimePickerDialog.OnTimeSetListener() {
-                    @Override
-                    public void onTimeSet(TimePicker view, int hourOfDay, int minute) {
-                        String h = hourOfDay < 10 ? "0" + hourOfDay : String.valueOf(hourOfDay);
-                        String m = minute < 10 ? "0" + minute : String.valueOf(minute);
-                        String result = h + ":" + m;
-                        listener.onPick(true, result);
-                    }
-                },
-                calendar.get(Calendar.HOUR_OF_DAY),
-                calendar.get(Calendar.MINUTE),
-                false
-        );
-
-        dialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
-            @Override
-            public void onCancel(DialogInterface dialog) {
-                listener.onPick(false, null);
-            }
-        });
-
-        setButtonText(dialog, DialogInterface.BUTTON_NEGATIVE, String.valueOf(extras != null ? extras.get("cancelTitle") : null));
-        setButtonText(dialog, DialogInterface.BUTTON_POSITIVE, String.valueOf(extras != null ? extras.get("confirmTitle") : null));
-
-        dialog.show();
-    }
-
-    public interface OnPickListener {
-        void onPick(boolean set, @Nullable String result);
-    }
-
-    private static Date parseDate(String s) {
-        if (dateFormatter == null) {
-            dateFormatter = new SimpleDateFormat("yyyy-MM-dd", Locale.getDefault());
-        }
-
-        try {
-            return dateFormatter.parse(s);
-        } catch (ParseException e) {
-            //don't worry
-            WXLogUtils.w("[DatePickerImpl] " + e.toString());
-        }
-        return new Date();
-    }
-
-    private static Date parseTime(String s) {
-        if (timeFormatter == null) {
-            timeFormatter = new SimpleDateFormat("HH:mm", Locale.getDefault());
-        }
-
-        try {
-            return timeFormatter.parse(s);
-        } catch (ParseException e) {
-            //don't worry
-            WXLogUtils.w("[DatePickerImpl] " + e.toString());
-        }
-        return new Date();
-    }
-
-    private static void setButtonText(final AlertDialog dialog, final int which, final CharSequence text) {
-        if (TextUtils.isEmpty(text) || "null".equals(text)) {
-            return;
-        }
-        try {
-            dialog.getWindow().getDecorView().post(WXThread.secure(new Runnable() {
-                @Override
-                public void run() {
-                    Button button = dialog.getButton(which);
-                    if (button != null) {
-                        button.setAllCaps(false);
-                        button.setText(text);
-                    }
-                }
-            }));
-        } catch (Throwable t) {
-            t.printStackTrace();
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/pickers/WXPickersModule.java b/android/sdk/src/main/java/com/taobao/weex/appfram/pickers/WXPickersModule.java
deleted file mode 100644
index ef46f8f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/pickers/WXPickersModule.java
+++ /dev/null
@@ -1,310 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.pickers;
-
-import android.content.Context;
-import android.content.DialogInterface;
-import android.graphics.Color;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v7.app.AlertDialog;
-import android.util.TypedValue;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.AdapterView;
-import android.widget.ArrayAdapter;
-import android.widget.Button;
-import android.widget.Checkable;
-import android.widget.ListView;
-import android.widget.TextView;
-
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Created by moxun on 16/10/27.
- */
-
-public class WXPickersModule extends WXModule {
-
-    private static final String SUCCESS = "success";
-    private static final String CANCEL = "cancel";
-    private static final String ERROR = "error";
-
-    private static final String RESULT = "result";
-    private static final String DATA = "data";
-
-    private static final String KEY_VALUE = "value";
-    private static final String KEY_INDEX = "index";
-    private static final String KEY_TITLE = "title";
-    private static final String KEY_MAX = "max";
-    private static final String KEY_MIN = "min";
-    private static final String KEY_ITEMS = "items";
-
-    private static final String KEY_TITLE_COLOR = "titleColor";
-    private static final String KEY_CANCEL_TITLE_COLOR = "cancelTitleColor";
-    private static final String KEY_CONFIRM_TITLE = "confirmTitle";
-    private static final String KEY_CANCEL_TITLE = "cancelTitle";
-    private static final String KEY_CONFIRM_TITLE_COLOR = "confirmTitleColor";
-    private static final String KEY_TITLE_BACKGROUND_COLOR = "titleBackgroundColor";
-    private static final String KEY_TEXT_COLOR = "textColor";
-    private static final String KEY_SELECTION_COLOR = "selectionColor";
-
-    private int selected;
-
-    @JSMethod
-    public void pick(Map<String, Object> options, JSCallback callback) {
-        List<String> items = safeConvert(getOption(options, KEY_ITEMS, new ArrayList<String>()));
-        try {
-            performSinglePick(items, options, callback);
-        } catch (Throwable throwable) {
-            throwable.printStackTrace();
-        }
-    }
-
-    @JSMethod
-    public void pickDate(Map<String, Object> options, JSCallback callback) {
-        performPickDate(options, callback);
-    }
-
-    @JSMethod
-    public void pickTime(Map<String, Object> options, JSCallback callback) {
-        performPickTime(options, callback);
-    }
-
-    private List<String> safeConvert(List src) {
-        List<String> result = new ArrayList<>(src.size());
-        for (Object obj : src) {
-            result.add(String.valueOf(obj));
-        }
-        return result;
-    }
-
-    private <T> T getOption(Map<String, Object> options, String key, T defValue) {
-        Object value = options.get(key);
-        if (value == null) {
-            return defValue;
-        } else {
-            try {
-                return (T) value;
-            } catch (Exception e) {
-                e.printStackTrace();
-                return defValue;
-            }
-        }
-    }
-
-    private int getColor(Map<String, Object> options, String key, int defValue) {
-        Object value = getOption(options, key, null);
-        if (value == null) {
-            return defValue;
-        }
-        return WXResourceUtils.getColor(value.toString(), defValue);
-    }
-
-    private void performPickTime(Map<String, Object> options, final JSCallback callback) {
-        String value = getOption(options, KEY_VALUE, "");
-        DatePickerImpl.pickTime(
-                mWXSDKInstance.getContext(),
-                value,
-                new DatePickerImpl.OnPickListener() {
-                    @Override
-                    public void onPick(boolean set, @Nullable String result) {
-                        if (set) {
-                            Map<String, Object> ret = new HashMap<>(2);
-                            ret.put(RESULT, SUCCESS);
-                            ret.put(DATA, result);
-                            callback.invoke(ret);
-                        } else {
-                            Map<String, Object> ret = new HashMap<>(2);
-                            ret.put(RESULT, CANCEL);
-                            ret.put(DATA, null);
-                            callback.invoke(ret);
-                        }
-                    }
-                },
-                options);
-    }
-
-    private void performPickDate(Map<String, Object> options, final JSCallback callback) {
-        String value = getOption(options, KEY_VALUE, "");
-        String max = getOption(options, KEY_MAX, "");
-        String min = getOption(options, KEY_MIN, "");
-        DatePickerImpl.pickDate(
-                mWXSDKInstance.getContext(),
-                value,
-                max,
-                min,
-                new DatePickerImpl.OnPickListener() {
-                    @Override
-                    public void onPick(boolean set, @Nullable String result) {
-                        if (set) {
-                            Map<String, Object> ret = new HashMap<>(2);
-                            ret.put(RESULT, SUCCESS);
-                            ret.put(DATA, result);
-                            callback.invoke(ret);
-                        } else {
-                            Map<String, Object> ret = new HashMap<>(2);
-                            ret.put(RESULT, CANCEL);
-                            ret.put(DATA, null);
-                            callback.invoke(ret);
-                        }
-                    }
-                },
-                options);
-
-    }
-
-    private void performSinglePick(final List<String> items, final Map<String, Object> options, final JSCallback callback) {
-        selected = getOption(options, KEY_INDEX, 0);
-        final int textColor = getColor(options, KEY_TEXT_COLOR, Color.TRANSPARENT);
-        final int selectionColor = getColor(options, KEY_SELECTION_COLOR, Color.TRANSPARENT);
-        final ArrayAdapter adapter = new ArrayAdapter<String>(
-            mWXSDKInstance.getContext(),
-            android.R.layout.simple_list_item_single_choice,
-            items) {
-            @NonNull
-            @Override
-            public View getView(int position, View convertView, @Nullable ViewGroup parent) {
-                View itemView =  super.getView(position, convertView, parent);
-
-                if (itemView != null && itemView instanceof Checkable) {
-                    boolean needSelected = position == selected;
-                    ((Checkable) itemView).setChecked(needSelected);
-
-                    if (needSelected) {
-                        itemView.setBackgroundColor(selectionColor);
-                    } else {
-                        itemView.setBackgroundColor(Color.TRANSPARENT);
-                    }
-                }
-
-                if (itemView instanceof TextView && textColor != Color.TRANSPARENT) {
-                    ((TextView) itemView).setTextColor(textColor);
-                }
-
-                return itemView;
-            }
-        };
-        final AlertDialog dialog =  new AlertDialog.Builder(mWXSDKInstance.getContext())
-                .setAdapter(adapter, null)
-                .setPositiveButton(android.R.string.ok, new DialogInterface.OnClickListener() {
-                    @Override
-                    public void onClick(DialogInterface dialog, int which) {
-                        //which == -1
-                        Map<String, Object> ret = new HashMap<>(2);
-                        ret.put(RESULT, SUCCESS);
-                        ret.put(DATA, selected);
-                        callback.invoke(ret);
-                    }
-                })
-                .setNegativeButton(android.R.string.cancel, new DialogInterface.OnClickListener() {
-                    @Override
-                    public void onClick(DialogInterface dialog, int which) {
-                        //which == -2
-                        Map<String, Object> ret = new HashMap<>(2);
-                        ret.put(RESULT, CANCEL);
-                        ret.put(DATA, -1);
-                        callback.invoke(ret);
-                    }
-                })
-                .setCustomTitle(makeTitleView(mWXSDKInstance.getContext(), options))
-                .create();
-
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            //pre create the content view on dialog.
-            //if not , the content view will not be created until dialog.show() called
-            dialog.create();
-        }
-
-        final ListView listView = dialog.getListView();
-        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
-            @Override
-            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
-                selected = position;
-                adapter.notifyDataSetChanged();
-            }
-        });
-
-        dialog.getWindow().getDecorView().post(WXThread.secure(new Runnable() {
-            @Override
-            public void run() {
-                Button confirm = dialog.getButton(DialogInterface.BUTTON_POSITIVE);
-                Button cancel = dialog.getButton(DialogInterface.BUTTON_NEGATIVE);
-
-                if (confirm != null) {
-                    String confirmTitle = getOption(options, KEY_CONFIRM_TITLE, null);
-                    int confirmColor = getColor(options, KEY_CONFIRM_TITLE_COLOR, Color.TRANSPARENT);
-
-                    if (confirmTitle != null) {
-                        confirm.setText(confirmTitle);
-                        confirm.setAllCaps(false);
-                    }
-
-                    if (confirmColor != Color.TRANSPARENT) {
-                        confirm.setTextColor(confirmColor);
-                        confirm.setAllCaps(false);
-                    }
-                }
-
-                if (cancel != null) {
-                    String cancelTitle = getOption(options, KEY_CANCEL_TITLE, null);
-                    int cancelColor = getColor(options, KEY_CANCEL_TITLE_COLOR, Color.TRANSPARENT);
-
-                    if (cancelTitle != null) {
-                        cancel.setText(cancelTitle);
-                    }
-
-                    if (cancelColor != Color.TRANSPARENT) {
-                        cancel.setTextColor(cancelColor);
-                    }
-                }
-            }
-        }));
-
-        dialog.show();
-    }
-
-    private TextView makeTitleView(Context context, Map<String, Object> options) {
-        String text = getOption(options, KEY_TITLE, null);
-        if (text == null) {
-            return null;
-        }
-        TextView textView = new TextView(context);
-        textView.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT));
-        textView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 20);
-        int padding = WXViewUtils.dip2px(12);
-        textView.setPadding(padding, padding, padding, padding);
-        textView.getPaint().setFakeBoldText(true);
-        textView.setBackgroundColor(getColor(options, KEY_TITLE_BACKGROUND_COLOR, Color.TRANSPARENT));
-        textView.setTextColor(getColor(options, KEY_TITLE_COLOR, Color.BLACK));
-        textView.setText(text);
-        return textView;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/DefaultWXStorage.java b/android/sdk/src/main/java/com/taobao/weex/appfram/storage/DefaultWXStorage.java
deleted file mode 100644
index 9bcc75e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/DefaultWXStorage.java
+++ /dev/null
@@ -1,335 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.storage;
-
-import android.content.ContentValues;
-import android.content.Context;
-import android.database.Cursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.database.sqlite.SQLiteFullException;
-import android.database.sqlite.SQLiteStatement;
-import android.support.annotation.Nullable;
-
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.ArrayList;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-
-public class DefaultWXStorage implements IWXStorageAdapter {
-
-    private WXSQLiteOpenHelper mDatabaseSupplier;
-
-    private ExecutorService mExecutorService;
-
-    private void execute(@Nullable final Runnable runnable) {
-        if (mExecutorService == null) {
-            mExecutorService = Executors.newSingleThreadExecutor();
-        }
-
-        if(runnable != null && !mExecutorService.isShutdown() && !mExecutorService.isTerminated()) {
-            mExecutorService.execute(WXThread.secure(runnable));
-        }
-    }
-
-    public DefaultWXStorage(Context context) {
-        this.mDatabaseSupplier = new WXSQLiteOpenHelper(context);
-    }
-
-
-    @Override
-    public void setItem(final String key, final String value, final OnResultReceivedListener listener) {
-        execute(new Runnable() {
-            @Override
-            public void run() {
-                Map<String, Object> data = StorageResultHandler.setItemResult(performSetItem(key, value, false, true));
-                if (listener == null) {
-                    return;
-                }
-                listener.onReceived(data);
-            }
-        });
-    }
-
-    @Override
-    public void getItem(final String key, final OnResultReceivedListener listener) {
-        execute(new Runnable() {
-            @Override
-            public void run() {
-                Map<String, Object> data = StorageResultHandler.getItemResult(performGetItem(key));
-                if (listener == null) {
-                    return;
-                }
-                listener.onReceived(data);
-            }
-        });
-    }
-
-    @Override
-    public void removeItem(final String key, final OnResultReceivedListener listener) {
-        execute(new Runnable() {
-            @Override
-            public void run() {
-                Map<String, Object> data = StorageResultHandler.removeItemResult(performRemoveItem(key));
-                if (listener == null) {
-                    return;
-                }
-                listener.onReceived(data);
-            }
-        });
-    }
-
-    @Override
-    public void length(final OnResultReceivedListener listener) {
-        execute(new Runnable() {
-            @Override
-            public void run() {
-                Map<String, Object> data = StorageResultHandler.getLengthResult(performGetLength());
-                if (listener == null) {
-                    return;
-                }
-                listener.onReceived(data);
-            }
-        });
-    }
-
-    @Override
-    public void getAllKeys(final OnResultReceivedListener listener) {
-        execute(new Runnable() {
-            @Override
-            public void run() {
-                Map<String, Object> data = StorageResultHandler.getAllkeysResult(performGetAllKeys());
-                if (listener == null) {
-                    return;
-                }
-                listener.onReceived(data);
-            }
-        });
-    }
-
-    @Override
-    public void setItemPersistent(final String key, final String value, final OnResultReceivedListener listener) {
-        execute(new Runnable() {
-            @Override
-            public void run() {
-                Map<String, Object> data = StorageResultHandler.setItemResult(performSetItem(key, value, true, true));
-                if (listener == null) {
-                    return;
-                }
-                listener.onReceived(data);
-            }
-        });
-    }
-
-    @Override
-    public void close() {
-        final ExecutorService needCloseService = mExecutorService;
-        execute(new Runnable() {
-            @Override
-            public void run() {
-                try {
-                    mDatabaseSupplier.closeDatabase();
-                    if (needCloseService != null) {
-                        needCloseService.shutdown();
-                    }
-                } catch (Exception e) {
-                    WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, e.getMessage());
-                }
-            }
-        });
-        mExecutorService = null;
-    }
-
-    private boolean performSetItem(String key, String value, boolean isPersistent, boolean allowRetryWhenFull) {
-        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
-        if (database == null) {
-            return false;
-        }
-
-        WXLogUtils.d(WXSQLiteOpenHelper.TAG_STORAGE, "set k-v to storage(key:" + key + ",value:" + value + ",isPersistent:" + isPersistent + ",allowRetry:" + allowRetryWhenFull + ")");
-        String sql = "INSERT OR REPLACE INTO " + WXSQLiteOpenHelper.TABLE_STORAGE + " VALUES (?,?,?,?);";
-        SQLiteStatement statement = null;
-        String timeStamp = WXSQLiteOpenHelper.sDateFormatter.format(new Date());
-        try {
-            statement = database.compileStatement(sql);
-            statement.clearBindings();
-            statement.bindString(1, key);
-            statement.bindString(2, value);
-            statement.bindString(3, timeStamp);
-            statement.bindLong(4, isPersistent ? 1 : 0);
-            statement.execute();
-            return true;
-        } catch (Exception e) {
-            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute setItem :" + e.getMessage());
-            if (e instanceof SQLiteFullException) {
-                if (allowRetryWhenFull && trimToSize()) {
-                    //try again
-                    //setItem/setItemPersistent method only allow try once when occurred a sqliteFullException.
-                    WXLogUtils.d(WXSQLiteOpenHelper.TAG_STORAGE, "retry set k-v to storage(key:" + key + ",value:" + value + ")");
-                    return performSetItem(key, value, isPersistent, false);
-                }
-            }
-
-            return false;
-        } finally {
-            if(statement != null) {
-                statement.close();
-            }
-        }
-    }
-
-    /**
-     * remove 10% of total record(at most) ordered by timestamp.
-     * */
-    private boolean trimToSize() {
-        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
-        if (database == null) {
-            return false;
-        }
-
-        List<String> toEvict = new ArrayList<>();
-        int num = 0;
-
-        Cursor c = database.query(WXSQLiteOpenHelper.TABLE_STORAGE, new String[]{WXSQLiteOpenHelper.COLUMN_KEY, WXSQLiteOpenHelper.COLUMN_PERSISTENT}, null, null, null, null, WXSQLiteOpenHelper.COLUMN_TIMESTAMP + " ASC");
-        try {
-            int evictSize = c.getCount() / 10;
-            while (c.moveToNext()) {
-                String key = c.getString(c.getColumnIndex(WXSQLiteOpenHelper.COLUMN_KEY));
-                boolean persistent = c.getInt(c.getColumnIndex(WXSQLiteOpenHelper.COLUMN_PERSISTENT)) == 1;
-                if (!persistent && key != null) {
-                    num++;
-                    toEvict.add(key);
-                    if (num == evictSize) {
-                        break;
-                    }
-                }
-            }
-        } catch (Exception e) {
-            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute trimToSize:" + e.getMessage());
-        } finally {
-            c.close();
-        }
-
-        if (num <= 0) {
-            return false;
-        }
-
-        for (String key : toEvict) {
-            performRemoveItem(key);
-        }
-        WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "remove " + num + " items by lru");
-        return true;
-    }
-
-    private String performGetItem(String key) {
-        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
-        if (database == null) {
-            return null;
-        }
-
-        Cursor c = database.query(WXSQLiteOpenHelper.TABLE_STORAGE,
-                new String[]{WXSQLiteOpenHelper.COLUMN_VALUE},
-                WXSQLiteOpenHelper.COLUMN_KEY + "=?",
-                new String[]{key},
-                null, null, null);
-        try {
-            if (c.moveToNext()) {
-                ContentValues values = new ContentValues();
-                //update timestamp
-                values.put(WXSQLiteOpenHelper.COLUMN_TIMESTAMP, WXSQLiteOpenHelper.sDateFormatter.format(new Date()));
-                int updateResult = mDatabaseSupplier.getDatabase().update(WXSQLiteOpenHelper.TABLE_STORAGE, values, WXSQLiteOpenHelper.COLUMN_KEY + "= ?", new String[]{key});
-
-                WXLogUtils.d(WXSQLiteOpenHelper.TAG_STORAGE, "update timestamp " + (updateResult == 1 ? "success" : "failed") + " for operation [getItem(key = " + key + ")]");
-                return c.getString(c.getColumnIndex(WXSQLiteOpenHelper.COLUMN_VALUE));
-            } else {
-                return null;
-            }
-        } catch (Exception e) {
-            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute getItem:" + e.getMessage());
-            return null;
-        } finally {
-            c.close();
-        }
-    }
-
-    private boolean performRemoveItem(String key) {
-        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
-        if (database == null) {
-            return false;
-        }
-
-        int count = 0;
-        try {
-            count = database.delete(WXSQLiteOpenHelper.TABLE_STORAGE,
-                    WXSQLiteOpenHelper.COLUMN_KEY + "=?",
-                    new String[]{key});
-        } catch (Exception e) {
-            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute removeItem:" + e.getMessage());
-            return false;
-        }
-        return count == 1;
-    }
-
-    private long performGetLength() {
-        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
-        if (database == null) {
-            return 0;
-        }
-
-        String sql = "SELECT count(" + WXSQLiteOpenHelper.COLUMN_KEY + ") FROM " + WXSQLiteOpenHelper.TABLE_STORAGE;
-        SQLiteStatement statement = null;
-        try {
-            statement = database.compileStatement(sql);
-            return statement.simpleQueryForLong();
-        } catch (Exception e) {
-            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute getLength:" + e.getMessage());
-            return 0;
-        } finally {
-            if(statement != null) {
-                statement.close();
-            }
-        }
-    }
-
-    private List<String> performGetAllKeys() {
-        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
-        if (database == null) {
-            return null;
-        }
-
-        List<String> result = new ArrayList<>();
-        Cursor c = database.query(WXSQLiteOpenHelper.TABLE_STORAGE, new String[]{WXSQLiteOpenHelper.COLUMN_KEY}, null, null, null, null, null);
-        try {
-            while (c.moveToNext()) {
-                result.add(c.getString(c.getColumnIndex(WXSQLiteOpenHelper.COLUMN_KEY)));
-            }
-            return result;
-        } catch (Exception e) {
-            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute getAllKeys:" + e.getMessage());
-            return result;
-        } finally {
-            c.close();
-        }
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/IWXStorage.java b/android/sdk/src/main/java/com/taobao/weex/appfram/storage/IWXStorage.java
deleted file mode 100644
index c869d53..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/IWXStorage.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.storage;
-
-import android.support.annotation.Nullable;
-
-import com.taobao.weex.bridge.JSCallback;
-
-interface IWXStorage {
-    public void setItem(String key, String value,@Nullable JSCallback callback);
-    public void getItem(String key,@Nullable JSCallback callback);
-    public void removeItem(String key,@Nullable JSCallback callback);
-    public void length(@Nullable JSCallback callback);
-    public void getAllKeys(@Nullable JSCallback callback);
-    public void setItemPersistent(String key, String value, @Nullable JSCallback callback);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/IWXStorageAdapter.java b/android/sdk/src/main/java/com/taobao/weex/appfram/storage/IWXStorageAdapter.java
deleted file mode 100644
index c04512c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/IWXStorageAdapter.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.storage;
-
-import java.util.Map;
-
-/**
- * interface for {@link WXStorageModule} class.
- * this interface works as an adapter for different storage strategy.
- * the default is use {@link android.database.sqlite.SQLiteDatabase} to store k-v pairs.
- * You can call {@link com.taobao.weex.InitConfig.Builder#setStorageAdapter(IWXStorageAdapter)} to inject your own
- * storage implementation.
- * */
-public interface IWXStorageAdapter {
-    void setItem(String key, String value,OnResultReceivedListener listener);
-
-    void getItem(String key,OnResultReceivedListener listener);
-
-    void removeItem(String key,OnResultReceivedListener listener);
-
-    void length(OnResultReceivedListener listener);
-
-    void getAllKeys(OnResultReceivedListener listener);
-
-    void setItemPersistent(String key, String value, OnResultReceivedListener listener);
-
-    void close();
-
-    /**
-     * the callback of storage operation.
-     * */
-    interface OnResultReceivedListener {
-        void onReceived(Map<String,Object> data);
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/StorageResultHandler.java b/android/sdk/src/main/java/com/taobao/weex/appfram/storage/StorageResultHandler.java
deleted file mode 100644
index f8be207..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/StorageResultHandler.java
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.storage;
-
-import android.support.annotation.Nullable;
-
-import com.taobao.weex.bridge.JSCallback;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-public class StorageResultHandler {
-
-    private StorageResultHandler() {
-    }
-
-    private static final String RESULT = "result";
-    private static final String DATA = "data";
-
-
-    private static final String UNDEFINED = "undefined";
-    private static final String RESULT_FAILED_NO_HANDLER = "no_handler";
-    private static final String RESULT_FAILED_INVALID_PARAM = "invalid_param";
-
-
-    private static final String RESULT_OK = "success";
-    private static final String RESULT_FAILED = "failed";
-
-
-    public static Map<String, Object> getItemResult(String result) {
-        Map<String, Object> map = new HashMap<>(4);
-        map.put(RESULT, result != null ? RESULT_OK : RESULT_FAILED);
-        map.put(DATA, result != null ? result : UNDEFINED);
-        return map;
-    }
-
-    public static Map<String, Object> setItemResult(boolean result) {
-        Map<String, Object> map = new HashMap<>(4);
-        map.put(RESULT, result ? RESULT_OK : RESULT_FAILED);
-        map.put(DATA, UNDEFINED);
-        return map;
-    }
-
-
-    public static Map<String, Object> removeItemResult(boolean result) {
-        Map<String, Object> map = new HashMap<>(4);
-        map.put(RESULT, result ? RESULT_OK : RESULT_FAILED);
-        map.put(DATA, UNDEFINED);
-        return map;
-    }
-
-    public static Map<String, Object> getLengthResult(long result) {
-        Map<String, Object> map = new HashMap<>(4);
-        map.put(RESULT, RESULT_OK);
-        map.put(DATA, result);
-        return map;
-    }
-
-    public static Map<String, Object> getAllkeysResult(List<String> result) {
-        if (result == null) {
-            result = new ArrayList<>(1);
-        }
-        Map<String, Object> map = new HashMap<>(4);
-        map.put(RESULT, RESULT_OK);
-        map.put(DATA, result);
-        return map;
-    }
-
-
-    private static void handleResult(@Nullable JSCallback callback, String result, Object data) {
-        if (callback == null) {
-            return;
-        }
-        Map<String, Object> retVal = new HashMap<>(4);
-        retVal.put(RESULT, result);
-        retVal.put(DATA, data);
-        callback.invoke(retVal);
-    }
-
-    public static void handleNoHandlerError(@Nullable JSCallback callback) {
-        handleResult(callback, RESULT_FAILED, RESULT_FAILED_NO_HANDLER);
-    }
-
-    public static void handleInvalidParam(@Nullable JSCallback callback) {
-        handleResult(callback, RESULT_FAILED, RESULT_FAILED_INVALID_PARAM);
-    }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/WXSQLiteOpenHelper.java b/android/sdk/src/main/java/com/taobao/weex/appfram/storage/WXSQLiteOpenHelper.java
deleted file mode 100644
index 4477030..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/WXSQLiteOpenHelper.java
+++ /dev/null
@@ -1,226 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.storage;
-
-import android.content.Context;
-import android.database.Cursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.database.sqlite.SQLiteException;
-import android.database.sqlite.SQLiteOpenHelper;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.text.SimpleDateFormat;
-import java.util.Date;
-import java.util.Locale;
-
-public class WXSQLiteOpenHelper extends SQLiteOpenHelper {
-
-    private static final String DATABASE_NAME = "WXStorage";
-    private static final int DATABASE_VERSION = 2;
-    static final String TAG_STORAGE = "weex_storage";
-
-    private long mMaximumDatabaseSize = 5 * 10 * 1024 * 1024L;//50mb
-    static SimpleDateFormat sDateFormatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss", Locale.getDefault());
-    private Context mContext;
-    private SQLiteDatabase mDb;
-
-
-    static final String TABLE_STORAGE = "default_wx_storage";
-    static final String COLUMN_KEY = "key";
-    static final String COLUMN_VALUE = "value";
-    static final String COLUMN_TIMESTAMP = "timestamp";
-    static final String COLUMN_PERSISTENT = "persistent";
-
-    private static final int SLEEP_TIME_MS = 30;
-
-    private static final String STATEMENT_CREATE_TABLE = "CREATE TABLE IF NOT EXISTS " + TABLE_STORAGE + " ("
-            + COLUMN_KEY
-            + " TEXT PRIMARY KEY,"
-            + COLUMN_VALUE
-            + " TEXT NOT NULL,"
-            + COLUMN_TIMESTAMP
-            + " TEXT NOT NULL,"
-            + COLUMN_PERSISTENT
-            + " INTEGER DEFAULT 0"
-            + ")";
-
-
-    public WXSQLiteOpenHelper(Context context) {
-        super(context, DATABASE_NAME, null, DATABASE_VERSION);
-        this.mContext = context;
-    }
-
-    /**
-     * retrieve sqlite database
-     *
-     * @return a {@link SQLiteDatabase} instance or null if retrieve fails.
-     * */
-    public @Nullable SQLiteDatabase getDatabase() {
-        ensureDatabase();
-        return mDb;
-    }
-
-    @Override
-    public void onCreate(SQLiteDatabase db) {
-        db.execSQL(STATEMENT_CREATE_TABLE);
-    }
-
-
-    /**
-     * version 1:
-     *
-     *   ----------------
-     *   | key | value |
-     *   ---------------
-     *
-     * version 2:
-     *
-     *  ----------------------------------------
-     *  | key | value | timestamp | persistent |
-     *  ----------------------------------------
-     **/
-    @Override
-    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
-        if (oldVersion != newVersion) {
-            if(newVersion == 2 && oldVersion == 1){
-                WXLogUtils.d(TAG_STORAGE,"storage is updating from version "+oldVersion+" to version "+newVersion);
-                boolean updateResult = true;
-                try {
-                    long start = System.currentTimeMillis();
-
-                    db.beginTransaction();
-                    // update table structure
-                    String SQL_ADD_COLUMN_TIMESTAMP = "ALTER TABLE "+TABLE_STORAGE+" ADD COLUMN "+COLUMN_TIMESTAMP+" TEXT;";
-                    WXLogUtils.d(TAG_STORAGE,"exec sql : "+ SQL_ADD_COLUMN_TIMESTAMP);
-                    db.execSQL(SQL_ADD_COLUMN_TIMESTAMP);
-
-                    String SQL_ADD_COLUMN_PERSISTENT = "ALTER TABLE "+TABLE_STORAGE+" ADD COLUMN "+COLUMN_PERSISTENT+" INTEGER;";
-                    WXLogUtils.d(TAG_STORAGE,"exec sql : "+ SQL_ADD_COLUMN_PERSISTENT);
-                    db.execSQL(SQL_ADD_COLUMN_PERSISTENT);
-
-                    // update timestamp & persistent
-                    String SQL_UPDATE_TABLE = "UPDATE "+TABLE_STORAGE+" SET "+ COLUMN_TIMESTAMP+" = '"+sDateFormatter.format(new Date())+"' , "+ COLUMN_PERSISTENT +" = 0";
-                    WXLogUtils.d(TAG_STORAGE,"exec sql : "+ SQL_UPDATE_TABLE);
-                    db.execSQL(SQL_UPDATE_TABLE);
-
-                    db.setTransactionSuccessful();
-                    long time = System.currentTimeMillis() - start;
-                    WXLogUtils.d(TAG_STORAGE,"storage updated success ("+time+"ms)");
-                }catch (Exception e){
-                    WXLogUtils.d(TAG_STORAGE,"storage updated failed from version "+oldVersion+" to version "+newVersion+","+e.getMessage());
-                    updateResult = false;
-                }finally {
-                    db.endTransaction();
-                }
-                //rollback
-                if(!updateResult){
-                    WXLogUtils.d(TAG_STORAGE,"storage is rollback,all data will be removed");
-                    deleteDB();
-                    onCreate(db);
-                }
-            }else{
-                deleteDB();
-                onCreate(db);
-            }
-        }
-    }
-
-
-
-    synchronized void ensureDatabase() {
-        if (mDb != null && mDb.isOpen()) {
-            return;
-        }
-
-        try {
-            // Sometimes retrieving the database fails. We do 2 retries: first without database deletion
-            // and then with deletion.
-            for (int tries = 0; tries < 2; tries++) {
-                try {
-                    if (tries > 0) {
-                        //delete db and recreate
-                        deleteDB();
-                    }
-                    mDb = getWritableDatabase();
-                    break;
-                } catch (SQLiteException e) {
-                    e.printStackTrace();
-                }
-                // Wait before retrying.
-                try {
-                    Thread.sleep(SLEEP_TIME_MS);
-                } catch (InterruptedException ie) {
-                    Thread.currentThread().interrupt();
-                }
-            }
-            if(mDb == null){
-                return;
-            }
-
-            createTableIfNotExists(mDb);
-
-            mDb.setMaximumSize(mMaximumDatabaseSize);
-        } catch (Throwable e) {
-            mDb = null;
-            WXLogUtils.d(TAG_STORAGE,"ensureDatabase failed, throwable = " + e.getMessage());
-        }
-
-    }
-
-    public synchronized void setMaximumSize(long size) {
-        mMaximumDatabaseSize = size;
-        if (mDb != null) {
-            mDb.setMaximumSize(mMaximumDatabaseSize);
-        }
-    }
-
-    private boolean deleteDB() {
-        closeDatabase();
-        return mContext.deleteDatabase(DATABASE_NAME);
-    }
-
-    public synchronized void closeDatabase() {
-        if (mDb != null && mDb.isOpen()) {
-            mDb.close();
-            mDb = null;
-        }
-    }
-
-    private void createTableIfNotExists(@NonNull SQLiteDatabase db) {
-        Cursor cursor = null;
-        try {
-            cursor = db.rawQuery("SELECT DISTINCT tbl_name FROM sqlite_master WHERE tbl_name = '"+TABLE_STORAGE+"'", null);
-            if(cursor != null && cursor.getCount() > 0) {
-                return;
-            }
-            db.execSQL(STATEMENT_CREATE_TABLE);
-        }catch (Exception e){
-            e.printStackTrace();
-        }finally {
-            if(cursor != null){
-                cursor.close();
-            }
-        }
-    }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/WXStorageModule.java b/android/sdk/src/main/java/com/taobao/weex/appfram/storage/WXStorageModule.java
deleted file mode 100644
index b6d9534..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/storage/WXStorageModule.java
+++ /dev/null
@@ -1,180 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.storage;
-
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.annotation.JSMethod;
-
-import java.util.Map;
-
-public class WXStorageModule extends WXSDKEngine.DestroyableModule implements IWXStorage {
-
-    IWXStorageAdapter mStorageAdapter;
-
-    private IWXStorageAdapter ability() {
-        if (mStorageAdapter != null) {
-            return mStorageAdapter;
-        }
-        mStorageAdapter = WXSDKEngine.getIWXStorageAdapter();
-        return mStorageAdapter;
-    }
-
-
-    @Override
-    @JSMethod(uiThread = false)
-    public void setItem(String key, String value, @Nullable final JSCallback callback) {
-        if (TextUtils.isEmpty(key) || value == null) {
-            StorageResultHandler.handleInvalidParam(callback);
-            return;
-        }
-
-        IWXStorageAdapter adapter = ability();
-        if (adapter == null) {
-            StorageResultHandler.handleNoHandlerError(callback);
-            return;
-        }
-        adapter.setItem(key, value, new IWXStorageAdapter.OnResultReceivedListener() {
-            @Override
-            public void onReceived(Map<String, Object> data) {
-                if(callback != null){
-                    callback.invoke(data);
-                }
-            }
-        });
-
-
-    }
-
-    @Override
-    @JSMethod(uiThread = false)
-    public void getItem(String key, @Nullable final JSCallback callback) {
-        if (TextUtils.isEmpty(key)) {
-            StorageResultHandler.handleInvalidParam(callback);
-            return;
-        }
-
-        IWXStorageAdapter adapter = ability();
-        if (adapter == null) {
-            StorageResultHandler.handleNoHandlerError(callback);
-            return;
-        }
-        adapter.getItem(key, new IWXStorageAdapter.OnResultReceivedListener() {
-            @Override
-            public void onReceived(Map<String, Object> data) {
-                if(callback != null){
-                    callback.invoke(data);
-                }
-            }
-        });
-    }
-
-    @Override
-    @JSMethod(uiThread = false)
-    public void removeItem(String key, @Nullable final JSCallback callback) {
-        if (TextUtils.isEmpty(key)) {
-            StorageResultHandler.handleInvalidParam(callback);
-            return;
-        }
-
-        IWXStorageAdapter adapter = ability();
-        if (adapter == null) {
-            StorageResultHandler.handleNoHandlerError(callback);
-            return;
-        }
-        adapter.removeItem(key, new IWXStorageAdapter.OnResultReceivedListener() {
-            @Override
-            public void onReceived(Map<String, Object> data) {
-                if(callback != null){
-                    callback.invoke(data);
-                }
-            }
-        });
-    }
-
-    @Override
-    @JSMethod(uiThread = false)
-    public void length(@Nullable final JSCallback callback) {
-        IWXStorageAdapter adapter = ability();
-        if (adapter == null) {
-            StorageResultHandler.handleNoHandlerError(callback);
-            return;
-        }
-        adapter.length(new IWXStorageAdapter.OnResultReceivedListener() {
-            @Override
-            public void onReceived(Map<String, Object> data) {
-                if(callback != null){
-                    callback.invoke(data);
-                }
-            }
-        });
-    }
-
-    @Override
-    @JSMethod(uiThread = false)
-    public void getAllKeys(@Nullable final JSCallback callback) {
-        IWXStorageAdapter adapter = ability();
-        if (adapter == null) {
-            StorageResultHandler.handleNoHandlerError(callback);
-            return;
-        }
-        adapter.getAllKeys(new IWXStorageAdapter.OnResultReceivedListener() {
-            @Override
-            public void onReceived(Map<String, Object> data) {
-                if(callback != null){
-                    callback.invoke(data);
-                }
-            }
-        });
-    }
-
-    @Override
-    @JSMethod(uiThread = false)
-    public void setItemPersistent(String key, String value, @Nullable final JSCallback callback) {
-        if (TextUtils.isEmpty(key) || value == null) {
-            StorageResultHandler.handleInvalidParam(callback);
-            return;
-        }
-
-        IWXStorageAdapter adapter = ability();
-        if (adapter == null) {
-            StorageResultHandler.handleNoHandlerError(callback);
-            return;
-        }
-        adapter.setItemPersistent(key, value, new IWXStorageAdapter.OnResultReceivedListener() {
-            @Override
-            public void onReceived(Map<String, Object> data) {
-                if(callback != null){
-                    callback.invoke(data);
-                }
-            }
-        });
-    }
-
-    @Override
-    public void destroy() {
-        IWXStorageAdapter adapter = ability();
-        if (adapter != null) {
-            adapter.close();
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/IWebSocketAdapter.java b/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/IWebSocketAdapter.java
deleted file mode 100644
index aebd1b8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/IWebSocketAdapter.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.websocket;
-
-import android.support.annotation.Nullable;
-
-/**
- * Created by moxun on 16/12/27.
- */
-
-public interface IWebSocketAdapter {
-
-    String HEADER_SEC_WEBSOCKET_PROTOCOL = "Sec-WebSocket-Protocol";
-
-    void connect(String url, @Nullable String protocol, EventListener listener);
-
-    void send(String data);
-
-    void close(int code, String reason);
-
-    void destroy();
-
-    interface EventListener {
-        void onOpen();
-
-        void onMessage(String data);
-
-        void onClose(int code, String reason, boolean wasClean);
-
-        void onError(String msg);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/IWebSocketAdapterFactory.java b/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/IWebSocketAdapterFactory.java
deleted file mode 100644
index e2e21dd..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/IWebSocketAdapterFactory.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.websocket;
-
-/**
- * Created by moxun on 16/12/28.
- */
-
-public interface IWebSocketAdapterFactory {
-    IWebSocketAdapter createWebSocketAdapter();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/WebSocketCloseCodes.java b/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/WebSocketCloseCodes.java
deleted file mode 100644
index 6251399..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/WebSocketCloseCodes.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.websocket;
-
-/**
- * Created by moxun on 17/1/3.
- * @link {https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent}
- */
-
-public enum WebSocketCloseCodes {
-    CLOSE_NORMAL(1000),
-    CLOSE_GOING_AWAY(1001),
-    CLOSE_PROTOCOL_ERROR(1002),
-    CLOSE_UNSUPPORTED(1003),
-    CLOSE_NO_STATUS(1005),
-    CLOSE_ABNORMAL(1006),
-    UNSUPPORTED_DATA(1007),
-    POLICY_VIOLATION(1008),
-    CLOSE_TOO_LARGE(1009),
-    MISSING_EXTENSION(1010),
-    INTERNAL_ERROR(1011),
-    SERVICE_RESTART(1012),
-    TRY_AGAIN_LATER(1013),
-    TLS_HANDSHAKE(1015);
-
-    private int code;
-
-    WebSocketCloseCodes(int code) {
-        this.code = code;
-    }
-
-    public int getCode() {
-        return code;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/WebSocketModule.java b/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/WebSocketModule.java
deleted file mode 100644
index f05f560..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/appfram/websocket/WebSocketModule.java
+++ /dev/null
@@ -1,188 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.websocket;
-
-import android.os.Looper;
-
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by moxun on 16/12/27.
- */
-
-public class WebSocketModule extends WXSDKEngine.DestroyableModule {
-
-    private static final String TAG = "WebSocketModule";
-    private static final String KEY_DATA = "data";
-    private static final String KEY_CODE = "code";
-    private static final String KEY_REASON = "reason";
-    private static final String KEY_WAS_CLEAN = "wasClean";
-
-    private IWebSocketAdapter webSocketAdapter;
-    private WebSocketEventListener eventListener;
-
-    public WebSocketModule() {
-        WXLogUtils.e(TAG, "create new instance");
-    }
-
-    @JSMethod(uiThread = false)
-    public void WebSocket(String url, String protocol) {
-        if (webSocketAdapter != null) {
-            WXLogUtils.w(TAG, "close");
-            webSocketAdapter.close(WebSocketCloseCodes.CLOSE_GOING_AWAY.getCode(), WebSocketCloseCodes.CLOSE_GOING_AWAY.name());
-        }
-        webSocketAdapter = mWXSDKInstance.getWXWebSocketAdapter();
-        if (!reportErrorIfNoAdapter()) {
-            eventListener = new WebSocketEventListener();
-            webSocketAdapter.connect(url, protocol, eventListener);
-        }
-    }
-
-    @JSMethod(uiThread = false)
-    public void send(String data) {
-        if (!reportErrorIfNoAdapter()) {
-            webSocketAdapter.send(data);
-        }
-    }
-
-    @JSMethod(uiThread = false)
-    public void close(String code, String reason) {
-        if (!reportErrorIfNoAdapter()) {
-            int codeNumber = WebSocketCloseCodes.CLOSE_NORMAL.getCode();
-            if (code != null) {
-                try {
-                    codeNumber = Integer.parseInt(code);
-                } catch (NumberFormatException e) {
-                    //ignore
-                }
-            }
-            webSocketAdapter.close(codeNumber, reason);
-        }
-    }
-
-    @JSMethod(uiThread = false)
-    public void onopen(JSCallback callback) {
-        if (eventListener != null) {
-            eventListener.onOpen = callback;
-        }
-    }
-
-    @JSMethod(uiThread = false)
-    public void onmessage(JSCallback callback) {
-        if (eventListener != null) {
-            eventListener.onMessage = callback;
-        }
-    }
-
-    @JSMethod(uiThread = false)
-    public void onclose(JSCallback callback) {
-        if (eventListener != null) {
-            eventListener.onClose = callback;
-        }
-    }
-
-    @JSMethod(uiThread = false)
-    public void onerror(JSCallback callback) {
-        if (eventListener != null) {
-            eventListener.onError = callback;
-        }
-    }
-
-    @Override
-    public void destroy() {
-        Runnable destroyTask = new Runnable() {
-            @Override
-            public void run() {
-                WXLogUtils.w(TAG, "close session with instance id " + mWXSDKInstance.getInstanceId());
-                if (webSocketAdapter != null) {
-                    webSocketAdapter.destroy();
-                }
-                webSocketAdapter = null;
-                eventListener = null;
-            }
-        };
-
-        if (Looper.myLooper() == Looper.getMainLooper()) {
-            WXBridgeManager.getInstance().post(destroyTask);
-        } else {
-            destroyTask.run();
-        }
-    }
-
-    private boolean reportErrorIfNoAdapter() {
-        if (webSocketAdapter == null) {
-            if (eventListener != null) {
-                eventListener.onError("No implementation found for IWebSocketAdapter");
-            }
-            WXLogUtils.e(TAG, "No implementation found for IWebSocketAdapter");
-            return true;
-        }
-        return false;
-    }
-
-    private class WebSocketEventListener implements IWebSocketAdapter.EventListener {
-        private JSCallback onOpen;
-        private JSCallback onClose;
-        private JSCallback onError;
-        private JSCallback onMessage;
-
-        @Override
-        public void onOpen() {
-            if (onOpen != null) {
-                onOpen.invoke(new HashMap<>(0));
-            }
-        }
-
-        @Override
-        public void onMessage(String data) {
-            if (onMessage != null) {
-                Map<String, String> msg = new HashMap<>(1);
-                msg.put(KEY_DATA, data);
-                onMessage.invokeAndKeepAlive(msg);
-            }
-        }
-
-        @Override
-        public void onClose(int code, String reason, boolean wasClean) {
-            if (onClose != null) {
-                Map<String, Object> msg = new HashMap<>(3);
-                msg.put(KEY_CODE, code);
-                msg.put(KEY_REASON, reason);
-                msg.put(KEY_WAS_CLEAN, wasClean);
-                onClose.invoke(msg);
-            }
-        }
-
-        @Override
-        public void onError(String msg) {
-            if (onError != null) {
-                Map<String, String> info = new HashMap<>(1);
-                info.put(KEY_DATA, msg);
-                onError.invokeAndKeepAlive(info);
-            }
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/base/CalledByNative.java b/android/sdk/src/main/java/com/taobao/weex/base/CalledByNative.java
deleted file mode 100644
index 15fa920..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/base/CalledByNative.java
+++ /dev/null
@@ -1,22 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-
-package com.taobao.weex.base;
-public @interface CalledByNative {
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/base/FloatUtil.java b/android/sdk/src/main/java/com/taobao/weex/base/FloatUtil.java
deleted file mode 100755
index ecbeeb4..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/base/FloatUtil.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.base;
-
-public class FloatUtil {
-
-  private static final float EPSILON = .00001f;
-
-  public static boolean floatsEqual(float f1, float f2) {
-    if (Float.isNaN(f1) || Float.isNaN(f2)) {
-      return Float.isNaN(f1) && Float.isNaN(f2);
-    }
-    return Math.abs(f2 - f1) < EPSILON;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/base/SystemMessageHandler.java b/android/sdk/src/main/java/com/taobao/weex/base/SystemMessageHandler.java
deleted file mode 100644
index 50ecfa7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/base/SystemMessageHandler.java
+++ /dev/null
@@ -1,106 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.base;
-
-import android.os.Handler;
-import android.os.Message;
-import android.util.Log;
-
-import java.io.Serializable;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-
-
-public class SystemMessageHandler extends Handler implements Serializable {
-
-    private static final String TAG = "SystemMessageHandler";
-
-    private static final int SCHEDULED_WORK = 1;
-
-    private long mMessagePumpDelegateNative = 0;
-
-    private Method mMessageMethodSetAsynchronous;
-
-    private native void nativeRunWork(long delegateNative);
-
-    private SystemMessageHandler(long messagePumpDelegateNative) {
-        this.mMessagePumpDelegateNative = messagePumpDelegateNative;
-        try {
-            Class<?> messageClass = Class.forName("android.os.Message");
-            mMessageMethodSetAsynchronous = messageClass.getMethod(
-                    "setAsynchronous", new Class[]{boolean.class});
-        } catch (ClassNotFoundException e) {
-            Log.e(TAG, "Failed to find android.os.Message class:" + e);
-        } catch (NoSuchMethodException e) {
-            Log.e(TAG, "Failed to load Message.setAsynchronous method:" + e);
-        } catch (RuntimeException e) {
-            Log.e(TAG, "Exception while loading Message.setAsynchronous method: " + e);
-        }
-    }
-
-    @CalledByNative
-    public static SystemMessageHandler create(long messagePumpDelegateNative) {
-        return new SystemMessageHandler(messagePumpDelegateNative);
-    }
-
-    @CalledByNative
-    private void scheduleWork() {
-        sendMessage(obtainAsyncMessage(SCHEDULED_WORK));
-    }
-
-    @CalledByNative
-    private void scheduleDelayedWork(long delayMillis) {
-        sendMessageDelayed(obtainAsyncMessage(SCHEDULED_WORK), delayMillis);
-    }
-
-    @CalledByNative
-    private void stop() {
-        removeMessages(SCHEDULED_WORK);
-    }
-
-    private Message obtainAsyncMessage(int what) {
-        Message msg = Message.obtain();
-        msg.what = what;
-//        if (mMessageMethodSetAsynchronous != null) {
-//            // If invocation fails, assume this is indicative of future
-//            // failures, and avoid log spam by nulling the reflected method.
-//            try {
-//                mMessageMethodSetAsynchronous.invoke(msg, true);
-//            } catch (IllegalAccessException e) {
-//                Log.e(TAG, "Illegal access to asynchronous message creation, disabling.");
-//                mMessageMethodSetAsynchronous = null;
-//            } catch (IllegalArgumentException e) {
-//                Log.e(TAG, "Illegal argument for asynchronous message creation, disabling.");
-//                mMessageMethodSetAsynchronous = null;
-//            } catch (InvocationTargetException e) {
-//                Log.e(TAG, "Invocation exception during asynchronous message creation, disabling.");
-//                mMessageMethodSetAsynchronous = null;
-//            } catch (RuntimeException e) {
-//                Log.e(TAG, "Runtime exception during asynchronous message creation, disabling.");
-//                mMessageMethodSetAsynchronous = null;
-//            }
-//        }
-        return msg;
-    }
-
-    @Override
-    public void handleMessage(Message msg) {
-        nativeRunWork(mMessagePumpDelegateNative);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/EventResult.java b/android/sdk/src/main/java/com/taobao/weex/bridge/EventResult.java
deleted file mode 100644
index 5d0e82d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/EventResult.java
+++ /dev/null
@@ -1,46 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-/**
- * Created by furture on 2017/10/17.
- */
-
-public class EventResult {
-
-    private Object result;
-    private boolean success = false;
-    /**
-     * onCallback javascript event callback method
-     * @param result
-     */
-    public void onCallback(Object result){
-        this.success = true;
-        this.result = result;
-    }
-
-    public boolean isSuccess() {
-        return success;
-    }
-
-    public Object getResult(){
-        return  result;
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/Invoker.java b/android/sdk/src/main/java/com/taobao/weex/bridge/Invoker.java
deleted file mode 100644
index 43eab76..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/Invoker.java
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Type;
-
-/**
- * Created by sospartan on 6/16/16.
- */
-public interface Invoker {
-  Object invoke(Object receiver,Object...params) throws InvocationTargetException, IllegalAccessException;
-
-  Type[] getParameterTypes();
-
-  boolean isRunOnUIThread();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/JSCallback.java b/android/sdk/src/main/java/com/taobao/weex/bridge/JSCallback.java
deleted file mode 100644
index d0ccb69..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/JSCallback.java
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-/**
- * Created by sospartan on 5/24/16.
- */
-public interface JSCallback {
-  /**
-   * invoke javascript callback method, this method will destoryed after invoke.
-   * @param data
-   */
-  void invoke(Object data);
-
-  /**
-   * invoke javascript callback method and keep callback alive for later use.
-   * @param data
-   */
-  void invokeAndKeepAlive(Object data);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/JavascriptInvokable.java b/android/sdk/src/main/java/com/taobao/weex/bridge/JavascriptInvokable.java
deleted file mode 100644
index 32afe62..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/JavascriptInvokable.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-/**
- * Created by sospartan on 11/11/2016.
- */
-
-public interface JavascriptInvokable {
-  String[] getMethods();
-  Invoker getMethodInvoker(String name);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/MethodInvoker.java b/android/sdk/src/main/java/com/taobao/weex/bridge/MethodInvoker.java
deleted file mode 100644
index 740e081..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/MethodInvoker.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-import java.lang.reflect.Type;
-
-/**
- * Created by sospartan on 6/16/16.
- */
-public class MethodInvoker implements Invoker {
-
-  final Method mMethod;
-  final boolean mRunOnUIThread;
-  Type[] mParam;
-
-  public MethodInvoker(Method method){
-    this(method,false);
-  }
-
-  public MethodInvoker(Method method,boolean runInUIThread){
-    mMethod = method;
-    mParam = mMethod.getGenericParameterTypes();
-    mRunOnUIThread = runInUIThread;
-  }
-
-  @Override
-  public Object invoke(Object receiver, Object... params) throws InvocationTargetException, IllegalAccessException {
-    return mMethod.invoke(receiver,params);
-  }
-
-  @Override
-  public Type[] getParameterTypes() {
-    if(mParam ==null){
-      mParam = mMethod.getGenericParameterTypes();
-    }
-    return mParam;
-  }
-
-  @Override
-  public boolean isRunOnUIThread() {
-    return mRunOnUIThread;
-  }
-
-  @Override
-  public String toString() {
-    return mMethod.getName();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/ModuleFactory.java b/android/sdk/src/main/java/com/taobao/weex/bridge/ModuleFactory.java
deleted file mode 100644
index a5b41db..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/ModuleFactory.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import com.taobao.weex.common.WXModule;
-
-import java.util.ArrayList;
-import java.util.Map;
-
-/**
- * Created by sospartan on 6/17/16.
- */
-public interface ModuleFactory<T extends WXModule> extends JavascriptInvokable {
-
-  T buildInstance() throws IllegalAccessException, InstantiationException;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/ModuleFactoryImpl.java b/android/sdk/src/main/java/com/taobao/weex/bridge/ModuleFactoryImpl.java
deleted file mode 100644
index da26f14..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/ModuleFactoryImpl.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-/**
- * Created by shiwentao on 2018/3/13.
- */
-
-public class ModuleFactoryImpl {
-  public ModuleFactory mFactory = null;
-  public boolean hasRigster = false;
-
-  public ModuleFactoryImpl(ModuleFactory factory) {
-    mFactory = factory;
-  }
-
-  public ModuleFactoryImpl(ModuleFactory factory, boolean rigister) {
-    mFactory = factory;
-    hasRigster = rigister;
-  }
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/NativeInvokeHelper.java b/android/sdk/src/main/java/com/taobao/weex/bridge/NativeInvokeHelper.java
deleted file mode 100644
index a84a240..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/NativeInvokeHelper.java
+++ /dev/null
@@ -1,125 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import android.util.Log;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.performance.WXAnalyzerDataTransfer;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXReflectionUtils;
-
-import java.lang.reflect.Type;
-
-/**
- * Created by sospartan on 10/11/2016.
- */
-
-public class NativeInvokeHelper {
-  private String mInstanceId;
-
-  public NativeInvokeHelper(String instanceId){
-    mInstanceId = instanceId;
-  }
-
-  public Object invoke(final Object target,final Invoker invoker,JSONArray args) throws Exception {
-    final Object[] params = prepareArguments(
-            invoker.getParameterTypes(),
-            args);
-
-    if (WXAnalyzerDataTransfer.isInteractionLogOpen() && invoker instanceof MethodInvoker) {
-      for (int i = 0; i < params.length; i++) {
-        if (params[i] instanceof SimpleJSCallback) {
-          final String callBackId = ((SimpleJSCallback)params[i]).getCallbackId();
-          Log.d(WXAnalyzerDataTransfer.INTERACTION_TAG, "[client][callNativeModuleStart]," + mInstanceId + "," + ((MethodInvoker) invoker).mMethod.getDeclaringClass() + "," + ((MethodInvoker) invoker).mMethod.getName() + "," + callBackId);
-          ((SimpleJSCallback) params[i]).setInvokerCallback(new SimpleJSCallback.InvokerCallback() {
-            @Override
-            public void onInvokeSuccess() {
-              Log.d(WXAnalyzerDataTransfer.INTERACTION_TAG, "[client][callNativeModuleEnd]," + mInstanceId + "," + ((MethodInvoker) invoker).mMethod.getDeclaringClass() + "," + ((MethodInvoker) invoker).mMethod.getName() + "," + callBackId);
-            }
-          });
-          break;
-        }
-      }
-    }
-
-    if (invoker.isRunOnUIThread()) {
-      WXSDKManager.getInstance().postOnUiThread(new Runnable() {
-        @Override
-        public void run() {
-          if (invoker != null) {
-            try {
-              WXSDKInstance targetInstance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
-              if (null == targetInstance || targetInstance.isDestroy()){
-                return;
-              }
-              invoker.invoke(target, params);
-            } catch (Exception e) {
-              WXLogUtils.e("NativeInvokeHelper",target + " Invoker " + invoker.toString()+" exception:"+e);
-            }
-          }
-        }
-      }, 0);
-    } else {
-      return invoker.invoke(target, params);
-    }
-    return null;
-  }
-
-  protected Object[] prepareArguments(Type[] paramClazzs, JSONArray args) throws Exception {
-    Object[] params = new Object[paramClazzs.length];
-    Object value;
-    Type paramClazz;
-    for (int i = 0; i < paramClazzs.length; i++) {
-      paramClazz = paramClazzs[i];
-      if(i>=args.size()){
-        if(!paramClazz.getClass().isPrimitive()) {
-          params[i] = null;
-          continue;
-        }else {
-          throw new Exception("[prepareArguments] method argument list not match.");
-        }
-      }
-      value = args.get(i);
-
-      if (paramClazz == JSONObject.class) {
-        if(value instanceof  JSONObject || value == null) {
-          params[i] = value;
-        }else if (value instanceof String){
-          params[i] = JSON.parseObject(value.toString());
-        }
-      } else if(JSCallback.class == paramClazz){
-        if(value instanceof String){
-          params[i] = new SimpleJSCallback(mInstanceId,(String)value);
-        }else{
-          throw new Exception("Parameter type not match.");
-        }
-      } else {
-        params[i] = WXReflectionUtils.parseArgument(paramClazz,value);
-      }
-    }
-    return params;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/RequestHandler.java b/android/sdk/src/main/java/com/taobao/weex/bridge/RequestHandler.java
deleted file mode 100644
index f49ba9c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/RequestHandler.java
+++ /dev/null
@@ -1,155 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import static com.taobao.weex.http.WXHttpUtil.KEY_USER_AGENT;
-
-import android.net.Uri;
-import android.support.annotation.Keep;
-import android.text.TextUtils;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXHttpListener;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.base.CalledByNative;
-import com.taobao.weex.bridge.WXBridgeManager.BundType;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXRequest;
-import com.taobao.weex.common.WXResponse;
-import com.taobao.weex.http.WXHttpUtil;
-import com.taobao.weex.utils.WXExceptionUtils;
-
-import com.taobao.weex.utils.WXLogUtils;
-import java.util.HashMap;
-import java.util.Locale;
-
-public class RequestHandler {
-
-  @Keep
-  native void nativeInvokeOnSuccess(long callback, String script, String bundleType);
-  native void nativeInvokeOnFailed(long callback);
-
-  @CalledByNative
-  public static RequestHandler create() {
-    return new RequestHandler();
-  }
-
-  @CalledByNative
-  public void send(String instanceId, String url, long nativeCallback) {
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(url) ||
-        nativeCallback == 0 ||
-        !WXSDKManager.getInstance().getAllInstanceMap().containsKey(
-            instanceId)) {
-      return;
-    }
-
-    WXSDKManager manager = WXSDKManager.getInstance();
-    WXSDKInstance instance =
-        WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (instance == null)
-      return;
-    IWXHttpAdapter adapter = WXSDKManager.getInstance().getIWXHttpAdapter();
-
-    WXRequest wxRequest = new WXRequest();
-    wxRequest.url = manager.getURIAdapter()
-                        .rewrite(instance, URIAdapter.BUNDLE, Uri.parse(url))
-                        .toString();
-
-    if (wxRequest.paramMap == null) {
-      wxRequest.paramMap = new HashMap<>();
-    }
-    wxRequest.paramMap.put(
-        KEY_USER_AGENT, WXHttpUtil.assembleUserAgent(
-                            instance.getContext(), WXEnvironment.getConfig()));
-    wxRequest.paramMap.put("isBundleRequest", "true");
-    WXLogUtils.i("Eagle", String.format(Locale.ENGLISH, "Weex eagle is going to download script from %s", url));
-    adapter.sendRequest(wxRequest, new OnHttpListenerInner(instance, nativeCallback, url));
-  }
-
-  @Keep
-  @CalledByNative
-  public void getBundleType(String instanceId, final String content, final long nativeCallback){
-    BundType bundleType = WXBridgeManager.getInstance().getBundleType("", content);
-    final String bundleTypeStr = bundleType == null ? "Others" : bundleType.toString();
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if ("Others".equalsIgnoreCase(bundleTypeStr) && null != instance){
-      WXExceptionUtils.commitCriticalExceptionRT(
-          instanceId,
-          WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE,
-          "RequestHandler.onSuccess",
-          "eagle ->" +WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE.getErrorMsg(),
-          null
-      );
-    }
-    WXBridgeManager.getInstance().post(new Runnable() {
-      @Override
-      public void run() {
-        if(WXBridgeManager.getInstance().isJSFrameworkInit()) {
-          nativeInvokeOnSuccess(nativeCallback, content, bundleTypeStr);
-        }
-        else {
-          nativeInvokeOnFailed(nativeCallback);
-        }
-      }
-    });
-  }
-
-  class OnHttpListenerInner extends WXHttpListener {
-    private long sNativeCallback;
-
-    OnHttpListenerInner(WXSDKInstance instance, long nativeCallback, String bundlUrl) {
-      super(instance, bundlUrl);
-      sNativeCallback = nativeCallback;
-    }
-
-    @Override
-    public void onSuccess(WXResponse response) {
-        final String script = new String(response.originalData);
-        BundType bundleType = WXBridgeManager.getInstance().getBundleType("", script);
-        final String bundleTypeStr = bundleType == null ? "Others" : bundleType.toString();
-        if ("Others".equalsIgnoreCase(bundleTypeStr) && null != getInstance()){
-          WXExceptionUtils.commitCriticalExceptionRT(
-              getInstance().getInstanceId(),
-              WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE,
-              "RequestHandler.onSuccess",
-              "eagle ->" +WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE.getErrorMsg(),
-              null
-          );
-        }
-        WXBridgeManager.getInstance().post(new Runnable() {
-          @Override
-          public void run() {
-            if(WXBridgeManager.getInstance().isJSFrameworkInit()) {
-              nativeInvokeOnSuccess(sNativeCallback, script, bundleTypeStr);
-            }
-            else{
-              nativeInvokeOnFailed(sNativeCallback);
-            }
-          }
-        });
-    }
-
-    @Override
-    public void onFail(WXResponse response) {
-      nativeInvokeOnFailed(sNativeCallback);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/ResultCallback.java b/android/sdk/src/main/java/com/taobao/weex/bridge/ResultCallback.java
deleted file mode 100644
index 368a5b1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/ResultCallback.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-public interface ResultCallback<T> {
-    void onReceiveResult(T result);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/ResultCallbackManager.java b/android/sdk/src/main/java/com/taobao/weex/bridge/ResultCallbackManager.java
deleted file mode 100644
index 59475be..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/ResultCallbackManager.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import android.util.SparseArray;
-
-/**
- * Manage async callbacks which waiting for the result of executing javascript
- */
-/* default */ class ResultCallbackManager {
-    // Unique id for callback after executing js
-    private static long sCallbackId = 0;
-    // Map for save callbacks, key is id
-    private static SparseArray<ResultCallback> mResultCallbacks = new SparseArray<>();
-
-    // Generate unique id
-    static long generateCallbackId(ResultCallback callback) {
-        if (sCallbackId >= Integer.MAX_VALUE) {
-            sCallbackId = 0;
-        }
-        int id = (int) sCallbackId++;
-        mResultCallbacks.put(id, callback);
-        return id;
-    }
-
-    // Remove id from callback map
-    static ResultCallback removeCallbackById(long id) {
-        ResultCallback callback = mResultCallbacks.get((int) id);
-        mResultCallbacks.remove((int) id);
-        return callback;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/SimpleJSCallback.java b/android/sdk/src/main/java/com/taobao/weex/bridge/SimpleJSCallback.java
deleted file mode 100644
index 8b9411e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/SimpleJSCallback.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-/**
- * Created by sospartan on 27/10/2016.
- */
-public class SimpleJSCallback implements JSCallback {
-
-  String mInstanceId;
-  String mCallbackId;
-
-  private InvokerCallback mInvokerCallback;
-
-  public void setInvokerCallback(InvokerCallback callback) {
-    this.mInvokerCallback = callback;
-  }
-
-  interface InvokerCallback {
-    void onInvokeSuccess();
-  }
-
-  public String getCallbackId() {
-    return mCallbackId;
-  }
-
-  public SimpleJSCallback(String instanceId, String callbackId) {
-    this.mCallbackId = callbackId;
-    this.mInstanceId = instanceId;
-  }
-
-
-  @Override
-  public void invoke(Object data) {
-    WXBridgeManager.getInstance().callbackJavascript(mInstanceId, mCallbackId, data, false);
-    if (mInvokerCallback != null) {
-      mInvokerCallback.onInvokeSuccess();
-    }
-  }
-
-  @Override
-  public void invokeAndKeepAlive(Object data) {
-    WXBridgeManager.getInstance().callbackJavascript(mInstanceId, mCallbackId, data, true);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXBridge.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXBridge.java
deleted file mode 100755
index 35e5468..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXBridge.java
+++ /dev/null
@@ -1,945 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import android.text.TextUtils;
-import android.util.Log;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.base.CalledByNative;
-import com.taobao.weex.common.IWXBridge;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.layout.ContentBoxMeasurement;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.performance.WXStateRecord;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXJsonUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXWsonJSONSwitch;
-import com.taobao.weex.utils.tools.TimeCalculator;
-
-import java.io.Serializable;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Map;
-
-/**
- * Communication interface for Java code and JavaScript code.
- */
-
-    public class WXBridge implements IWXBridge {
-
-  private native int nativeInitFrameworkEnv(String framework, WXParams params, String cacheDir, boolean pieSupport);
-
-  private native int nativeInitFramework(String framework, WXParams params);
-
-  private native void nativeRefreshInstance(String instanceId, String namespace, String function, WXJSObject[] args);
-
-  private native int nativeExecJS(String instanceId, String name, String function, WXJSObject[] args);
-
-  private native int nativeExecJSService(String javascript);
-
-  public native byte[] nativeExecJSWithResult(String instanceId, String _namespace, String _function, WXJSObject[] args);
-  public native void nativeExecJSWithCallback(String instanceId, String _namespace, String _function, WXJSObject[] args, long callbackId);
-
-  public native int nativeCreateInstanceContext(String instanceId, String name, String function, WXJSObject[] args);
-
-  public native int nativeDestoryInstance(String instanceId, String name, String function, WXJSObject[] args);
-
-  public native String nativeExecJSOnInstance(String instanceId, String script, int type);
-
-  public native void nativeFireEventOnDataRenderNode(String instanceId, String ref, String type, String data, String domChanges);
-
-  public native void nativeInvokeCallbackOnDataRender(String instanceId, String callbackId, String data, boolean keepAlive);
-
-  public native void nativeRegisterModuleOnDataRenderNode( String data);
-
-  public native void nativeRegisterComponentOnDataRenderNode( String data);
-
-  private native void nativeTakeHeapSnapshot(String filename);
-
-  private native void nativeBindMeasurementToRenderObject(long ptr);
-
-  private native void nativeSetRenderContainerWrapContent(boolean wrap, String instanceId);
-
-  public native long[] nativeGetFirstScreenRenderTime(String instanceId);
-
-  public native long[] nativeGetRenderFinishTime(String instanceId);
-
-  private native void nativeSetDefaultHeightAndWidthIntoRootDom(String instanceId, float defaultWidth, float defaultHeight, boolean isWidthWrapContent, boolean isHeightWrapContent);
-
-  private native void nativeOnInstanceClose(String instanceId);
-
-  private native void nativeForceLayout(String instanceId);
-
-  private native boolean nativeNotifyLayout(String instanceId);
-
-  private native void nativeSetStyleWidth(String instanceId, String ref, float value);
-
-  private native void nativeSetStyleHeight(String instanceId, String ref, float value);
-
-  private native void nativeSetMargin(String instanceId, String ref, int edge, float value);
-
-  private native void nativeSetPadding(String instanceId, String ref, int edge, float value);
-
-  private native void nativeSetPosition(String instanceId, String ref, int edge, float value);
-
-  private native void nativeMarkDirty(String instanceId, String ref, boolean dirty);
-
-  private native void nativeSetDeviceDisplay(String instanceId, float width, float height, float scale);
-
-  private native void nativeRegisterCoreEnv(String key, String value);
-
-  private native void nativeResetWXBridge(Object bridge, String className);
-
-  private native void nativeSetInstanceRenderType(String instanceId, String renderType);
-
-  private native void nativeRemoveInstanceRenderType(String instanceId);
-
-  private native void nativeSetPageArgument(String instanceId, String key, String value);
-
-  public native void nativeOnInteractionTimeUpdate(String instanceId);
-
-  public native String nativeDumpIpcPageQueueInfo();
-
-  /**
-   * Update Init Framework Params
-   * */
-  private native void nativeUpdateInitFrameworkParams(String key, String value, String desc);
-
-  /**
-   * update global config,
-   * @param config params
-   * */
-  public native void nativeUpdateGlobalConfig(String config);
-
-  private native void nativeSetViewPortWidth(String instanceId, float viewPortWidth);
-  private native void nativeSetLogType(float type, float isPerf);
-
-  private native void nativeReloadPageLayout(String instanceId);
-
-  private native void nativeSetDeviceDisplayOfPage(String instanceId,float width,float height);
-
-  public static final boolean MULTIPROCESS = true;
-
-
-  @Override
-  public void updateInitFrameworkParams(String key, String value, String desc){
-    WXStateRecord.getInstance().recordAction("","updateInitFrameworkParams:");
-     nativeUpdateInitFrameworkParams(key, value, desc);
-  }
-
-  @Override
-  public void setLogType(float type, boolean isPerf) {
-    Log.e("WeexCore", "setLog" + WXEnvironment.sLogLevel.getValue() + "isPerf : " + isPerf);
-    nativeSetLogType(type, isPerf ? 1 : 0);
-  }
-
-  @Override
-  public int initFramework(String framework, WXParams params) {
-    return nativeInitFramework(framework, params);
-  }
-
-  @Override
-  public int initFrameworkEnv(String framework, WXParams params, String cacheDir, boolean pieSupport) {
-    if (MULTIPROCESS) {
-      WXStateRecord.getInstance().recordAction("","nativeInitFrameworkEnv:");
-      return nativeInitFrameworkEnv(framework, params, cacheDir, pieSupport);
-    } else {
-      WXStateRecord.getInstance().recordAction("","nativeInitFramework:");
-      return nativeInitFramework(framework, params);
-    }
-  }
-
-  @Override
-  public void refreshInstance(String instanceId, String namespace, String function, WXJSObject[] args) {
-    WXStateRecord.getInstance().recordAction(instanceId,"refreshInstance:"+namespace+","+function);
-    nativeRefreshInstance(instanceId, namespace, function, args);
-  }
-
-  @Override
-  public int execJS(String instanceId, String namespace, String function, WXJSObject[] args) {
-    WXStateRecord.getInstance().recordAction(instanceId,"execJS:"+namespace+","+function);
-    return nativeExecJS(instanceId, namespace, function, args);
-  }
-
-  @Override
-  public void execJSWithCallback(String instanceId, String namespace, String function, WXJSObject[] args, ResultCallback callback) {
-    WXStateRecord.getInstance().recordAction(instanceId,"execJSWithCallback:"+namespace+","+function);
-    if (callback == null) {
-      execJS(instanceId, namespace, function, args);
-    }
-    nativeExecJSWithCallback(instanceId, namespace, function, args,
-            ResultCallbackManager.generateCallbackId(callback));
-  }
-
-  @CalledByNative
-  public void onNativePerformanceDataUpdate(String instanceId,Map<String,String> map){
-    if (TextUtils.isEmpty(instanceId) || null == map || map.size() < 1){
-      return;
-    }
-    WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
-    if (null == instance || null == instance.getApmForInstance()){
-      return;
-    }
-    instance.getApmForInstance().updateNativePerformanceData(map);
-  }
-
-  // Result from js engine
-  @CalledByNative
-  public void onReceivedResult(long callbackId, byte[] result) {
-    WXStateRecord.getInstance().recordAction("onReceivedResult","callbackId"+callbackId);
-    ResultCallback callback = ResultCallbackManager.removeCallbackById(callbackId);
-    if (callback != null) {
-       callback.onReceiveResult(result);
-    }
-  }
-
-  @Override
-  public int execJSService(String javascript) {
-    WXStateRecord.getInstance().recordAction("execJSService","execJSService:");
-    return nativeExecJSService(javascript);
-  }
-
-
-  @Override
-  public void takeHeapSnapshot(String filename) {
-    nativeTakeHeapSnapshot(filename);
-  }
-
-  @Override
-  public int createInstanceContext(String instanceId, String name, String function, WXJSObject[] args) {
-    Log.e(TimeCalculator.TIMELINE_TAG,"createInstance :" + System.currentTimeMillis());
-    WXStateRecord.getInstance().recordAction(instanceId,"createInstanceContext:");
-    return nativeCreateInstanceContext(instanceId, name, function, args);
-  }
-
-  @Override
-  public int destoryInstance(String instanceId, String name, String function, WXJSObject[] args) {
-    WXStateRecord.getInstance().recordAction(instanceId,"destoryInstance:");
-    return nativeDestoryInstance(instanceId, name, function, args);
-  }
-
-  @Override
-  public String execJSOnInstance(String instanceId, String script, int type) {
-    WXStateRecord.getInstance().recordAction(instanceId,"execJSOnInstance:"+type);
-    return nativeExecJSOnInstance(instanceId, script, type);
-  }
-
-  public static final String TAG = "WXBridge";
-
-  /**
-   * JavaScript uses this methods to call Android code
-   *
-   * @param instanceId
-   * @param tasks
-   * @param callback
-   */
-  @CalledByNative
-  public int callNative(String instanceId, byte[] tasks, String callback) {
-    if("HeartBeat".equals(callback)) {
-      Log.e("HeartBeat instanceId", instanceId);
-      WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if(sdkInstance != null) {
-        sdkInstance.createInstanceFuncHeartBeat();
-      }
-      return IWXBridge.INSTANCE_RENDERING;
-    }
-
-    return callNative(instanceId, (JSONArray) JSON.parseArray(new String(tasks)), callback);
-  }
-
-  @Override
-  public int callNative(String instanceId, String tasks, String callback) {
-    try{
-      return callNative(instanceId, JSONArray.parseArray(tasks), callback);
-    }catch (Exception e){
-      WXLogUtils.e(TAG, "callNative throw exception: " + WXLogUtils.getStackTrace(e));
-      return IWXBridge.INSTANCE_RENDERING;
-    }
-  }
-
-  private int callNative(String instanceId, JSONArray tasks, String callback){
-    long start = System.currentTimeMillis();
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (instance != null) {
-      instance.firstScreenCreateInstanceTime(start);
-    }
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callNative(instanceId, tasks, callback);
-    } catch (Throwable e) {
-      WXLogUtils.e(TAG, "callNative throw exception:" + WXLogUtils.getStackTrace(e));
-    }
-
-    if (WXEnvironment.isApkDebugable()) {
-      if (errorCode == IWXBridge.DESTROY_INSTANCE) {
-        WXLogUtils.w("destroyInstance :" + instanceId + " JSF must stop callNative");
-      }
-    }
-    return errorCode;
-  }
-
-  @CalledByNative
-  public void reportJSException(String instanceId, String func, String exception) {
-    WXBridgeManager.getInstance().reportJSException(instanceId, func, exception);
-  }
-
-
-  /**
-   * Bridge module Js Method
-   * support Sync or Async through setting  Annotation as {@link com.taobao.weex.annotation.JSMethod }
-   *
-   * @param instanceId Instance ID
-   * @param module     the name of module
-   * @param method     the name of method
-   * @param arguments  the arguments of the method
-   * @param options    option arguments for extending
-   * @return the result
-   */
-  @Override
-  @CalledByNative
-  public Object callNativeModule(String instanceId, String module, String method, byte[] arguments, byte[] options) {
-    try {
-      WXStateRecord.getInstance().recordAction(instanceId,"callNativeModule:"+module+"."+method);
-      long start = WXUtils.getFixUnixTime();
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      JSONArray argArray = null;
-      if (arguments != null){
-        // TODO use a better way
-        if (instance!=null && (instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER
-                || instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER_BINARY)){
-          try {
-            argArray = (JSONArray) JSON.parse(new String(arguments, "UTF-8"));
-          } catch (Exception e) {
-            // For wson use in data render mode
-            argArray = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(arguments);
-          }
-        } else {
-          argArray = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(arguments);
-        }
-      }
-      JSONObject optionsObj = null;
-      if (options != null) {
-        optionsObj = (JSONObject) WXWsonJSONSwitch.parseWsonOrJSON(options);
-      } else if (argArray != null) {
-        final WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-        if (sdkInstance != null) {
-          if (WXBridgeManager.BundType.Rax.equals(sdkInstance.bundleType)) {
-            Object weex_options__ = null;
-            for (Object object: argArray) {
-              if (object instanceof JSONObject && ((JSONObject) object).containsKey("__weex_options__")) {
-                weex_options__ = ((JSONObject) object).get("__weex_options__");
-              }
-            }
-
-            if (weex_options__ instanceof JSONObject)
-              optionsObj = (JSONObject) weex_options__;
-          }
-        }
-
-      }
-
-      Object object = WXBridgeManager.getInstance().callNativeModule(instanceId, module, method, argArray, optionsObj);
-
-      if (null != instance){
-        instance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_CALL_NATIVE_NUM,1);
-        instance.getApmForInstance().updateFSDiffStats(
-            WXInstanceApm.KEY_PAGE_STATS_FS_CALL_NATIVE_TIME,
-            WXUtils.getFixUnixTime()-start
-        );
-      }
-      if (instance!=null && (instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER
-          || instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER_BINARY)){
-        try {
-          if(object == null){
-            return new WXJSObject(null);
-          }
-          if(object.getClass() == WXJSObject.class){
-            return (WXJSObject) object;
-          }
-          return new WXJSObject(WXJSObject.JSON, WXJsonUtils.fromObjectToJSONString(object));
-        } catch (Exception e) {
-          // For wson use in data render mode
-          return WXWsonJSONSwitch.toWsonOrJsonWXJSObject(object);
-        }
-      } else {
-        return WXWsonJSONSwitch.toWsonOrJsonWXJSObject(object);
-      }
-    }catch (Exception e){
-      WXLogUtils.e(TAG,  e);
-      return new WXJSObject(null);
-    }
-  }
-
-  /**
-   * Bridge component Js Method
-   *
-   * @param instanceId   Instance ID
-   * @param ref the ref of component
-   * @param method       the name of method
-   * @param arguments    the arguments of the method
-   * @param options      option arguments for extending
-   */
-  @Override
-  @CalledByNative
-  public void callNativeComponent(String instanceId, String ref, String method, byte[] arguments, byte[] optionsData) {
-    WXStateRecord.getInstance().recordAction(instanceId,"callNativeComponent:"+method);
-    try{
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      JSONArray argArray = null;
-      if (arguments != null){
-        // TODO use a better way
-        if (instance!=null && (instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER
-            || instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER_BINARY)){
-          try {
-            argArray = (JSONArray) JSON.parse(new String(arguments, "UTF-8"));
-          } catch (Exception e) {
-            // For wson use in data render mode
-            argArray = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(arguments);
-          }
-        } else {
-          argArray = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(arguments);
-        }
-      }
-      Object options = WXWsonJSONSwitch.parseWsonOrJSON(optionsData);
-      WXBridgeManager.getInstance().callNativeComponent(instanceId, ref, method, argArray, options);
-    }catch (Exception e){
-      WXLogUtils.e(TAG,  e);
-    }
-  }
-
-  @Override
-  @CalledByNative
-  public void setTimeoutNative(String callbackId, String time) {
-    WXBridgeManager.getInstance().setTimeout(callbackId, time);
-  }
-
-  @Override
-  @CalledByNative
-  public void setJSFrmVersion(String version) {
-    if (version != null) {
-      WXEnvironment.JS_LIB_SDK_VERSION = version;
-    }
-    WXStateRecord.getInstance().onJSFMInit();
-  }
-
-  @Override
-  public void resetWXBridge(boolean remoteDebug) {
-    final String className = this.getClass().getName().replace('.', '/');
-    nativeResetWXBridge(this, className);
-  }
-
-  @Override
-  @CalledByNative
-  public int callUpdateFinish(String instanceId, byte[] tasks, String callback) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callUpdateFinish(instanceId, callback);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callCreateBody throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callRefreshFinish(String instanceId, byte[] tasks, String callback) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callRefreshFinish(instanceId, callback);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callCreateFinish throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public void reportServerCrash(String instanceId, String crashFile) {
-    WXLogUtils.e(TAG, "reportServerCrash instanceId:" + instanceId + " crashFile: " + crashFile);
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callReportCrashReloadPage(instanceId, crashFile);
-
-      // upload crash log
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "reloadPageNative throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-  }
-
-  @Override
-  @CalledByNative
-  public int callCreateBody(String instanceId, String componentType, String ref,
-                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
-                            float[] margins, float[] paddings, float[] borders) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-
-    try {
-      errorCode = WXBridgeManager.getInstance().callCreateBody(instanceId, componentType, ref,
-              styles, attributes, events, margins, paddings, borders);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callCreateBody throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callAddElement(String instanceId, String componentType, String ref, int index, String parentRef,
-                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
-                            float[] margins, float[] paddings, float[] borders,  boolean willLayout) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-
-    try {
-      errorCode = WXBridgeManager.getInstance().callAddElement(instanceId, componentType, ref, index, parentRef,
-              styles, attributes, events, margins, paddings, borders, willLayout);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        e.printStackTrace();
-        WXLogUtils.e(TAG, "callAddElement throw error:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callRemoveElement(String instanceId, String ref) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callRemoveElement(instanceId, ref);
-    } catch (Throwable e) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callRemoveElement throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callMoveElement(String instanceId, String ref, String parentref, int index) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callMoveElement(instanceId, ref, parentref, index);
-    } catch (Throwable e) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callMoveElement throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callAddEvent(String instanceId, String ref, String event) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callAddEvent(instanceId, ref, event);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      // if(WXEnvironment.isApkDebugable()){
-      WXLogUtils.e(TAG, "callAddEvent throw exception:" + WXLogUtils.getStackTrace(e));
-      // }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callRemoveEvent(String instanceId, String ref, String event) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callRemoveEvent(instanceId, ref, event);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callRemoveEvent throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callUpdateStyle(String instanceId, String ref,
-                             HashMap<String, Object> styles,
-                             HashMap<String, String> paddings,
-                             HashMap<String, String> margins,
-                             HashMap<String, String> borders) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callUpdateStyle(instanceId, ref, styles, paddings, margins, borders);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callUpdateStyle throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callUpdateAttrs(String instanceId, String ref, HashMap<String, String> attrs) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callUpdateAttrs(instanceId, ref, attrs);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callUpdateAttr throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callAddChildToRichtext(String instanceId, String nodeType, String ref, String parentRef, String richTextRef,
-                             HashMap<String, String> styles, HashMap<String, String> attrs){
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callAddChildToRichtext(instanceId, nodeType, ref, parentRef, richTextRef,
-              styles, attrs);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callAddChildToRichtext throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-  @Override
-  @CalledByNative
-  public int callRemoveChildFromRichtext(String instanceId, String ref, String parentRef, String richTextRef){
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callRemoveChildFromRichtext(instanceId, ref, parentRef, richTextRef);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callRemoveChildFromRichtext throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callUpdateRichtextStyle(String instanceId, String ref, HashMap<String, String> styles, String parentRef, String richTextRef){
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callUpdateRichtextStyle(instanceId, ref, styles, parentRef, richTextRef);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callUpdateRichtextStyle throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-  @Override
-  @CalledByNative
-  public int callUpdateRichtextChildAttr(String instanceId, String ref, HashMap<String, String> attrs, String parentRef, String richTextRef){
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callUpdateRichtextChildAttr(instanceId, ref, attrs, parentRef, richTextRef);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callUpdateRichtextChildAttr throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-
-  @Override
-  @CalledByNative
-  public int callLayout(String instanceId, String ref, int top, int bottom, int left, int right, int height, int width, boolean isRTL, int index) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callLayout(instanceId, ref, top, bottom, left, right, height, width, isRTL, index);
-    } catch (Throwable e) {
-      //catch everything during call native.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callLayout throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callCreateFinish(String instanceId) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callCreateFinish(instanceId);
-    } catch (Throwable e) {
-      WXLogUtils.e(TAG, "callCreateFinish throw exception:" + WXLogUtils.getStackTrace(e));
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callRenderSuccess(String instanceId) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callRenderSuccess(instanceId);
-    } catch (Throwable e) {
-      WXLogUtils.e(TAG, "callCreateFinish throw exception:" + WXLogUtils.getStackTrace(e));
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callAppendTreeCreateFinish(String instanceId, String ref) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callAppendTreeCreateFinish(instanceId, ref);
-    } catch (Throwable e) {
-      WXLogUtils.e(TAG, "callAppendTreeCreateFinish throw exception:" + WXLogUtils.getStackTrace(e));
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public int callHasTransitionPros(String instanceId, String ref, HashMap<String, String> styles) {
-    int errorCode = IWXBridge.INSTANCE_RENDERING;
-    try {
-      errorCode = WXBridgeManager.getInstance().callHasTransitionPros(instanceId, ref, styles);
-    } catch (Throwable e) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "callHasTransitionPros throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return errorCode;
-  }
-
-  @Override
-  @CalledByNative
-  public ContentBoxMeasurement getMeasurementFunc(String instanceId, long renderObjectPtr) {
-    ContentBoxMeasurement obj = null;
-    try {
-      obj = WXBridgeManager.getInstance().getMeasurementFunc(instanceId, renderObjectPtr);
-    } catch (Throwable e) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(TAG, "getMeasurementFunc throw exception:" + WXLogUtils.getStackTrace(e));
-      }
-    }
-    return obj;
-  }
-
-  @Override
-  public void bindMeasurementToRenderObject(long ptr){
-    nativeBindMeasurementToRenderObject(ptr);
-  }
-
-  @Override
-  public void setRenderContainerWrapContent(boolean wrap, String instanceId) {
-    nativeSetRenderContainerWrapContent(wrap, instanceId);
-  }
-
-  @Override
-  public long[] getFirstScreenRenderTime(String instanceId) {
-    return nativeGetFirstScreenRenderTime(instanceId);
-  }
-
-  @Override
-  public long[] getRenderFinishTime(String instanceId) {
-    return nativeGetRenderFinishTime(instanceId);
-  }
-
-  @Override
-  public void setDefaultHeightAndWidthIntoRootDom(String instanceId, float defaultWidth, float defaultHeight, boolean isWidthWrapContent, boolean isHeightWrapContent) {
-    nativeSetDefaultHeightAndWidthIntoRootDom(instanceId, defaultWidth, defaultHeight, isWidthWrapContent, isHeightWrapContent);
-  }
-
-  @Override
-  public void onInstanceClose(String instanceId) {
-    nativeOnInstanceClose(instanceId);
-  }
-
-  @Override
-  public void forceLayout(String instanceId) {
-    nativeForceLayout(instanceId);
-  }
-
-  @Override
-  public boolean notifyLayout(String instanceId) {
-    return nativeNotifyLayout(instanceId);
-  }
-
-  @Override
-  public void setStyleWidth(String instanceId, String ref, float value) {
-    nativeSetStyleWidth(instanceId, ref, value);
-  }
-
-  @Override
-  public void setMargin(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
-    nativeSetMargin(instanceId, ref, edge.ordinal(), value);
-  }
-
-  @Override
-  public void setPadding(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
-    nativeSetPadding(instanceId, ref, edge.ordinal(), value);
-  }
-
-  @Override
-  public void setPosition(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
-    nativeSetPosition(instanceId, ref, edge.ordinal(), value);
-  }
-
-  @Override
-  public void markDirty(String instanceId, String ref, boolean dirty) {
-    nativeMarkDirty(instanceId, ref, dirty);
-  }
-
-  @Override
-  public void setDeviceDisplay(String instanceId, float width, float height, float scale) {
-    nativeSetDeviceDisplay(instanceId, width, height, scale);
-  }
-
-  @Override
-  public void setStyleHeight(String instanceId, String ref, float value) {
-    nativeSetStyleHeight(instanceId, ref, value);
-  }
-
-  @Override
-  public void setInstanceRenderType(String instanceId, String renderType){
-    if(TextUtils.isEmpty(renderType)){
-       return;
-    }
-    nativeSetInstanceRenderType(instanceId, renderType);
-  }
-
-  @Override
-  public void setViewPortWidth(String instanceId,float viewPortWidth){
-    nativeSetViewPortWidth(instanceId,viewPortWidth);
-  }
-
-  @Override
-  public void removeInstanceRenderType(String instanceId){
-      nativeRemoveInstanceRenderType(instanceId);
-  }
-
-  @Override
-  public void setPageArgument(String instanceId, String key, String value){
-      nativeSetPageArgument(instanceId, key, value);
-  }
-
-  @Override
-  public void registerCoreEnv(String key, String value) {
-    nativeRegisterCoreEnv(key, value);
-  }
-
-  @CalledByNative
-  public void reportNativeInitStatus(String statusCode, String errorMsg) {
-    if (WXErrorCode.WX_JS_FRAMEWORK_INIT_SINGLE_PROCESS_SUCCESS.getErrorCode().equals(statusCode)
-            || WXErrorCode.WX_JS_FRAMEWORK_INIT_FAILED.getErrorCode().equals(statusCode)) {
-      IWXUserTrackAdapter userTrackAdapter = WXSDKManager.getInstance().getIWXUserTrackAdapter();
-      if (userTrackAdapter != null) {
-        Map<String, Serializable> params = new HashMap<>(3);
-        params.put(IWXUserTrackAdapter.MONITOR_ERROR_CODE, statusCode);
-        params.put(IWXUserTrackAdapter.MONITOR_ARG, "InitFrameworkNativeError");
-        params.put(IWXUserTrackAdapter.MONITOR_ERROR_MSG, errorMsg);
-        WXLogUtils.e("reportNativeInitStatus is running and errorCode is " + statusCode + " And errorMsg is " + errorMsg);
-        userTrackAdapter.commit(null, null, IWXUserTrackAdapter.INIT_FRAMEWORK, null, params);
-      }
-
-      return;
-    }
-
-    if (WXErrorCode.WX_JS_FRAMEWORK_INIT_FAILED_PARAMS_NULL.getErrorCode().equals(statusCode)) {
-      WXExceptionUtils.commitCriticalExceptionRT(null, WXErrorCode.WX_JS_FRAMEWORK_INIT_FAILED_PARAMS_NULL,
-              "WeexProxy::initFromParam()",
-              WXErrorCode.WX_JS_FRAMEWORK_INIT_FAILED_PARAMS_NULL.getErrorMsg() + ": " + errorMsg,
-              null);
-      return;
-    }
-
-    for (WXErrorCode e : WXErrorCode.values()) {
-      if (e.getErrorType().equals(WXErrorCode.ErrorType.NATIVE_ERROR)
-              && e.getErrorCode().equals(statusCode)) {
-        WXExceptionUtils.commitCriticalExceptionRT(null, e, "initFramework", errorMsg, null);
-        break;
-      }
-    }
-  }
-
-  public void fireEventOnDataRenderNode(String instanceId, String ref, String type, String data, String domChanges) {
-    nativeFireEventOnDataRenderNode(instanceId,ref,type,data, domChanges);
-  }
-
-  public void invokeCallbackOnDataRender(String instanceId, String callbackId, String data, boolean keepAlive) {
-    nativeInvokeCallbackOnDataRender(instanceId,callbackId,data, keepAlive);
-  }
-
-  public void registerModuleOnDataRenderNode(String data) {
-    nativeRegisterModuleOnDataRenderNode(data);
-  }
-
-  public void registerComponentOnDataRenderNode(String data) {
-    nativeRegisterComponentOnDataRenderNode(data);
-  }
-  public void reloadPageLayout(String instanceId){
-    nativeReloadPageLayout(instanceId);
-  }
-
-  public void setDeviceDisplayOfPage(String instanceId, float width, float height){
-    nativeSetDeviceDisplayOfPage(instanceId,width,height);
-  }
-
-  @CalledByNative
-  @Override
-  public void setPageDirty(String instanceId, boolean dirty) {
-    WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if(sdkInstance != null) {
-      sdkInstance.setPageDirty(dirty);
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXBridgeManager.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXBridgeManager.java
deleted file mode 100755
index 1730612..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXBridgeManager.java
+++ /dev/null
@@ -1,3683 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import static com.taobao.weex.bridge.WXModuleManager.createDomModule;
-
-import android.content.Context;
-import android.net.Uri;
-import android.os.Build;
-import android.os.Handler;
-import android.os.Handler.Callback;
-import android.os.Looper;
-import android.os.Message;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.support.annotation.UiThread;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-import android.util.Log;
-import android.util.Pair;
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.Script;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.adapter.IWXJSExceptionAdapter;
-import com.taobao.weex.adapter.IWXJsFileLoaderAdapter;
-import com.taobao.weex.adapter.IWXJscProcessManager;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.common.IWXBridge;
-import com.taobao.weex.common.IWXDebugConfig;
-import com.taobao.weex.common.WXConfig;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXException;
-import com.taobao.weex.common.WXJSBridgeMsgType;
-import com.taobao.weex.common.WXJSExceptionInfo;
-import com.taobao.weex.common.WXRefreshData;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.jsEngine.JSEngine;
-import com.taobao.weex.layout.ContentBoxMeasurement;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.performance.WXStateRecord;
-import com.taobao.weex.ui.WXComponentRegistry;
-import com.taobao.weex.ui.WXRenderManager;
-import com.taobao.weex.ui.action.ActionReloadPage;
-import com.taobao.weex.ui.action.BasicGraphicAction;
-import com.taobao.weex.ui.action.GraphicActionAddChildToRichtext;
-import com.taobao.weex.ui.action.GraphicActionAddElement;
-import com.taobao.weex.ui.action.GraphicActionAddEvent;
-import com.taobao.weex.ui.action.GraphicActionAppendTreeCreateFinish;
-import com.taobao.weex.ui.action.GraphicActionCreateBody;
-import com.taobao.weex.ui.action.GraphicActionCreateFinish;
-import com.taobao.weex.ui.action.GraphicActionLayout;
-import com.taobao.weex.ui.action.GraphicActionMoveElement;
-import com.taobao.weex.ui.action.GraphicActionRefreshFinish;
-import com.taobao.weex.ui.action.GraphicActionRemoveChildFromRichtext;
-import com.taobao.weex.ui.action.GraphicActionRemoveElement;
-import com.taobao.weex.ui.action.GraphicActionRemoveEvent;
-import com.taobao.weex.ui.action.GraphicActionRenderSuccess;
-import com.taobao.weex.ui.action.GraphicActionUpdateAttr;
-import com.taobao.weex.ui.action.GraphicActionUpdateRichtextAttr;
-import com.taobao.weex.ui.action.GraphicActionUpdateRichtextStyle;
-import com.taobao.weex.ui.action.GraphicActionUpdateStyle;
-import com.taobao.weex.ui.action.GraphicPosition;
-import com.taobao.weex.ui.action.GraphicSize;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.module.WXDomModule;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXFileUtils;
-import com.taobao.weex.utils.WXJsonUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import com.taobao.weex.utils.WXWsonJSONSwitch;
-import com.taobao.weex.utils.batch.BactchExecutor;
-import com.taobao.weex.utils.batch.Interceptor;
-import com.taobao.weex.utils.tools.LogDetail;
-import java.io.BufferedReader;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileReader;
-import java.io.InputStreamReader;
-import java.io.Serializable;
-import java.lang.reflect.Constructor;
-import java.lang.reflect.Method;
-import java.text.DateFormat;
-import java.text.SimpleDateFormat;
-import java.util.ArrayList;
-import java.util.Date;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Locale;
-import java.util.Map;
-import java.util.Stack;
-import java.util.concurrent.CountDownLatch;
-import java.util.concurrent.TimeUnit;
-import java.util.regex.Pattern;
-
-/**
- * Manager class for communication between JavaScript and Android.
- * <ol>
- * <li>
- * Handle Android to JavaScript call, can be one of the following
- * <ul>
- * <li>{@link #createInstance(String, String, Map, String)}</li>
- * <li>{@link #destroyInstance(String)}</li>
- * <li>{@link #refreshInstance(String, WXRefreshData)}</li>
- * <li>{@link #registerModules(Map)}</li>
- * <li>{@link #registerComponents(List)}</li>
- * <li>{@link #invokeCallJSBatch(Message)}</li>
- * </ul>
- * </li>
- * <li>
- * Handle JavaScript to Android call
- * </li>
- * <li>
- * Handle next tick of message.
- * </li>
- * </ol>
- */
-public class WXBridgeManager implements Callback, BactchExecutor {
-
-  private static Class clazz_debugProxy = null;
-  public static final String METHOD_CREATE_INSTANCE = "createInstance";
-  public static final String METHOD_CREATE_PAGE_WITH_CONTENT = "CreatePageWithContent";
-  public static final String METHOD_UPDATE_COMPONENT_WITH_DATA = "UpdateComponentData";
-  private static final String METHOD_POST_TASK_TO_MSG_LOOP = "PostTaskToMsgLoop";
-  private static final String METHOD_JSFM_NOT_INIT_IN_EAGLE_MODE = "JsfmNotInitInEagleMode";
-  public static final String METHOD_DESTROY_INSTANCE = "destroyInstance";
-  public static final String METHOD_CALL_JS = "callJS";
-  public static final String METHOD_SET_TIMEOUT = "setTimeoutCallback";
-  public static final String METHOD_REGISTER_MODULES = "registerModules";
-  public static final String METHOD_REGISTER_COMPONENTS = "registerComponents";
-  public static final String METHOD_FIRE_EVENT = "fireEvent";
-  public static final String METHD_FIRE_EVENT_SYNC = "fireEventSync";
-  public static final String METHD_COMPONENT_HOOK_SYNC = "componentHook";
-  public static final String METHOD_CALLBACK = "callback";
-  public static final String METHOD_REFRESH_INSTANCE = "refreshInstance";
-  public static final String METHOD_FIRE_EVENT_ON_DATA_RENDER_NODE = "fireEventOnDataRenderNode";
-  public static final String METHOD_NOTIFY_TRIM_MEMORY = "notifyTrimMemory";
-  public static final String METHOD_NOTIFY_SERIALIZE_CODE_CACHE =
-          "notifySerializeCodeCache";
-  public static final String METHOD_CREATE_INSTANCE_CONTEXT = "createInstanceContext";
-
-  public static final String KEY_METHOD = "method";
-  public static final String KEY_ARGS = "args";
-
-  // args
-  public static final String COMPONENT = "component";
-  public static final String REF = "ref";
-  public static final String MODULE = "module";
-  public static final String METHOD = "method";
-  public static final String KEY_PARAMS = "params";
-  public static final String ARGS = "args";
-  public static final String OPTIONS = "options";
-  public static final String INITLOGFILE = "/jsserver_start.log";
-  private static final String NON_CALLBACK = "-1";
-  private static final String UNDEFINED = "undefined";
-  private static final String BUNDLE_TYPE = "bundleType";
-  private static final String RENDER_STRATEGY = "renderStrategy";
-  private static final int INIT_FRAMEWORK_OK = 1;
-  private static final int CRASHREINIT = 50;
-  static volatile WXBridgeManager mBridgeManager;
-  private static long LOW_MEM_VALUE = 120;
-  public volatile static int reInitCount = 1;
-  private volatile static int sInitFrameWorkCount = 0;
-  private static String crashUrl = null;
-  private static long lastCrashTime = 0;
-
-  private static String mRaxApi = null;
-//  private static String mRaxExtApi = null;
-
-  // add for clound setting, default value is true
-  // can use it to control weex sandbox
-  // if true will open weex sandbox for multi context
-  private volatile static boolean isSandBoxContext = true;
-
-  // add for cloud setting, default value is false.
-  // weexcore use single process or not
-  private static boolean isUseSingleProcess = false;
-  // add for cloud setting, default value is false.
-  // jsEngine use multiThread or not
-  private volatile static boolean isJsEngineMultiThreadEnable = false;
-
-  public enum BundType {
-    Vue,
-    Rax,
-    Others
-  };
-
-  private static final boolean BRIDGE_LOG_SWITCH = false;
-
-  /**
-   * Whether JS Framework(main.js) has been initialized.
-   */
-  private volatile static boolean mInit = false;
-
-  private static String globalConfig = "none";
-  private static String GLOBAL_CONFIG_KEY = "global_switch_config";
-
-  private static Map<String, String> mWeexCoreEnvOptions = new HashMap<>();
-
-  /**
-   * package
-   **/
-  Handler mJSHandler;
-  /**
-   * next tick tasks, can set priority
-   */
-  private WXHashMap<String, ArrayList<WXHashMap<String, Object>>> mNextTickTasks = new WXHashMap<>();
-  /**
-   * JSThread
-   */
-  private WXThread mJSThread;
-  private IWXBridge mWXBridge;
-  private Object mWxDebugProxy;
-
-  private boolean mMock = false;
-
-  private List<Map<String, Object>> mRegisterComponentFailList = new ArrayList<>(8);
-  private List<Map<String, Object>> mRegisterModuleFailList = new ArrayList<>(8);
-  private List<String> mRegisterServiceFailList = new ArrayList<>(8);
-  private HashSet<String> mDestroyedInstanceId = new HashSet<>();
-  private StringBuilder mLodBuilder = new StringBuilder(50);
-  private Interceptor mInterceptor;
-  private WXParams mInitParams;
-
-  private WXBridgeManager() {
-    initWXBridge(WXEnvironment.sRemoteDebugMode);
-    mJSThread = new WXThread("WeexJSBridgeThread", this);
-    mJSHandler = mJSThread.getHandler();
-  }
-
-  public static WXBridgeManager getInstance() {
-    if (mBridgeManager == null) {
-      synchronized (WXBridgeManager.class) {
-        if (mBridgeManager == null) {
-          mBridgeManager = new WXBridgeManager();
-        }
-      }
-    }
-    return mBridgeManager;
-  }
-
-  public void setUseSingleProcess(final boolean flag) {
-    if (flag != isUseSingleProcess) {
-      isUseSingleProcess = flag;
-//      //we should reinit framework if js framework has been initialized
-//      if (isJSFrameworkInit()) {
-//        if (isJSThread()) {
-//          WXSDKEngine.reload();
-//        } else {
-//          post(new Runnable() {
-//            @Override
-//            public void run() {
-//              WXSDKEngine.reload();
-//            }
-//          });
-//        }
-//      }
-    }
-  }
-
-  public void onInteractionTimeUpdate(final String instanceId){
-    post(new Runnable() {
-      @Override
-      public void run() {
-        if (mWXBridge instanceof WXBridge ){
-          ((WXBridge)mWXBridge).nativeOnInteractionTimeUpdate(instanceId);
-        }
-      }
-    });
-  }
-
-  public boolean jsEngineMultiThreadEnable() {
-    return isJsEngineMultiThreadEnable;
-  }
-
-  public void checkJsEngineMultiThread() {
-    boolean flag = false;
-    IWXJscProcessManager wxJscProcessManager = WXSDKManager.getInstance().getWXJscProcessManager();
-    if(wxJscProcessManager!=null) {
-      flag = wxJscProcessManager.enableBackupThread();
-    }
-
-    if(flag == WXBridgeManager.isJsEngineMultiThreadEnable) {
-        return;
-    }
-
-    WXBridgeManager.isJsEngineMultiThreadEnable = flag;
-    //we should reinit framework if js framework has been initialized
-    if (isJSFrameworkInit()) {
-      if (isJSThread()) {
-        WXSDKEngine.reload();
-      } else {
-        post(new Runnable() {
-          @Override
-          public void run() {
-            WXSDKEngine.reload();
-          }
-        });
-      }
-    }
-  }
-  public void setSandBoxContext(final boolean flag) {
-    if (flag != isSandBoxContext) {
-      isSandBoxContext = flag;
-      // use diff context reinit jsf
-      if (isJSThread()) {
-
-        setJSFrameworkInit(false);
-        WXModuleManager.resetAllModuleState();
-        String jsf = "";
-        if (!isSandBoxContext) {
-          jsf = WXFileUtils.loadAsset("main.js", WXEnvironment.getApplication());
-        } else {
-          jsf = WXFileUtils.loadAsset("weex-main-jsfm.js", WXEnvironment.getApplication());
-        }
-        initFramework(jsf);
-        WXServiceManager.reload();
-        WXModuleManager.reload();
-        WXComponentRegistry.reload();
-      } else {
-        post(new Runnable() {
-          @Override
-          public void run() {
-            setJSFrameworkInit(false);
-            WXModuleManager.resetAllModuleState();
-            String jsf = "";
-            if (!isSandBoxContext) {
-              jsf = WXFileUtils.loadAsset("main.js", WXEnvironment.getApplication());
-            } else {
-              jsf = WXFileUtils.loadAsset("weex-main-jsfm.js", WXEnvironment.getApplication());
-            }
-            initFramework(jsf);
-            WXServiceManager.reload();
-            WXModuleManager.reload();
-            WXComponentRegistry.reload();
-          }
-        });
-      }
-    }
-  }
-
-  // setJSFrameworkInit and isJSFrameworkInit may use on diff thread
-  // use volatile
-  @RestrictTo(Scope.LIBRARY)
-  boolean isJSFrameworkInit() {
-    return mInit;
-  }
-
-  private void setJSFrameworkInit(boolean init) {
-    mInit = init;
-    WXStateRecord.getInstance().recoreJsfmInitHistory("setJsfmInitFlag:"+init);
-    if (init == true) {
-      onJsFrameWorkInitSuccees();
-      JSEngine.getInstance().engineInitFinished();
-    }
-  }
-
-  private void initWXBridge(boolean remoteDebug) {
-    if (remoteDebug && WXEnvironment.isApkDebugable()) {
-      WXEnvironment.sDebugServerConnectable = true;
-    }
-
-    if (WXEnvironment.sDebugServerConnectable && (WXEnvironment.isApkDebugable() || WXEnvironment.sForceEnableDevTool)) {
-      if (WXEnvironment.getApplication() != null) {
-        try {
-          if (clazz_debugProxy == null) {
-            clazz_debugProxy = Class.forName("com.taobao.weex.devtools.debug.DebugServerProxy");
-          }
-          if (clazz_debugProxy != null) {
-            Constructor constructor = clazz_debugProxy.getConstructor(Context.class, IWXDebugConfig.class);
-            if (constructor != null) {
-              mWxDebugProxy = constructor.newInstance(WXEnvironment.getApplication(),
-                      new IWXDebugConfig() {
-                        @Override
-                        public WXBridgeManager getWXJSManager() {
-                          return WXBridgeManager.this;
-                        }
-
-                        @Override
-                        public WXDebugJsBridge getWXDebugJsBridge() {
-                          return new WXDebugJsBridge();
-                        }
-                      });
-              if (mWxDebugProxy != null) {
-                Method method_start = clazz_debugProxy.getMethod("start");
-                if (method_start != null) {
-                  method_start.invoke(mWxDebugProxy);
-                }
-              }
-            }
-          }
-        } catch (Throwable e) {
-          //Ignore, It will throw Exception on Release environment
-        }
-        WXServiceManager.execAllCacheJsService();
-      } else {
-        WXLogUtils.e("WXBridgeManager", "WXEnvironment.sApplication is null, skip init Inspector");
-      }
-    }
-    if (remoteDebug && mWxDebugProxy != null) {
-      try {
-        if (clazz_debugProxy == null ) {
-          clazz_debugProxy = Class.forName("com.taobao.weex.devtools.debug.DebugServerProxy");
-        }
-        if (clazz_debugProxy != null) {
-          Method method_getWXBridge = clazz_debugProxy.getMethod("getWXBridge");
-          if (method_getWXBridge != null) {
-            mWXBridge = (IWXBridge) method_getWXBridge.invoke(mWxDebugProxy);
-          }
-        }
-      } catch (Throwable e) {
-        //Ignore, It will throw Exception on Release environment
-      }
-    } else {
-      mWXBridge = new WXBridge();
-    }
-  }
-
-  public String dumpIpcPageInfo(){
-    if (mWXBridge instanceof WXBridge){
-      return ((WXBridge)mWXBridge).nativeDumpIpcPageQueueInfo();
-    }
-    return "";
-  }
-
-  public boolean isRebootExceedLimit(){
-    return reInitCount > CRASHREINIT;
-  }
-
-  public void stopRemoteDebug() {
-    if (mWxDebugProxy != null) {
-      try {
-        if (clazz_debugProxy == null) {
-          clazz_debugProxy = Class.forName("com.taobao.weex.devtools.debug.DebugServerProxy");
-        }
-        if (clazz_debugProxy != null) {
-          Method method_stop = clazz_debugProxy.getMethod("stop", boolean.class);
-          if (method_stop != null) {
-            method_stop.invoke(mWxDebugProxy, true);
-          }
-        }
-      } catch (Throwable e) {
-        //Ignore, It will throw Exception on Release environment
-      }
-    }
-  }
-
-  public Object callModuleMethod(String instanceId, String moduleStr, String methodStr, JSONArray args) {
-    return callModuleMethod(instanceId, moduleStr, methodStr, args, null);
-  }
-
-  public Object callModuleMethod(String instanceId, String moduleStr, String methodStr, JSONArray args, JSONObject options) {
-    WXSDKInstance wxsdkInstance = WXSDKManager.getInstance()
-            .getSDKInstance(instanceId);
-    if (wxsdkInstance == null) {
-      return null;
-    }
-    if (wxsdkInstance.isNeedValidate()
-            && WXSDKManager.getInstance().getValidateProcessor() != null) {
-      WXValidateProcessor.WXModuleValidateResult validateResult = WXSDKManager
-              .getInstance().getValidateProcessor()
-              .onModuleValidate(wxsdkInstance, moduleStr, methodStr, args, options);
-      if (validateResult == null) {
-        return null;
-      }
-      if (validateResult.isSuccess) {
-        return WXModuleManager.callModuleMethod(instanceId, moduleStr, methodStr,
-                args);
-      } else {
-        JSONObject validateInfo = validateResult.validateInfo;
-        if (validateInfo != null) {
-          WXLogUtils.e("[WXBridgeManager] module validate fail. >>> " + validateInfo.toJSONString());
-        }
-        return validateInfo;
-      }
-    }
-    try {
-      return WXModuleManager.callModuleMethod(instanceId, moduleStr, methodStr, args);
-    }catch(NumberFormatException e){
-      ArrayMap<String, String> ext = new ArrayMap<>();
-      ext.put("moduleName", moduleStr);
-      ext.put("methodName", methodStr);
-      ext.put("args", args.toJSONString());
-      WXLogUtils.e("[WXBridgeManager] callNative : numberFormatException when parsing string to numbers in args", ext.toString());
-      return null;
-    }
-  }
-
-  /**
-   * Model switch. For now, debug model and release model are supported
-   */
-  public void restart() {
-    setJSFrameworkInit(false);
-    WXModuleManager.resetAllModuleState();
-    initWXBridge(WXEnvironment.sRemoteDebugMode);
-    mWXBridge.resetWXBridge(WXEnvironment.sRemoteDebugMode);
-  }
-
-  /**
-   * Set current Instance
-   *
-   * @param instanceId {@link WXSDKInstance#mInstanceId}
-   */
-  public synchronized void setStackTopInstance(final String instanceId) {
-    post(new Runnable() {
-
-      @Override
-      public void run() {
-        mNextTickTasks.setStackTopInstance(instanceId);
-      }
-    },instanceId, null, null);
-  }
-
-  @Override
-  public void post(Runnable r) {
-      postWithName(r,null,null);
-  }
-
-  public void postWithName(Runnable r, WXSDKInstance instance, String runnableName) {
-   Runnable secure = WXThread.secure(r,instance, runnableName);
-    if (mInterceptor != null && mInterceptor.take(secure)) {
-      //task is token by the interceptor
-      return;
-    }
-    if (mJSHandler == null) {
-      return;
-    }
-
-    mJSHandler.post(secure);
-  }
-
-  @Override
-  public void setInterceptor(Interceptor interceptor) {
-    mInterceptor = interceptor;
-  }
-
-  public void post(Runnable r, Object token, WXSDKInstance instance, String runnableName) {
-    if (mJSHandler == null) {
-      return;
-    }
-
-    Message m = Message.obtain(mJSHandler, WXThread.secure(r, instance, runnableName));
-    m.obj = token;
-    m.sendToTarget();
-  }
-
-  public void post(Runnable r, Object token) {
-    post(r, token, null, null);
-  }
-
-  public void postDelay(Runnable r,long delayMillis){
-    if (mJSHandler == null) {
-      return;
-    }
-    mJSHandler.postDelayed(WXThread.secure(r),delayMillis);
-  }
-
-  void setTimeout(String callbackId, String time) {
-    Message message = Message.obtain();
-    message.what = WXJSBridgeMsgType.SET_TIMEOUT;
-    TimerInfo timerInfo = new TimerInfo();
-    timerInfo.callbackId = callbackId;
-    timerInfo.time = (long) Float.parseFloat(time);
-    message.obj = timerInfo;
-
-    mJSHandler.sendMessageDelayed(message, timerInfo.time);
-  }
-
-  public void sendMessageDelayed(Message message, long delayMillis) {
-    if (message == null || mJSHandler == null || mJSThread == null
-            || !mJSThread.isWXThreadAlive() || mJSThread.getLooper() == null) {
-      return;
-    }
-    mJSHandler.sendMessageDelayed(message, delayMillis);
-  }
-
-  public void removeMessage(int what, Object obj) {
-    if (mJSHandler == null || mJSThread == null
-            || !mJSThread.isWXThreadAlive() || mJSThread.getLooper() == null) {
-      return;
-    }
-    mJSHandler.removeMessages(what, obj);
-  }
-
-  public Object callNativeModule(String instanceId, String module, String method, JSONArray arguments, Object options) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(module) || TextUtils.isEmpty(method)) {
-      WXLogUtils.d("[WXBridgeManager] call callNativeModule arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callNativeModule",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callNativeModule >>>> instanceId:").append(instanceId)
-              .append(", module:").append(module).append(", method:").append(method).append(", arguments:").append(arguments);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    try {
-      if (WXDomModule.WXDOM.equals(module)) {
-        WXDomModule dom = WXModuleManager.getDomModule(instanceId);
-        return dom.callDomMethod(method, arguments);
-      } else {
-        return callModuleMethod(instanceId, module,
-              method, arguments);
-      }
-    } catch (Exception e) {
-      String err = "[WXBridgeManager] callNative exception: " + WXLogUtils.getStackTrace(e);
-      WXLogUtils.e(err);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callNativeModule",
-              err, null);
-    }
-
-    return null;
-  }
-
-  public Object callNativeModule(String instanceId, String module, String method, JSONArray arguments, JSONObject options) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(module) || TextUtils.isEmpty(method)) {
-      WXLogUtils.d("[WXBridgeManager] call callNativeModule arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callNativeModule",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callNativeModule >>>> instanceId:").append(instanceId)
-              .append(", module:").append(module).append(", method:").append(method).append(", arguments:").append(arguments);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    try {
-      if (WXDomModule.WXDOM.equals(module)) {
-        WXDomModule dom = WXModuleManager.getDomModule(instanceId);
-        if(dom != null){
-          return dom.callDomMethod(method, arguments);
-        } else {
-          createDomModule(WXSDKManager.getInstance().getSDKInstance(instanceId));
-        }
-      } else {
-        return callModuleMethod(instanceId, module,
-              method, arguments, options);
-      }
-    } catch (Exception e) {
-      String err = "[WXBridgeManager] callNativeModule exception: " + WXLogUtils.getStackTrace(e);
-      WXLogUtils.e(err);
-    }
-
-    return null;
-  }
-
-  public Object callNativeComponent(String instanceId, String componentRef, String method, JSONArray arguments, Object options) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(componentRef) || TextUtils.isEmpty(method)) {
-      WXLogUtils.d("[WXBridgeManager] call callNativeComponent arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callNativeComponent",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callNativeComponent >>>> instanceId:").append(instanceId)
-              .append(", componentRef:").append(componentRef).append(", method:").append(method).append(", arguments:").append(arguments);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    try {
-      WXDomModule dom = WXModuleManager.getDomModule(instanceId);
-      if (null != dom){
-        dom.invokeMethod(componentRef, method, arguments);
-      }else {
-        WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-        if(null == instance || !instance.isDestroy()){
-          WXLogUtils.e("WXBridgeManager","callNativeComponent exception :null == dom ,method:"+method);
-        }
-      }
-
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callNativeComponent exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callNativeComponent",
-              WXLogUtils.getStackTrace(e), null);
-    }
-    return null;
-  }
-
-  /**
-   * Dispatch the native task to be executed.
-   *
-   * @param instanceId {@link WXSDKInstance#mInstanceId}
-   * @param tasks      tasks to be executed
-   * @param callback   next tick id
-   */
-  public int callNative(String instanceId, JSONArray tasks, String callback) {
-
-    if (TextUtils.isEmpty(instanceId) || tasks == null) {
-      WXLogUtils.d("[WXBridgeManager] call callNative arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callNative",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callNative >>>> instanceId:").append(instanceId)
-              .append(", tasks:").append(tasks).append(", callback:").append(callback);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-
-    long parseNanos = System.nanoTime();
-    JSONArray array = tasks;
-    parseNanos = System.nanoTime() - parseNanos;
-
-    if (null != array && array.size() > 0) {
-      int size = array.size();
-      try {
-        JSONObject task;
-        for (int i = 0; i < size; ++i) {
-          task = (JSONObject) array.get(i);
-          if (task != null && WXSDKManager.getInstance().getSDKInstance(instanceId) != null) {
-            Object module = task.get(MODULE);
-            if (module != null) {
-              if (WXDomModule.WXDOM.equals(module)) {
-                WXDomModule dom = WXModuleManager.getDomModule(instanceId);
-                dom.callDomMethod(task, parseNanos);
-              } else {
-                JSONObject optionObj = task.getJSONObject(OPTIONS);
-                WXStateRecord.getInstance().recordAction(instanceId,"callModuleMethod:"+instanceId+","+module+","+task.get(METHOD));
-                callModuleMethod(instanceId, (String) module,
-                        (String) task.get(METHOD), (JSONArray) task.get(ARGS), optionObj);
-              }
-            } else if (task.get(COMPONENT) != null) {
-              WXDomModule dom = WXModuleManager.getDomModule(instanceId);
-              WXStateRecord.getInstance().recordAction(instanceId,"callDomMethod:"+instanceId+","+task.get(METHOD));
-              dom.invokeMethod((String) task.get(REF), (String) task.get(METHOD), (JSONArray) task.get(ARGS));
-            } else {
-              throw new IllegalArgumentException("unknown callNative");
-            }
-          }
-        }
-      } catch (Exception e) {
-        WXLogUtils.e("[WXBridgeManager] callNative exception: ", e);
-        WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-                WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callNative",
-                WXLogUtils.getStackTrace(e) , null);
-      }
-    }
-
-    if (UNDEFINED.equals(callback) || NON_CALLBACK.equals(callback)) {
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-    // get next tick
-    getNextTick(instanceId, callback);
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  // callUpdateFinish
-  public int callUpdateFinish(String instanceId, String callback) {
-
-    if (TextUtils.isEmpty(instanceId)) {
-      WXLogUtils.d("[WXBridgeManager] call callUpdateFinish arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateFinish",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callUpdateFinish >>>> instanceId:").append(instanceId)
-              .append(", callback:").append(callback);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      if (WXSDKManager.getInstance().getSDKInstance(instanceId) != null) {
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callUpdateFinish exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateFinish",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    if (callback == null || callback.isEmpty() || UNDEFINED.equals(callback) || NON_CALLBACK.equals(callback)) {
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-    // get next tick
-    getNextTick(instanceId, callback);
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  // callRefreshFinish
-  public int callRefreshFinish(String instanceId, String callback) {
-
-    if (TextUtils.isEmpty(instanceId)) {
-      WXLogUtils.d("[WXBridgeManager] call callRefreshFinish arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRefreshFinish",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callRefreshFinish >>>> instanceId:").append(instanceId)
-              .append(", callback:").append(callback);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-        WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-        if (instance != null) {
-          GraphicActionRefreshFinish action = new GraphicActionRefreshFinish(instance);
-          WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(instanceId, action);
-        }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callRefreshFinish exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRefreshFinish",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    if (UNDEFINED.equals(callback) || NON_CALLBACK.equals(callback)) {
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-    // get next tick
-    getNextTick(instanceId, callback);
-    return IWXBridge.INSTANCE_RENDERING;
-
-  }
-
-  public int callReportCrashReloadPage(String instanceId, String crashFile) {
-    boolean isCrashFileEmpty = TextUtils.isEmpty(crashFile);
-    try {
-      String url = null;
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        url = instance.getBundleUrl();
-        instance.setHasException(true);
-      }
-      Map<String,String> extInfo = new HashMap<>(2);
-      extInfo.put("weexCoreThreadStackTrace:",WXBridgeManager.getInstance().getWeexCoreThreadStackTrace());
-      extInfo.put("wxStateInfo",WXStateRecord.getInstance().getStateInfo().toString());
-
-      if(!isCrashFileEmpty) {
-        try {
-            if (WXEnvironment.getApplication() != null) {
-                crashFile = mInitParams.getCrashFilePath() + crashFile;
-                Log.d("jsengine", "callReportCrashReloadPage crashFile:" + crashFile);
-            }
-        } catch (Throwable e) {
-          WXLogUtils.e(WXLogUtils.getStackTrace(e));
-        }
-        WXStateRecord.getInstance().onJSCCrash(TextUtils.isEmpty(instanceId)?"null":instanceId);
-        callReportCrash(crashFile, instanceId, url,extInfo);
-      } else {
-        WXStateRecord.getInstance().onJSEngineReload(TextUtils.isEmpty(instanceId)?"null":instanceId);
-         commitJscCrashAlarmMonitor(IWXUserTrackAdapter.JS_BRIDGE, WXErrorCode.WX_ERR_RELOAD_PAGE, "reboot jsc Engine", instanceId, url,extInfo);
-      }
-      JSEngine.getInstance().engineCrashed();
-      WXLogUtils.e("reInitCount:"+reInitCount);
-
-      if (reInitCount > CRASHREINIT) {
-        WXExceptionUtils.commitCriticalExceptionRT("jsEngine", WXErrorCode.WX_ERR_RELOAD_PAGE_EXCEED_LIMIT,
-            "callReportCrashReloadPage","reInitCount:"+reInitCount,extInfo);
-        return IWXBridge.INSTANCE_RENDERING_ERROR;
-      }
-      reInitCount++;
-      // reinit frame work
-      setJSFrameworkInit(false);
-      WXModuleManager.resetAllModuleState();
-      initScriptsFramework("");
-
-      if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-        return IWXBridge.DESTROY_INSTANCE;
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callReportCrashReloadPage exception: ", e);
-    }
-    try {
-
-      if (WXSDKManager.getInstance().getSDKInstance(instanceId) != null) {
-        boolean reloadThisInstance = shouldReloadCurrentInstance(
-                WXSDKManager.getInstance().getSDKInstance(instanceId).getBundleUrl());
-        new ActionReloadPage(instanceId, reloadThisInstance).executeAction();
-      }
-
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callReloadPage exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callReportCrashReloadPage",
-              WXLogUtils.getStackTrace(e), null);
-    }
-    return IWXBridge.INSTANCE_RENDERING_ERROR;
-  }
-
-  public boolean shouldReloadCurrentInstance(String aUrl) {
-    long time = System.currentTimeMillis();
-    String bizUrl = aUrl;
-    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
-    if (adapter != null) {
-        boolean check_biz_url = Boolean.parseBoolean(adapter
-                .getConfig("android_weex_ext_config",
-                        "check_biz_url",
-                        "true"));
-        WXLogUtils.e("check_biz_url : " + check_biz_url);
-        if(check_biz_url && !TextUtils.isEmpty(aUrl)) {
-            Uri uri = Uri.parse(aUrl);
-            if(uri != null) {
-                bizUrl = uri.buildUpon().clearQuery().build().toString();
-            }
-        }
-    }
-
-    if (crashUrl == null ||
-            (crashUrl != null && !crashUrl.equals(bizUrl)) ||
-            ((time - lastCrashTime) > 15000)) {
-      crashUrl = bizUrl;
-      lastCrashTime = time;
-      return true;
-    }
-    lastCrashTime = time;
-    return false;
-  }
-
-  public void callReportCrash(String crashFile, final String instanceId, final String url,final Map<String,String> extInfo) {
-    // statistic weex core process crash
-    Date date = new Date();
-    DateFormat format = new SimpleDateFormat("yyyyMMddHHmmss", Locale.US);
-    String time = format.format(date);
-    final String origin_filename = crashFile + "." + time;
-    File oldfile = new File(crashFile);
-    File newfile = new File(origin_filename);
-    if (oldfile.exists()) {
-      oldfile.renameTo(newfile);
-    }
-    Thread t = new Thread(new Runnable() {
-      public void run() {
-        try {
-          File file = new File(origin_filename);
-          if (file.exists()) {
-            if (file.length() > 0) {
-              StringBuilder result = new StringBuilder();
-              try {
-                BufferedReader br = new BufferedReader(new FileReader(origin_filename));
-                String s = null;
-                // boolean foundStart = false;
-                while ((s = br.readLine()) != null) {
-                  if ("".equals(s)) {
-                    continue;
-                  }
-                  // if (("r0:").equals(s)) {
-                  //  break;
-                  // }
-                  result.append(s + "\n");
-                }
-                commitJscCrashAlarmMonitor(IWXUserTrackAdapter.JS_BRIDGE, WXErrorCode.WX_ERR_JSC_CRASH, result.toString(), instanceId, url,extInfo);
-                br.close();
-              } catch (Exception e) {
-                WXLogUtils.e(WXLogUtils.getStackTrace(e));
-              }
-            } else {
-              WXLogUtils.e("[WXBridgeManager] callReportCrash crash file is empty");
-            }
-            if(!WXEnvironment.isApkDebugable())
-              file.delete();
-          }
-        } catch (Throwable throwable) {
-          WXLogUtils.e("[WXBridgeManager] callReportCrash exception: ", throwable);
-        }
-      }
-    });
-    t.start();
-  }
-
-  private void getNextTick(final String instanceId, final String callback) {
-    addJSTask(METHOD_CALLBACK, instanceId, callback, "{}");
-    sendMessage(instanceId, WXJSBridgeMsgType.CALL_JS_BATCH);
-  }
-
-  private void getNextTick(final String instanceId) {
-    addJSTask(METHOD_CALLBACK, instanceId, "", "{}");
-    sendMessage(instanceId, WXJSBridgeMsgType.CALL_JS_BATCH);
-  }
-
-  public String syncExecJsOnInstanceWithResult(final String instanceId, final String js, final int type) {
-    final CountDownLatch waitLatch = new CountDownLatch(1);
-    EventResult callback = new EventResult(){
-      @Override
-      public void onCallback(Object result) {
-        super.onCallback(result);
-        waitLatch.countDown();
-      }
-    };
-    try{
-      execJSOnInstance(callback, instanceId, js, type);
-      waitLatch.await(100, TimeUnit.MILLISECONDS);
-      if (callback != null && callback.getResult() != null) {
-        return  callback.getResult().toString();
-      }
-      return "";
-    }catch (Throwable e){
-      WXLogUtils.e("syncCallExecJsOnInstance", e);
-      return  "";
-    }
-  }
-
-  public void loadJsBundleInPreInitMode(final String instanceId, final String js){
-    post(new Runnable() {
-      @Override
-      public void run() {
-        invokeExecJSOnInstance(instanceId, js, -1);
-        WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
-        if (null != instance && instance.isPreInitMode()){
-          instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_END);
-          instance.getApmForInstance().onStageWithTime(WXInstanceApm.KEY_PAGE_STAGES_END_EXCUTE_BUNDLE,WXUtils.getFixUnixTime()+600);
-        }
-      }
-    });
-  }
-
-  /**
-   * ref, type, data, domChanges
-   * */
-  public EventResult syncCallJSEventWithResult(final String method, final String instanceId, final List<Object> params, final Object... args) {
-    final CountDownLatch waitLatch = new CountDownLatch(1);
-    EventResult callback = new EventResult(){
-      @Override
-      public void onCallback(Object result) {
-        super.onCallback(result);
-        waitLatch.countDown();
-      }
-    };
-    try{
-      asyncCallJSEventWithResult(callback, method, instanceId, params, args);
-      waitLatch.await(100, TimeUnit.MILLISECONDS);
-      return  callback;
-    }catch (Exception e){
-      WXLogUtils.e("syncCallJSEventWithResult", e);
-      return  callback;
-    }
-  }
-
-  public void asyncCallJSEventVoidResult(final String method, final String instanceId, final List<Object> params, final Object... args) {
-    post(new Runnable() {
-      @Override
-      public void run() {
-        try{
-          if (args == null || args.length == 0) {
-            return;
-          }
-
-          ArrayList<Object> argsList = new ArrayList<>();
-          for (Object arg : args) {
-            argsList.add(arg);
-          }
-          if (params != null) {
-            ArrayMap map = new ArrayMap(4);
-            map.put(KEY_PARAMS, params);
-            argsList.add(map);
-          }
-
-          WXHashMap<String, Object> task = new WXHashMap<>();
-          task.put(KEY_METHOD, method);
-          task.put(KEY_ARGS, argsList);
-          Object[] tasks = {task};
-          WXJSObject[] jsArgs = {
-                  new WXJSObject(WXJSObject.String, instanceId),
-                  WXWsonJSONSwitch.toWsonOrJsonWXJSObject(tasks)};
-          invokeExecJS(String.valueOf(instanceId), null, METHOD_CALL_JS, jsArgs, true);
-          jsArgs[0] = null;
-          jsArgs = null;
-        }catch (Exception e){
-          WXLogUtils.e("asyncCallJSEventVoidResult" , e);
-        }
-      }
-    });
-  }
-
-  /**
-   * aync call js event and return result in eventResult callback
-   * */
-  private void asyncCallJSEventWithResult(final EventResult eventCallback, final String method, final String instanceId, final List<Object> params, final Object... args) {
-    post(new Runnable() {
-      @Override
-      public void run() {
-        Object result = null;
-        try{
-          if (args == null || args.length == 0) {
-            return;
-          }
-
-          ArrayList<Object> argsList = new ArrayList<>();
-          for (Object arg : args) {
-            argsList.add(arg);
-          }
-          if (params != null) {
-            ArrayMap map = new ArrayMap(4);
-            map.put(KEY_PARAMS, params);
-            argsList.add(map);
-          }
-
-          WXHashMap<String, Object> task = new WXHashMap<>();
-          task.put(KEY_METHOD, method);
-          task.put(KEY_ARGS, argsList);
-          Object[] tasks = {task};
-          WXJSObject[] jsArgs = {
-                  new WXJSObject(WXJSObject.String, instanceId),
-                  WXWsonJSONSwitch.toWsonOrJsonWXJSObject(tasks)};
-          ResultCallback<byte[]> resultCallback = null;
-          if (eventCallback != null) {
-            resultCallback = new ResultCallback<byte[]>() {
-              @Override
-              public void onReceiveResult(byte[] result) {
-                JSONArray arrayResult = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(result);
-                if(arrayResult != null && arrayResult.size() > 0){
-                  eventCallback.onCallback(arrayResult.get(0));
-                }
-              }
-            };
-          }
-          invokeExecJSWithCallback(String.valueOf(instanceId), null, METHOD_CALL_JS,
-                  jsArgs, resultCallback, true);
-          jsArgs[0] = null;
-        }catch (Exception e){
-          WXLogUtils.e("asyncCallJSEventWithResult" , e);
-        }
-      }
-    });
-  }
-
-  private void addJSEventTask(final String method, final String instanceId, final List<Object> params, final Object... args) {
-    post(new Runnable() {
-      @Override
-      public void run() {
-        if (args == null || args.length == 0) {
-          return;
-        }
-
-        ArrayList<Object> argsList = new ArrayList<>();
-        for (Object arg : args) {
-          argsList.add(arg);
-        }
-        if (params != null) {
-          ArrayMap map = new ArrayMap(4);
-          map.put(KEY_PARAMS, params);
-          argsList.add(map);
-        }
-
-        WXHashMap<String, Object> task = new WXHashMap<>();
-        task.put(KEY_METHOD, method);
-        task.put(KEY_ARGS, argsList);
-
-
-        if (mNextTickTasks.get(instanceId) == null) {
-          ArrayList<WXHashMap<String, Object>> list = new ArrayList<>();
-          list.add(task);
-          mNextTickTasks.put(instanceId, list);
-        } else {
-          mNextTickTasks.get(instanceId).add(task);
-        }
-      }
-    });
-  }
-
-  private void addJSTask(final String method, final String instanceId, final Object... args) {
-    addJSEventTask(method, instanceId, null, args);
-  }
-
-  private void sendMessage(String instanceId, int what) {
-    Message msg = Message.obtain(mJSHandler);
-    msg.obj = instanceId;
-    msg.what = what;
-    msg.sendToTarget();
-  }
-
-  /**
-   * Initialize JavaScript framework
-   *
-   * @param framework String representation of the framework to be init.
-   */
-  public synchronized void initScriptsFramework(String framework) {
-    Message msg = mJSHandler.obtainMessage();
-    msg.obj = framework;
-    msg.what = WXJSBridgeMsgType.INIT_FRAMEWORK;
-    msg.setTarget(mJSHandler);
-    msg.sendToTarget();
-  }
-
-  @Deprecated
-  public void fireEvent(final String instanceId, final String ref,
-                        final String type, final Map<String, Object> data) {
-    this.fireEvent(instanceId, ref, type, data, null);
-  }
-
-  /**
-   * Do not direct invoke this method in Components, use {@link WXSDKInstance#fireEvent(String, String, Map, Map)} instead.
-   *
-   * @param instanceId
-   * @param ref
-   * @param type
-   * @param data
-   * @param domChanges
-   */
-  @Deprecated
-  public void fireEvent(final String instanceId, final String ref,
-                        final String type, final Map<String, Object> data, final Map<String, Object> domChanges) {
-    fireEventOnNode(instanceId, ref, type, data, domChanges);
-  }
-
-  /**
-   * Notify the JavaScript about the event happened on Android
-   */
-  public void fireEventOnNode(final String instanceId, final String ref,
-                              final String type, final Map<String, Object> data, final Map<String, Object> domChanges) {
-    fireEventOnNode(instanceId, ref, type, data, domChanges, null, null);
-  }
-
-  /**
-   * Notify the JavaScript about the event happened on Android
-   */
-  public void fireEventOnNode(final String instanceId, final String ref,
-                              final String type, final Map<String, Object> data,
-                              final Map<String, Object> domChanges, List<Object> params){
-    fireEventOnNode(instanceId, ref, type, data, domChanges, params, null);
-  }
-
-  public void fireEventOnNode(final String instanceId, final String ref,
-                              final String type, final Map<String, Object> data,
-                              final Map<String, Object> domChanges, List<Object> params,  EventResult callback) {
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)
-            || TextUtils.isEmpty(type) || mJSHandler == null) {
-      return;
-    }
-    if (!checkMainThread()) {
-      throw new WXRuntimeException(
-              "fireEvent must be called by main thread");
-    }
-    WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
-    if (instance != null && (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER ||
-            instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY)) {
-      fireEventOnDataRenderNode(instanceId, ref, type, data, domChanges);
-    } else {
-      if(callback == null) {
-        addJSEventTask(METHOD_FIRE_EVENT, instanceId, params, ref, type, data, domChanges);
-        sendMessage(instanceId, WXJSBridgeMsgType.CALL_JS_BATCH);
-      }else{
-        asyncCallJSEventWithResult(callback, METHD_FIRE_EVENT_SYNC, instanceId, params, ref, type, data, domChanges);
-      }
-    }
-  }
-
-  private void fireEventOnDataRenderNode(final String instanceId, final String ref,
-                                         final String type, final Map<String, Object> data, final Map<String, Object> domChanges) {
-    mJSHandler.postDelayed(WXThread.secure(new Runnable() {
-      @Override
-      public void run() {
-        try {
-          WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-          long start = System.currentTimeMillis();
-          if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.d("fireEventOnDataRenderNode >>>> instanceId:" + instanceId
-                + ", data:" + data);
-          }
-          if (mWXBridge instanceof WXBridge) {
-            ((WXBridge) mWXBridge).fireEventOnDataRenderNode(instanceId, ref, type,
-                (data == null || data.isEmpty()) ? "{}" : JSON.toJSONString(data),
-                (domChanges == null || domChanges.isEmpty()) ? "{}" : JSON.toJSONString(domChanges));
-          }
-          WXLogUtils.renderPerformanceLog("fireEventOnDataRenderNode", System.currentTimeMillis() - start);
-        } catch (Throwable e) {
-          String err = "[WXBridgeManager] fireEventOnDataRenderNode " + WXLogUtils.getStackTrace(e);
-          WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "fireEventOnDataRenderNode",
-              err, null);
-          WXLogUtils.e(err);
-        }
-      }
-    }), 0);
-  }
-
-  private boolean checkMainThread() {
-    return Looper.myLooper() == Looper.getMainLooper();
-  }
-
-
-  /**
-   * Invoke JavaScript callback. Use {@link JSCallback} instead.
-   *
-   * @see #callback(String, String, String)
-   */
-  @Deprecated
-  public void callback(String instanceId, String callback, String data) {
-    callback(instanceId, callback, data, false);
-  }
-
-  /**
-   * Invoke JavaScript callback. Use {@link JSCallback} instead.
-   */
-  @Deprecated
-  public void callback(final String instanceId, final String callback,
-                       final Map<String, Object> data) {
-    callback(instanceId, callback, data, false);
-  }
-
-  /**
-   * Use {@link JSCallback} instead.
-   *
-   * @param instanceId Weex Instance Id
-   * @param callback   callback referenece handle
-   * @param data       callback data
-   * @param keepAlive  if keep callback instance alive for later use
-   */
-  @Deprecated
-  public void callback(final String instanceId, final String callback,
-                       final Object data, boolean keepAlive) {
-    callbackJavascript(instanceId, callback, data, keepAlive);
-  }
-
-  /**
-   * Callback to Javascript function.
-   *
-   * @param instanceId Weex Instance Id
-   * @param callback   callback referenece handle
-   * @param data       callback data
-   * @param keepAlive  if keep callback instance alive for later use
-   */
-  void callbackJavascript(final String instanceId, final String callback,
-                          final Object data, boolean keepAlive) {
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(callback)
-            || mJSHandler == null) {
-      return;
-    }
-
-    WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
-    if (instance != null && (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY)) {
-      callbackJavascriptOnDataRender(instanceId, callback, data, keepAlive);
-    } else {
-      addJSTask(METHOD_CALLBACK, instanceId, callback, data, keepAlive);
-      sendMessage(instanceId, WXJSBridgeMsgType.CALL_JS_BATCH);
-    }
-  }
-
-  void callbackJavascriptOnDataRender(final String instanceId, final String callback, final Object data, final boolean keepAlive){
-    mJSHandler.postDelayed(WXThread.secure(new Runnable() {
-      @Override
-      public void run() {
-        try {
-          long start = System.currentTimeMillis();
-          String data_str = JSON.toJSONString(data);
-          if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.d("callbackJavascriptOnDataRender >>>> instanceId:" + instanceId
-                + ", data:" + data_str);
-          }
-          if (mWXBridge instanceof WXBridge) {
-            ((WXBridge) mWXBridge).invokeCallbackOnDataRender(instanceId, callback,data_str ,keepAlive);
-          }
-          WXLogUtils.renderPerformanceLog("callbackJavascriptOnDataRender", System.currentTimeMillis() - start);
-        } catch (Throwable e) {
-          String err = "[WXBridgeManager] callbackJavascriptOnDataRender " + WXLogUtils.getStackTrace(e);
-          WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callbackJavascriptOnDataRender",
-              err, null);
-          WXLogUtils.e(err);
-        }
-      }
-    }), 0);
-  }
-
-  /**
-   * Refresh instance
-   */
-  public void refreshInstance(final String instanceId, final WXRefreshData jsonData) {
-    if (TextUtils.isEmpty(instanceId) || jsonData == null) {
-      return;
-    }
-    mJSHandler.postDelayed(WXThread.secure(new Runnable() {
-      @Override
-      public void run() {
-        invokeRefreshInstance(instanceId, jsonData);
-      }
-    }), 0);
-  }
-
-  private void invokeRefreshInstance(String instanceId, WXRefreshData refreshData) {
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (!isSkipFrameworkInit(instanceId) && !isJSFrameworkInit()) {
-        if (instance != null) {
-          instance.onRenderError(
-                  WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-                  WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg()
-                          + "invokeRefreshInstance FAILED for JSFrameworkInit FAILED, intance will invoke instance.onRenderError"
-          );
-        }
-        String err = "[WXBridgeManager] invokeRefreshInstance: framework.js uninitialized.";
-        WXLogUtils.e(err);
-        return;
-      }
-      long start = System.currentTimeMillis();
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.d("refreshInstance >>>> instanceId:" + instanceId
-                + ", data:" + refreshData.data + ", isDirty:" + refreshData.isDirty);
-      }
-
-      if (refreshData.isDirty) {
-        return;
-      }
-      WXJSObject instanceIdObj = new WXJSObject(WXJSObject.String,
-              instanceId);
-      WXJSObject dataObj = new WXJSObject(WXJSObject.JSON,
-              refreshData.data == null ? "{}" : refreshData.data);
-      WXJSObject[] args = {instanceIdObj, dataObj};
-      mWXBridge.refreshInstance(instanceId, null, METHOD_REFRESH_INSTANCE, args);
-    } catch (Throwable e) {
-      String err = "[WXBridgeManager] invokeRefreshInstance " + WXLogUtils.getStackTrace(e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "invokeRefreshInstance",
-              err, null);
-      WXLogUtils.e(err);
-    }
-  }
-
-  public void commitJscCrashAlarmMonitor(final String type, final WXErrorCode errorCode, String errMsg,
-                                         String instanceId, String url,Map<String, String> extInfo) {
-    if (TextUtils.isEmpty(type) || errorCode == null) {
-      return;
-    }
-
-    Log.d("ReportCrash", " commitJscCrashAlarmMonitor errMsg " + errMsg);
-    String method = "callReportCrash";
-    String exception = "weex core process crash and restart exception";
-    Map<String, String> extParams = new HashMap<String, String>();
-    extParams.put("jscCrashStack", errMsg);
-    if (null != extInfo){
-      extParams.putAll(extInfo);
-    }
-    IWXJSExceptionAdapter adapter = WXSDKManager.getInstance().getIWXJSExceptionAdapter();
-    if (adapter != null) {
-      WXJSExceptionInfo jsException = new WXJSExceptionInfo(instanceId, url, errorCode, method, exception, extParams);
-      adapter.onJSException(jsException);
-      // if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.e(jsException.toString());
-      // }
-    }
-  }
-
-  private boolean isSkipFrameworkInit(String instanceId) {
-    final WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    return isSkipFrameworkInit(instance);
-  }
-
-  private boolean isSkipFrameworkInit(WXSDKInstance instance) {
-    if (instance == null) {
-      return false;
-    }
-    return instance.skipFrameworkInit();
-  }
-
-  /**
-   * Create instance.
-   */
-  public void createInstance(final String instanceId, final String template,
-                             final Map<String, Object> options, final String data) {
-    createInstance(instanceId, new Script(template), options, data);
-  }
-
-  public void setLogLevel(final int level, final boolean isPerf) {
-    post(new Runnable() {
-      @Override
-      public void run() {
-        if(mWXBridge != null) {
-          mWXBridge.setLogType(level, isPerf);
-        }
-      }
-    });
-  }
-
-  public void createInstance(final String instanceId, final Script template,
-                             final Map<String, Object> options, final String data) {
-    final WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (instance == null) {
-      WXLogUtils.e("WXBridgeManager", "createInstance failed, SDKInstance does not exist");
-      return;
-    }
-    if (TextUtils.isEmpty(instanceId) || template == null || template.isEmpty() || mJSHandler == null) {
-      instance.onRenderError(
-              WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-              WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg() +
-                      " instanceId==" + instanceId + " template ==" + template + " mJSHandler== " + mJSHandler.toString()
-      );
-
-      instance.getApmForInstance().onStage("createInstance failed return; "+TextUtils.isEmpty(instanceId)+ ","+template.isEmpty()+","+(mJSHandler ==null));
-      return;
-    }
-
-    if (!isSkipFrameworkInit(instanceId) && !isJSFrameworkInit() && reInitCount == 1 && !WXEnvironment.sDebugServerConnectable) {
-      instance.onRenderError(
-              WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-              WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg() +
-                      " isJSFrameworkInit==" + isJSFrameworkInit() + " reInitCount == 1" );
-      instance.getApmForInstance().onStage("createInstance failed jsfm isn't init return;");
-      post(new Runnable() {
-        @Override
-        public void run() {
-          initFramework("");
-        }
-      }, instanceId, instance,"initFrameworkInCreateInstance");
-      return;
-    }
-
-    WXModuleManager.createDomModule(instance);
-    instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_START);
-    post(new Runnable() {
-      @Override
-      public void run() {
-        instance.getApmForInstance().onStage("wxLoadBundleStartOnJsThread");
-        long start = System.currentTimeMillis();
-        mWXBridge.setPageArgument(instanceId, "renderTimeOrigin", String.valueOf(instance.getWXPerformance().renderTimeOrigin));
-        mWXBridge.setInstanceRenderType(instance.getInstanceId(), instance.getRenderType());
-        invokeCreateInstance(instance, template, options, data);
-        long end = System.currentTimeMillis();
-        instance.getWXPerformance().callCreateInstanceTime = end - start;
-        instance.getWXPerformance().communicateTime =  instance.getWXPerformance().callCreateInstanceTime;
-      }
-    }, instanceId, instance,"createInstance");
-  }
-
-  private void invokeCreateInstance(@NonNull WXSDKInstance instance, Script template,
-                                    Map<String, Object> options, String data) {
-    // add for sandbox, will delete on sandbox ok
-    if (!isSkipFrameworkInit(instance)){
-      initFramework("");
-    }
-
-    if (mMock) {
-      mock(instance.getInstanceId());
-    } else {
-      if (!isSkipFrameworkInit(instance) && !isJSFrameworkInit()) {
-        String err = "[WXBridgeManager] invokeCreateInstance: framework.js uninitialized.";
-        instance.onRenderError(
-                WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-                WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg()
-        );
-        WXLogUtils.e(err);
-        instance.getApmForInstance().onStage("framework.js uninitialized and return");
-        return;
-      }
-
-      WXModuleManager.registerWhenCreateInstance();
-
-      try {
-        BundType type = BundType.Others;
-        try {
-          long start = System.currentTimeMillis();
-          type = getBundleType(instance.getBundleUrl(), template.getContent());
-
-          if (WXEnvironment.isOpenDebugLog()) {
-            long end = System.currentTimeMillis();
-            WXLogUtils.e("end getBundleType type:" + type.toString() + " time:" + (end - start));
-          }
-        } catch (Throwable e) {
-          WXLogUtils.e(WXLogUtils.getStackTrace(e));
-        }
-
-        try {
-          if (options == null) {
-            options = new HashMap<>();
-          }
-          // on file there is { "framework": "Vue" } or others
-          if (options.get(BUNDLE_TYPE) == null) {
-            // may vue or Rax
-            if (type == BundType.Vue) {
-              options.put(BUNDLE_TYPE, "Vue");
-            } else if (type == BundType.Rax) {
-              options.put(BUNDLE_TYPE, "Rax");
-            } else {
-              options.put(BUNDLE_TYPE, "Others");
-            }
-            Object recordBundleType = options.get(BUNDLE_TYPE);
-            if (recordBundleType instanceof String && "Others".equalsIgnoreCase((String)recordBundleType)){
-              //same as iOS record
-              recordBundleType = "other";
-            }
-            if (null != recordBundleType){
-              instance.getApmForInstance().addProperty(WXInstanceApm.KEY_PAGE_PROPERTIES_BUNDLE_TYPE, recordBundleType);
-            }
-          }
-          if (options.get("env") == null) {
-            options.put("env", mInitParams.toMap());
-          }
-        } catch (Throwable e) {
-          WXLogUtils.e(WXLogUtils.getStackTrace(e));
-        }
-        instance.bundleType = type;
-        if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-          WXLogUtils.d("createInstance >>>> instanceId:" + instance.getInstanceId()
-                  + ", options:"
-                  + WXJsonUtils.fromObjectToJSONString(options)
-                  + ", data:" + data);
-        }
-        WXJSObject instanceIdObj = new WXJSObject(WXJSObject.String,
-                instance.getInstanceId());
-        WXJSObject instanceObj = new WXJSObject(WXJSObject.String,
-                template.getContent());
-
-        Object extraOption = null;
-        if(options != null && options.containsKey("extraOption")) {
-           extraOption = options.get("extraOption");
-           options.remove("extraOption");
-        }
-
-        WXJSObject extraOptionObj = new WXJSObject(WXJSObject.JSON,
-                extraOption == null ? "{}"
-                        : WXJsonUtils.fromObjectToJSONString(extraOption));
-
-
-        WXJSObject optionsObj = new WXJSObject(WXJSObject.JSON,
-                options == null ? "{}"
-                        : WXJsonUtils.fromObjectToJSONString(options));
-        optionsObj = optionObjConvert(isSandBoxContext, type, optionsObj);
-        WXJSObject dataObj = new WXJSObject(WXJSObject.JSON,
-                data == null ? "{}" : data);
-
-        WXJSObject apiObj;
-        if (type == BundType.Rax || instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER) {
-          if (mRaxApi == null) {
-            IWXJsFileLoaderAdapter iwxJsFileLoaderAdapter = WXSDKEngine.getIWXJsFileLoaderAdapter();
-            if(iwxJsFileLoaderAdapter != null) {
-              mRaxApi = iwxJsFileLoaderAdapter.loadRaxApi();
-            }
-
-            if(TextUtils.isEmpty(mRaxApi)) {
-              mRaxApi =  WXFileUtils.loadAsset("weex-rax-api.js", WXEnvironment.getApplication());
-            }
-          }
-          apiObj = new WXJSObject(WXJSObject.String,
-                  mRaxApi);
-        } else {
-          apiObj = new WXJSObject(WXJSObject.String,
-                  "");
-        }
-
-        // When render strategy is data_render, put it into options. Others keep null.
-        WXJSObject renderStrategy = null;
-        if (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER) {
-          renderStrategy = new WXJSObject(WXJSObject.String, WXRenderStrategy.DATA_RENDER.getFlag());
-        } else if (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY) {
-          renderStrategy = new WXJSObject(WXJSObject.String, WXRenderStrategy.DATA_RENDER_BINARY.getFlag());
-          // In DATA_RENDER_BINARY strategy script is binary
-          instanceObj.data = template.getBinary();
-        }else if (instance.getRenderStrategy() == WXRenderStrategy.JSON_RENDER) {
-             renderStrategy = new WXJSObject(WXJSObject.String, WXRenderStrategy.JSON_RENDER.getFlag());
-        }
-
-        WXJSObject[] args = {instanceIdObj, instanceObj, optionsObj,
-                dataObj, apiObj, renderStrategy, extraOptionObj};
-
-        instance.setTemplate(template.getContent());
-
-        instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_END);
-
-        // if { "framework": "Vue" } or  { "framework": "Rax" } will use invokeCreateInstanceContext
-        // others will use invokeExecJS
-        if (!isSandBoxContext) {
-          instance.getApmForInstance().onStage("!isSandBoxContext,and excute");
-          WXLogUtils.e("Instance " + instance.getInstanceId() + " Did Not Render in SandBox Mode");
-          invokeExecJS(instance.getInstanceId(), null, METHOD_CREATE_INSTANCE, args, false);
-          return;
-        }
-        if (type == BundType.Vue || type == BundType.Rax
-                || instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER
-                || instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY
-                || instance.getRenderStrategy() == WXRenderStrategy.JSON_RENDER) {
-          instance.getApmForInstance().onStage("wxBeforeInvokeCreateInstanceContext");
-
-          WXLogUtils.d("Instance " + instance.getInstanceId() + " Render in SandBox Mode And Render Type is "
-                  + type + " Render Strategy is " + instance.getRenderStrategy());
-
-          int ret = invokeCreateInstanceContext(instance.getInstanceId(), null, "createInstanceContext", args, false);
-          instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_END);
-          if(ret == 0) {
-            String err = "[WXBridgeManager] invokeCreateInstance : " + instance.getTemplateInfo();
-            WXLogUtils.e("Instance " + instance.getInstanceId() + "Render error : " + err);
-            instance.onRenderError(
-                    WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-                    WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg() + err);
-          }
-          return;
-        } else {
-          //bad case for js bundle with out bundletype header //vue or rax
-          //WXExceptionUtils.commitCriticalExceptionRT(
-          //      instance.getInstanceId(),
-          //      WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE,
-          //      "invokeCreateInstance",
-          //      WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE.getErrorMsg(),
-          //      null
-          //);
-
-          WXLogUtils.d("Instance " + instance.getInstanceId() + "Did not Render in SandBox Mode And Render Type is "
-                + type + " Render Strategy is " + instance.getRenderStrategy());
-          instance.getApmForInstance().onStage("StartInvokeExecJSBadBundleType");
-          invokeExecJS(instance.getInstanceId(), null, METHOD_CREATE_INSTANCE, args, false);
-          instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_END);
-          return;
-        }
-      } catch (Throwable e) {
-        String err = "[WXBridgeManager] invokeCreateInstance " + e.getCause()
-                + instance.getTemplateInfo();
-        instance.getApmForInstance().onStage("createInstance error :"+e.toString());
-        WXLogUtils.e("Instance " + instance.getInstanceId() + "Render error : " + err);
-        instance.onRenderError(
-                WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-                WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg() + err);
-        WXLogUtils.e(err);
-      }
-    }
-  }
-
-  public WXJSObject optionObjConvert(boolean useSandBox, BundType type, WXJSObject opt) {
-    if (!useSandBox) {
-      return opt;
-    }
-    try {
-      String data = opt.data.toString();
-      JSONObject obj = JSON.parseObject(data);
-      JSONObject optEnv;
-      if ((optEnv = obj.getJSONObject("env")) != null) {
-        JSONObject opts = optEnv.getJSONObject("options");
-        if (opts != null) {
-          for (String s : opts.keySet()) {
-            optEnv.put(s, opts.getString(s));
-          }
-        }
-      }
-      return new WXJSObject(WXJSObject.JSON, obj.toString());
-    } catch (Throwable e) {
-      WXLogUtils.e(WXLogUtils.getStackTrace(e));
-    }
-    return opt;
-
-  }
-
-  /**
-   * check bundleType
-   * @param url
-   * @param temp
-   * @return
-   */
-  public BundType getBundleType(String url, String temp) {
-    try {
-      if (url != null) {
-        Uri uri = Uri.parse(url);
-        String type = uri.getQueryParameter(BUNDLE_TYPE);
-        if ("Vue".equals(type) || "vue".equals(type)) {
-          return BundType.Vue;
-        } else if ("Rax".equals(type) || "rax".equals(type)) {
-          return BundType.Rax;
-        }
-      }
-      if (temp != null) {
-        final String FRAMEWORK="framework", VUE="vue", RAX="rax";
-
-        // Find the first line that starts with '//' and convert it to json
-        int bundleTypeStart = temp.indexOf("//");
-        int bundleTypeEnd = temp.indexOf("\n", bundleTypeStart);
-        JSONObject bundleType = JSONObject.parseObject(
-            temp.substring(bundleTypeStart+2, bundleTypeEnd));
-        String type = bundleType.getString(FRAMEWORK);
-        if(VUE.equalsIgnoreCase(type)){
-          return BundType.Vue;
-        }
-        else if(RAX.equalsIgnoreCase(type)){
-          return BundType.Rax;
-        }
-        else{
-          // '//{ "framework": "Vue"}' is not found.
-          String regEx = "(use)(\\s+)(weex:vue)";
-          Pattern pattern = Pattern.compile(regEx, Pattern.CASE_INSENSITIVE);
-          if (pattern.matcher(temp).find()) {
-            return BundType.Vue;
-          }
-          regEx = "(use)(\\s+)(weex:rax)";
-          pattern = Pattern.compile(regEx, Pattern.CASE_INSENSITIVE);
-          if (pattern.matcher(temp).find()) {
-            return BundType.Rax;
-          }
-        }
-      }
-      return BundType.Others;
-    } catch (Throwable e) {
-      WXLogUtils.e(WXLogUtils.getStackTrace(e));
-      return BundType.Others;
-    }
-  }
-
-  private void mock(String instanceId) {
-
-  }
-
-  public void destroyInstance(final String instanceId) {
-    if (mJSHandler == null
-            || TextUtils.isEmpty(instanceId)) {
-      return;
-    }
-    if (mDestroyedInstanceId != null) {
-      mDestroyedInstanceId.add(instanceId);
-    }
-    // clear message with instanceId
-    mJSHandler.removeCallbacksAndMessages(instanceId);
-    post(new Runnable() {
-      @Override
-      public void run() {
-        removeTaskByInstance(instanceId);
-        invokeDestroyInstance(instanceId);
-      }
-    }, instanceId, null, "destroyInstance");
-  }
-
-  private void removeTaskByInstance(String instanceId) {
-    mNextTickTasks.removeFromMapAndStack(instanceId);
-  }
-
-  private void invokeDestroyInstance(String instanceId) {
-    try {
-      if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-        WXLogUtils.d("destroyInstance >>>> instanceId:" + instanceId);
-      }
-      WXJSObject instanceIdObj = new WXJSObject(WXJSObject.String,
-              instanceId);
-      WXJSObject[] args = {instanceIdObj};
-      if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-        invokeDestoryInstance(instanceId, null, METHOD_DESTROY_INSTANCE, args, true);
-        // invokeExecJS(instanceId, null, METHOD_DESTROY_INSTANCE, args);
-      }
-    } catch (Throwable e) {
-      String err = "[WXBridgeManager] invokeDestroyInstance " + e.getCause();
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "invokeDestroyInstance", err, null);
-      WXLogUtils.e(err);
-    }
-  }
-
-  @Override
-  public boolean handleMessage(Message msg) {
-    if (msg == null) {
-      return false;
-    }
-
-    int what = msg.what;
-    switch (what) {
-      case WXJSBridgeMsgType.INIT_FRAMEWORK:
-        invokeInitFramework(msg);
-        break;
-      case WXJSBridgeMsgType.CALL_JS_BATCH:
-        invokeCallJSBatch(msg);
-        break;
-      case WXJSBridgeMsgType.SET_TIMEOUT:
-        TimerInfo timerInfo = (TimerInfo) msg.obj;
-        if (timerInfo == null) {
-          break;
-        }
-        WXJSObject obj = new WXJSObject(WXJSObject.String, timerInfo.callbackId);
-        WXJSObject[] args = {obj};
-        invokeExecJS("", null, METHOD_SET_TIMEOUT, args);
-        break;
-      case WXJSBridgeMsgType.TAKE_HEAP_SNAPSHOT:
-        if (msg.obj != null) {
-          String filename = (String) msg.obj;
-          mWXBridge.takeHeapSnapshot(filename);
-        }
-        break;
-      default:
-        break;
-    }
-    return false;
-  }
-
-  private void invokeExecJS(String instanceId, String namespace, String function, WXJSObject[] args) {
-    invokeExecJS(instanceId, namespace, function, args, true);
-  }
-
-  public void invokeExecJS(final String instanceId, final String namespace, final String function,
-                           final WXJSObject[] args, boolean logTaskDetail) {
-    if (WXEnvironment.isOpenDebugLog() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("callJS >>>> instanceId:").append(instanceId)
-              .append("function:").append(function);
-      if (logTaskDetail) {
-        mLodBuilder.append(" tasks:").append(argsToJSON(args));
-      }
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-    final long start = System.currentTimeMillis();
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (instance != null && (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY)) {
-      Pair<Pair<String,Object>, Boolean> data = null;
-      if(args.length!=2 || !(args[0].data instanceof String)
-          || !(args[1].data instanceof String)
-          || (data = extractCallbackArgs((String) args[1].data))==null){
-        WXLogUtils.w("invokeExecJS on data render that is not a callback call");
-        return;
-      }
-      callbackJavascriptOnDataRender(instanceId, (String) data.first.first, data.first.second, data.second);
-    } else {
-
-      WXThread.secure(new Runnable() {
-        @Override
-        public void run() {
-          mWXBridge.execJS(instanceId, namespace, function, args);
-        }
-      }, instance, "ExecJs").run();
-    }
-    if (null != instance){
-      long diff = System.currentTimeMillis()-start;
-      instance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_CALL_JS_NUM,1);
-      instance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_CALL_JS_TIME,diff);
-      instance.callJsTime(diff);
-    }
-  }
-
-  private Pair<Pair<String,Object>,Boolean> extractCallbackArgs(String data) {
-    try {
-      JSONArray obj = JSON.parseArray(data);
-      JSONObject arg_obj = obj.getJSONObject(0);
-      JSONArray args = arg_obj.getJSONArray("args");
-      if (args.size()!=3){
-        return null;
-      }
-      String method = arg_obj.getString("method");
-      if (!"callback".equals(method)){
-        return null;
-      }
-
-      return new Pair<Pair<String,Object>, Boolean>(new Pair<String, Object>(args.getString(0), args.getJSONObject(1)),args.getBooleanValue(2));
-    } catch (Exception e) {
-      return null;
-    }
-  }
-
-  public int invokeCreateInstanceContext(String instanceId, String namespace, String function,
-                                          WXJSObject[] args, boolean logTaskDetail) {
-    WXLogUtils.d("invokeCreateInstanceContext instanceId:" + instanceId + " function:"
-            + function + String.format(" isJSFrameworkInit：%b", isJSFrameworkInit()));
-    mLodBuilder.append("createInstanceContext >>>> instanceId:").append(instanceId)
-            .append("function:").append(function);
-    if (logTaskDetail)
-      mLodBuilder.append(" tasks:").append(WXJsonUtils.fromObjectToJSONString(args));
-    WXLogUtils.d(mLodBuilder.substring(0));
-    mLodBuilder.setLength(0);
-    // }
-    return mWXBridge.createInstanceContext(instanceId, namespace, function, args);
-  }
-
-  public void invokeDestoryInstance(String instanceId, String namespace, String function,
-                                    WXJSObject[] args, boolean logTaskDetail) {
-    // if (WXEnvironment.isApkDebugable()) {
-    mLodBuilder.append("callJS >>>> instanceId:").append(instanceId)
-            .append("function:").append(function);
-    if (logTaskDetail)
-      mLodBuilder.append(" tasks:").append(WXJsonUtils.fromObjectToJSONString(args));
-    WXLogUtils.d(mLodBuilder.substring(0));
-    mLodBuilder.setLength(0);
-    // }
-    mWXBridge.removeInstanceRenderType(instanceId);
-    mWXBridge.destoryInstance(instanceId, namespace, function, args);
-  }
-
-  private void execJSOnInstance(final EventResult eventCallback, final String instanceId, final String js, final int type) {
-    post(new Runnable() {
-      @Override
-      public void run() {
-        String ret = invokeExecJSOnInstance(instanceId, js, type);
-        eventCallback.onCallback(ret);
-      }
-    });
-  }
-
-  private String invokeExecJSOnInstance(String instanceId, String js, int type) {
-    // if (WXEnvironment.isApkDebugable()) {
-    mLodBuilder.append("execJSOnInstance >>>> instanceId:").append(instanceId);
-    WXLogUtils.d(mLodBuilder.substring(0));
-    mLodBuilder.setLength(0);
-    // }
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      return mWXBridge.execJSOnInstance(instanceId, js, type);
-    }
-    return null;
-  }
-
-  private void invokeExecJSWithCallback(String instanceId, String namespace, String function,
-                                        WXJSObject[] args , ResultCallback callback, boolean logTaskDetail){
-    if (WXEnvironment.isOpenDebugLog() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("callJS >>>> instanceId:").append(instanceId)
-              .append("function:").append(function);
-      if(logTaskDetail) {
-        mLodBuilder.append(" tasks:").append(argsToJSON(args));
-      }
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.execJSWithCallback(instanceId, namespace, function, args, callback);
-    }
-  }
-
-  public @NonNull static String argsToJSON(WXJSObject[] args) {
-    StringBuilder builder = new StringBuilder();
-    builder.append("[");
-    for(WXJSObject object : args){
-      builder.append(WXWsonJSONSwitch.fromObjectToJSONString(object));
-      builder.append(",");
-    }
-    builder.append("]");
-    return  builder.toString();
-  }
-
-  private void invokeInitFramework(Message msg) {
-    String framework = "";
-    if (msg.obj != null) {
-      framework = (String) msg.obj;
-    }
-
-    if (WXUtils.getAvailMemory(WXEnvironment.getApplication()) > LOW_MEM_VALUE) {
-      initFramework(framework);
-    }
-  }
-
-  public static long sInitFrameWorkTimeOrigin;
-  public static StringBuilder sInitFrameWorkMsg = new StringBuilder();
-
-  private void initFramework(String framework) {
-    LogDetail logDetail = new LogDetail();
-    logDetail.name("initFramework");
-    logDetail.taskStart();
-    if (WXSDKEngine.isSoInitialized() && !isJSFrameworkInit()) {
-      sInitFrameWorkTimeOrigin = System.currentTimeMillis();
-      if (TextUtils.isEmpty(framework)) {
-        // if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.d("weex JS framework from assets");
-        // }
-
-        LogDetail logDetail2 = new LogDetail();
-        logDetail2.name("loadJSFramework");
-        logDetail2.taskStart();
-
-        IWXJsFileLoaderAdapter wxJsFileLoaderAdapter = WXSDKEngine.getIWXJsFileLoaderAdapter();
-
-        if (!isSandBoxContext) {
-          if(wxJsFileLoaderAdapter != null) {
-            framework = wxJsFileLoaderAdapter.loadJsFramework();
-          }
-
-          if(TextUtils.isEmpty(framework)) {
-            framework = WXFileUtils.loadAsset("main.js", WXEnvironment.getApplication());
-          }
-        } else {
-          if(wxJsFileLoaderAdapter != null) {
-            framework = wxJsFileLoaderAdapter.loadJsFrameworkForSandBox();
-          }
-
-          if(TextUtils.isEmpty(framework)) {
-            framework = WXFileUtils.loadAsset("weex-main-jsfm.js", WXEnvironment.getApplication());
-          }
-        }
-        sInitFrameWorkMsg.append("| weex JS framework from assets, isSandBoxContext: ").append(isSandBoxContext);
-        logDetail2.taskEnd();
-      }
-      if (TextUtils.isEmpty(framework)) {
-        setJSFrameworkInit(false);
-        sInitFrameWorkMsg.append("| framework isEmpty ");
-        WXExceptionUtils.commitCriticalExceptionRT(null, WXErrorCode.WX_ERR_JS_FRAMEWORK,
-                "initFramework", "framework is empty!! ", null);
-        return;
-      }
-      try {
-        if (WXSDKManager.getInstance().getWXStatisticsListener() != null) {
-          long start = System.currentTimeMillis();
-          WXSDKManager.getInstance().getWXStatisticsListener().onJsFrameworkStart();
-          WXEnvironment.sJSFMStartListenerTime = System.currentTimeMillis() - start;
-          try {
-            IWXUserTrackAdapter adapter = WXSDKManager.getInstance().getIWXUserTrackAdapter();
-            if (null != adapter){
-              Map<String,Serializable> params = new HashMap<>(1);
-              params.put("time",String.valueOf(WXEnvironment.sJSFMStartListenerTime));
-              adapter.commit(WXEnvironment.getApplication(),"sJSFMStartListener",IWXUserTrackAdapter.COUNTER,null,params);
-            }
-          }catch (Exception e){
-            WXLogUtils.e(WXLogUtils.getStackTrace(e));
-          }
-        }
-
-        long start = System.currentTimeMillis();
-        String crashFile = "";
-        try {
-          crashFile = WXEnvironment.getApplication().getApplicationContext().getCacheDir().getPath();
-        } catch (Exception e) {
-          WXLogUtils.e(WXLogUtils.getStackTrace(e));
-        }
-        boolean pieSupport = true;
-        try {
-          if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
-            pieSupport = false;
-          }
-        } catch (Exception e) {
-          WXLogUtils.e(WXLogUtils.getStackTrace(e));
-        }
-        sInitFrameWorkMsg.append(" | pieSupport:").append(pieSupport);
-        WXLogUtils.d("[WXBridgeManager] initFrameworkEnv crashFile:" + crashFile + " pieSupport:" + pieSupport);
-        // extends initFramework
-        LogDetail logDetail3 = new LogDetail();
-        logDetail3.name("native initFrameworkEnv");
-        logDetail3.taskStart();
-        if (mWXBridge.initFrameworkEnv(framework, assembleDefaultOptions(), crashFile, pieSupport) == INIT_FRAMEWORK_OK) {
-          logDetail3.taskEnd();
-          WXEnvironment.sJSLibInitTime = System.currentTimeMillis() - start;
-          WXEnvironment.sSDKInitTime = System.currentTimeMillis() - WXEnvironment.sSDKInitStart;
-          setJSFrameworkInit(true);
-          logDetail.taskEnd();
-          if (WXSDKManager.getInstance().getWXStatisticsListener() != null) {
-            WXSDKManager.getInstance().getWXStatisticsListener().onJsFrameworkReady();
-          }
-
-          execRegisterFailTask();
-          WXEnvironment.JsFrameworkInit = true;
-          sInitFrameWorkCount++;
-          WXLogUtils.e("initFrameWorkCount :"+ sInitFrameWorkCount);
-          registerDomModule();
-          trackComponentAndModulesTime();
-        } else {
-          sInitFrameWorkMsg.append(" | ExecuteJavaScript fail, reInitCount").append(reInitCount);
-          if (reInitCount > 1) {
-            WXLogUtils.e("[WXBridgeManager] invokeReInitFramework  ExecuteJavaScript fail");
-          } else {
-            WXLogUtils.e("[WXBridgeManager] invokeInitFramework  ExecuteJavaScript fail");
-          }
-        }
-      } catch (Throwable e) {
-        sInitFrameWorkMsg.append(" | invokeInitFramework exception ").append(e.toString());
-        if (reInitCount > 1) {
-          WXLogUtils.e("[WXBridgeManager] invokeInitFramework ", e);
-        } else {
-          WXLogUtils.e("[WXBridgeManager] invokeInitFramework ", e);
-        }
-      }
-
-    }
-  }
-
-  private void trackComponentAndModulesTime() {
-    post(new Runnable() {
-      @Override
-      public void run() {
-        WXEnvironment.sComponentsAndModulesReadyTime = System.currentTimeMillis() - WXEnvironment.sSDKInitStart;
-      }
-    });
-  }
-
-  @SuppressWarnings("unchecked")
-  private void invokeCallJSBatch(Message message) {
-    if (mNextTickTasks.isEmpty() || !isJSFrameworkInit()) {
-      if (!isJSFrameworkInit()) {
-        WXLogUtils.e("[WXBridgeManager] invokeCallJSBatch: framework.js uninitialized!!  message:" + message.toString());
-      }
-      return;
-    }
-
-    try {
-      Object instanceId = message.obj;
-
-      Object task = null;
-      Stack<String> instanceStack = mNextTickTasks.getInstanceStack();
-      int size = instanceStack.size();
-      for (int i = size - 1; i >= 0; i--) {
-        instanceId = instanceStack.get(i);
-        task = mNextTickTasks.remove(instanceId);
-        if (task != null && !((ArrayList) task).isEmpty()) {
-          break;
-        }
-      }
-      if (null != task){
-        task = ((ArrayList) task).toArray();
-
-        WXJSObject[] args = {
-            new WXJSObject(WXJSObject.String, instanceId),
-            WXWsonJSONSwitch.toWsonOrJsonWXJSObject(task)};
-
-        invokeExecJS(String.valueOf(instanceId), null, METHOD_CALL_JS, args);
-      }
-    } catch (Throwable e) {
-      WXLogUtils.e("WXBridgeManager", e);
-      String err = "invokeCallJSBatch#" + WXLogUtils.getStackTrace(e);
-      WXExceptionUtils.commitCriticalExceptionRT(null, WXErrorCode.WX_ERR_JS_FRAMEWORK,
-              "invokeCallJSBatch", err, null);
-    }
-
-    // If task is not empty, loop until it is empty
-    if (!mNextTickTasks.isEmpty()) {
-      mJSHandler.sendEmptyMessage(WXJSBridgeMsgType.CALL_JS_BATCH);
-    }
-  }
-
-  private WXParams assembleDefaultOptions() {
-    checkJsEngineMultiThread();
-
-    Map<String, String> config = WXEnvironment.getConfig();
-    WXParams wxParams = new WXParams();
-    wxParams.setPlatform(config.get(WXConfig.os));
-    wxParams.setCacheDir(config.get(WXConfig.cacheDir));
-    wxParams.setOsVersion(config.get(WXConfig.sysVersion));
-    wxParams.setAppVersion(config.get(WXConfig.appVersion));
-    wxParams.setWeexVersion(config.get(WXConfig.weexVersion));
-    wxParams.setDeviceModel(config.get(WXConfig.sysModel));
-    wxParams.setShouldInfoCollect(config.get("infoCollect"));
-    wxParams.setLogLevel(config.get(WXConfig.logLevel));
-    wxParams.setLayoutDirection(config.get(WXConfig.layoutDirection));
-    wxParams.setUseSingleProcess(isUseSingleProcess ? "true" : "false");
-    wxParams.setCrashFilePath(WXEnvironment.getCrashFilePath(WXEnvironment.getApplication().getApplicationContext()));
-    wxParams.setLibJsbPath(WXEnvironment.CORE_JSB_SO_PATH);
-    wxParams.setLibJssPath(WXEnvironment.getLibJssRealPath());
-    wxParams.setLibIcuPath(WXEnvironment.getLibJssIcuPath());
-    wxParams.setLibLdPath(WXEnvironment.getLibLdPath());
-    String libJScRealPath = WXEnvironment.getLibJScRealPath();
-    wxParams.setLibJscPath(TextUtils.isEmpty(libJScRealPath)? "" : new File(libJScRealPath).getParent());
-    String appName = config.get(WXConfig.appName);
-    if (!TextUtils.isEmpty(appName)) {
-      wxParams.setAppName(appName);
-    }
-    wxParams.setDeviceWidth(TextUtils.isEmpty(config.get("deviceWidth")) ? String.valueOf(WXViewUtils.getScreenWidth(WXEnvironment.sApplication)) : config.get("deviceWidth"));
-    wxParams.setDeviceHeight(TextUtils.isEmpty(config.get("deviceHeight")) ? String.valueOf(WXViewUtils.getScreenHeight(WXEnvironment.sApplication)) : config.get("deviceHeight"));
-    Map<String, String> customOptions = WXEnvironment.getCustomOptions();
-    customOptions.put("enableBackupThread", String.valueOf(jsEngineMultiThreadEnable()));
-    IWXJscProcessManager wxJscProcessManager = WXSDKManager.getInstance().getWXJscProcessManager();
-    if(wxJscProcessManager != null) {
-      customOptions.put("enableBackupThreadCache", String.valueOf(wxJscProcessManager.enableBackUpThreadCache()));
-    }
-
-    if (!WXEnvironment.sUseRunTimeApi){
-      customOptions.put("__enable_native_promise__","true");
-    }
-
-    String enableAlarmSignal = "true";
-    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
-    if (null != adapter){
-      try {
-        if (adapter.checkMode("white_screen_fix_open")){
-          WXEnvironment.isWsFixMode = true;
-          enableAlarmSignal = "true";
-        }else {
-          enableAlarmSignal = adapter.getConfigWhenInit("wxapm","enableAlarmSignal",enableAlarmSignal);
-          WXEnvironment.isWsFixMode = "true".equalsIgnoreCase(enableAlarmSignal);
-        }
-      }catch (Exception e){
-        e.printStackTrace();
-      }
-    }
-    if (null != enableAlarmSignal){
-      customOptions.put("enableAlarmSignal",enableAlarmSignal);
-    }
-    WXLogUtils.e("weex","enableAlarmSignal:"+enableAlarmSignal);
-
-    wxParams.setOptions(customOptions);
-    wxParams.setNeedInitV8(WXSDKManager.getInstance().needInitV8());
-    mInitParams = wxParams;
-    return wxParams;
-  }
-
-  public WXParams getInitParams() {
-    return mInitParams;
-  }
-
-  private void execRegisterFailTask() {
-
-    if (mRegisterModuleFailList.size() > 0) {
-      List<Map<String, Object>> moduleReceiver = new ArrayList<>();
-      for (int i = 0, moduleCount = mRegisterModuleFailList.size(); i < moduleCount; ++i) {
-        invokeRegisterModules(mRegisterModuleFailList.get(i), moduleReceiver);
-      }
-      mRegisterModuleFailList.clear();
-      if (moduleReceiver.size() > 0) {
-        mRegisterModuleFailList.addAll(moduleReceiver);
-      }
-    }
-
-    if (mRegisterComponentFailList.size() > 0) {
-      List<Map<String, Object>> receiver = new ArrayList<>();
-      invokeRegisterComponents(mRegisterComponentFailList, receiver);
-      mRegisterComponentFailList.clear();
-      if (receiver.size() > 0) {
-        mRegisterComponentFailList.addAll(receiver);
-      }
-    }
-
-    if (mRegisterServiceFailList.size() > 0) {
-      List<String> receiver = new ArrayList<>();
-      for (String service : mRegisterServiceFailList) {
-        invokeExecJSService(service, receiver);
-      }
-      mRegisterServiceFailList.clear();
-      if (receiver.size() > 0) {
-        mRegisterServiceFailList.addAll(receiver);
-      }
-    }
-  }
-
-  /**
-   * Register Android module
-   *
-   * @param modules the format is like
-   *                {'dom':['updateAttrs','updateStyle'],'event':['openUrl']}
-   */
-
-  public void registerModules(final Map<String, Object> modules) {
-    if (modules != null && modules.size() != 0) {
-      if (isJSThread()) {
-        invokeRegisterModules(modules, mRegisterModuleFailList);
-      } else {
-        post(new Runnable() {
-          @Override
-          public void run() {
-            invokeRegisterModules(modules, mRegisterModuleFailList);
-          }
-        });
-      }
-    }
-  }
-
-  /**
-   * Registered component
-   */
-  public void registerComponents(final List<Map<String, Object>> components) {
-    if (mJSHandler == null || components == null
-            || components.size() == 0) {
-      return;
-    }
-    Runnable runnable = new Runnable() {
-      @Override
-      public void run() {
-        invokeRegisterComponents(components, mRegisterComponentFailList);
-      }
-    };
-
-    if(isJSThread() && isJSFrameworkInit()){
-      runnable.run();
-    }else{
-      post(runnable);
-    }
-  }
-
-  public void execJSService(final String service) {
-    postWithName(new Runnable() {
-      @Override
-      public void run() {
-        invokeExecJSService(service, mRegisterServiceFailList);
-      }
-    },null,"execJSService");
-  }
-
-  private void invokeExecJSService(String service, List<String> receiver) {
-    try {
-      if (!isJSFrameworkInit()) {
-        WXLogUtils.e("[WXBridgeManager] invoke execJSService: framework.js uninitialized.");
-        receiver.add(service);
-        return;
-      }
-      mWXBridge.execJSService(service);
-    } catch (Throwable e) {
-      WXLogUtils.e("[WXBridgeManager] invokeRegisterService:", e);
-
-      Map<String, String> data = new HashMap<String, String>();
-      data.put("inputParams",service + "||" + receiver.toString());
-
-      WXExceptionUtils.commitCriticalExceptionRT("invokeExecJSService",
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_JSSERVICE_EXECUTE,
-              "invokeExecJSService",
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_JSSERVICE_EXECUTE.getErrorMsg()
-                      + "[WXBridgeManager] invokeRegisterService:"
-                      + WXLogUtils.getStackTrace(e),
-              data);
-    }
-  }
-
-  public boolean isJSThread() {
-    return mJSThread != null && mJSThread.getId() == Thread.currentThread().getId();
-  }
-
-  private void invokeRegisterModules(Map<String, Object> modules, List<Map<String, Object>> failReceiver) {
-    if (modules == null || !isJSFrameworkInit()) {
-      if (!isJSFrameworkInit()) {
-        WXLogUtils.d("[WXinvokeRegisterModulesBridgeManager] invokeRegisterModules: framework.js uninitialized.");
-      }
-      failReceiver.add(modules);
-      return;
-    }
-
-    WXJSObject[] args = {WXWsonJSONSwitch.toWsonOrJsonWXJSObject(modules)};
-    String errorMsg = null;
-    try{
-      // TODO use a better way
-      if (mWXBridge instanceof WXBridge) {
-        ((WXBridge) mWXBridge).registerModuleOnDataRenderNode(WXJsonUtils.fromObjectToJSONString(modules));
-      }
-    } catch (Throwable e){
-      WXLogUtils.e("Weex [data_render register err]", e);
-    }
-    try {
-        if(0 == mWXBridge.execJS("", null, METHOD_REGISTER_MODULES, args)) {
-            errorMsg = "execJS error";
-        }
-      try {
-        Iterator<String> iter = modules.keySet().iterator();
-        while (iter.hasNext()) {
-          String module = iter.next();
-          if (module != null) {
-            WXModuleManager.resetModuleState(module, true);
-            //WXLogUtils.e("[WXBridgeManager]invokeRegisterModules METHOD_REGISTER_MODULES success module:" + module);
-          }
-        }
-      } catch (Throwable e) {
-        WXLogUtils.e("Weex [invokeRegisterModules]", e);
-      }
-    } catch (Throwable e) {
-      errorMsg = WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_MODULES.getErrorMsg() +
-                " \n " + e.getMessage() + modules.entrySet().toString();
-    }
-
-    if(!TextUtils.isEmpty(errorMsg)) {
-        WXLogUtils.e("[WXBridgeManager] invokeRegisterModules:", errorMsg);
-        WXExceptionUtils.commitCriticalExceptionRT(null,
-                WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_MODULES,
-                "invokeRegisterModules", errorMsg,
-                null );
-    }
-  }
-
-  private void invokeRegisterComponents(List<Map<String, Object>> components, List<Map<String, Object>> failReceiver) {
-    if (components == failReceiver) {
-      throw new RuntimeException("Fail receiver should not use source.");
-    }
-    if (!isJSFrameworkInit()) {
-      //WXLogUtils.e("[WXBridgeManager] invokeRegisterComponents: framework.js uninitialized.");
-
-      for (Map<String, Object> comp : components) {
-        failReceiver.add(comp);
-      }
-      return;
-    }
-    if (components == null) {
-      return;
-    }
-
-    try{
-      // TODO use a better way
-      if (mWXBridge instanceof WXBridge) {
-        ((WXBridge) mWXBridge).registerComponentOnDataRenderNode(WXJsonUtils.fromObjectToJSONString(components));
-      }
-    } catch (Throwable e){
-      WXLogUtils.e("Weex [data_render register err]", e);
-    }
-
-    WXJSObject[] args = {WXWsonJSONSwitch.toWsonOrJsonWXJSObject(components)};
-    String errorMsg = null;
-    try {
-      if(0 == mWXBridge.execJS("", null, METHOD_REGISTER_COMPONENTS, args)) {
-          errorMsg = "execJS error";
-      }
-    } catch (Throwable e) {
-        errorMsg = WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT
-                + args.toString()
-                + WXLogUtils.getStackTrace(e);
-    }
-
-    if(!TextUtils.isEmpty(errorMsg)) {
-        WXLogUtils.e("[WXBridgeManager] invokeRegisterComponents ", errorMsg);
-        WXExceptionUtils.commitCriticalExceptionRT(null,
-                WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT,
-                METHOD_REGISTER_COMPONENTS, errorMsg,
-                null);
-    }
-  }
-
-  public void destroy() {
-    if (mJSThread != null) {
-      mJSThread.quit();
-    }
-    mBridgeManager = null;
-    if (mDestroyedInstanceId != null) {
-      mDestroyedInstanceId.clear();
-    }
-
-  }
-
-  /**
-   * Report JavaScript Exception
-   */
-  public void reportJSException(String instanceId, String function,
-                                String exception) {
-    WXLogUtils.e("reportJSException >>>> instanceId:" + instanceId
-            + ", exception function:" + function + ", exception:"
-            + exception);
-    WXSDKInstance instance = null;
-    WXErrorCode reportErrorCode = WXErrorCode.WX_ERR_JS_EXECUTE;
-    if (instanceId != null && (instance = WXSDKManager.getInstance().getSDKInstance(instanceId)) != null) {
-      instance.setHasException(true);
-      exception +=   "\n getTemplateInfo==" +instance.getTemplateInfo();//add network header info
-      if ((METHOD_CREATE_INSTANCE.equals(function)) || !instance.isContentMd5Match()) {
-        try {
-          //data render mode should report exception instead of reload page,
-          // so we use !isSkipFrameworkInit(instanceId) to skip the positive branch of if clause.
-          if (!isSkipFrameworkInit(instanceId) && isJSFrameworkInit() && (reInitCount > 1 && reInitCount < 10) && !instance.isNeedReLoad()) {
-            new ActionReloadPage(instanceId, true).executeAction();
-            instance.setNeedLoad(true);
-            return;
-          } else {
-            String errorMsg = new StringBuilder()
-                .append(WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg())
-                .append(", exception function:").append(function)
-                .append(", exception:").append(exception)
-                .append(", extInitTime:").append(System.currentTimeMillis()-WXBridgeManager.sInitFrameWorkTimeOrigin).append("ms")
-                .append(", extInitErrorMsg:").append(WXBridgeManager.sInitFrameWorkMsg.toString())
-                .toString();
-            instance.onRenderError(//DegradPassivity to H5
-                     WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
-                     errorMsg
-            );
-            if (!WXEnvironment.sInAliWeex){
-              WXExceptionUtils.commitCriticalExceptionRT(instanceId, WXErrorCode.WX_RENDER_ERR_JS_CREATE_INSTANCE, function,exception,null);
-            }
-            return;
-          }
-        } catch (Exception e) {
-          WXLogUtils.e(WXLogUtils.getStackTrace(e));
-        }
-      }
-      if (METHOD_CREATE_INSTANCE.equals(function) && !instance.getApmForInstance().hasAddView){
-        reportErrorCode = WXErrorCode.WX_RENDER_ERR_JS_CREATE_INSTANCE;
-      } else if ( METHOD_CREATE_INSTANCE_CONTEXT.equals(function) && !instance.getApmForInstance().hasAddView){
-        reportErrorCode = WXErrorCode.WX_RENDER_ERR_JS_CREATE_INSTANCE_CONTEXT;
-      } else if (
-          (METHOD_UPDATE_COMPONENT_WITH_DATA.equals(function) ||
-          METHOD_CREATE_PAGE_WITH_CONTENT.equals(function) ||
-          METHOD_POST_TASK_TO_MSG_LOOP.equals(function) ||
-              METHOD_JSFM_NOT_INIT_IN_EAGLE_MODE.equals(function) )
-          && !instance.getApmForInstance().hasAddView){
-        reportErrorCode = WXErrorCode.WX_DEGRAD_EAGLE_RENDER_ERROR;
-      }
-      instance.onJSException(reportErrorCode.getErrorCode(), function, exception);
-    }
-    doReportJSException(instanceId,function,reportErrorCode,exception);
-  }
-
-  private void doReportJSException(String instanceId, String function,WXErrorCode reportCode, String exception){
-    WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
-    IWXJSExceptionAdapter adapter = WXSDKManager.getInstance().getIWXJSExceptionAdapter();
-    if (adapter != null) {
-      String exceptionId = instanceId;
-
-      if (TextUtils.isEmpty(instanceId)) {
-        exceptionId = "instanceIdisNull";
-      }
-
-      if (instance == null) {
-        if (("initFramework").equals(function)) {
-          String exceptionExt = null;
-          try {
-            if (WXEnvironment.getApplication() != null) {
-              final String fileName = WXEnvironment.getApplication().getApplicationContext().getCacheDir().getPath() + INITLOGFILE;
-              try {
-                File file = new File(fileName);
-                if (file.exists()) {
-                  if (file.length() > 0) {
-                    StringBuilder result = new StringBuilder();
-                    try {
-                      InputStreamReader read = new InputStreamReader(new FileInputStream(file), "UTF-8");
-                      BufferedReader br = new BufferedReader(read);
-                      String s = null;
-                      while ((s = br.readLine()) != null) {
-                        result.append(s + "\n");
-                      }
-                      exceptionExt = result.toString();
-                      br.close();
-                    } catch (Exception e) {
-                      WXLogUtils.e(WXLogUtils.getStackTrace(e));
-                    }
-                  }
-                  file.delete();
-                }
-              } catch (Throwable throwable) {
-                WXLogUtils.e(WXLogUtils.getStackTrace(throwable));
-              }
-            }
-          } catch (Throwable e) {
-            WXLogUtils.e(WXLogUtils.getStackTrace(e));
-          }
-          exception += "\n" + exceptionExt;
-          WXLogUtils.e("reportJSException:" + exception);
-
-        }
-      }
-
-
-      WXExceptionUtils.commitCriticalExceptionRT(exceptionId, reportCode,
-            function,
-          reportCode.getErrorMsg() + exception,
-            null);
-
-    }
-  }
-
-  private void registerDomModule() throws WXException {
-    /** Tell Javascript Framework what methods you have. This is Required.**/
-    Map<String, Object> domMap = new HashMap<>();
-    domMap.put(WXDomModule.WXDOM, WXDomModule.METHODS);
-    registerModules(domMap);
-  }
-
-  //This method is deprecated because of performance issue.
-  @Deprecated
-  public void notifyTrimMemory() {
-
-  }
-
-  /**
-   * update js server global config, current support turn wson off
-   * by pass wson_off
-   * */
-  public static void  updateGlobalConfig(String config) {
-    if(TextUtils.isEmpty(config)){
-      config = "none";
-    }
-    if(!TextUtils.equals(config, globalConfig)){
-      globalConfig = config;
-      WXEnvironment.addCustomOptions(GLOBAL_CONFIG_KEY, globalConfig);
-      Runnable runnable = new Runnable() {
-        @Override
-        public void run() {
-          if(mBridgeManager != null){
-            if(mBridgeManager.isJSFrameworkInit()){
-              if(mBridgeManager.mWXBridge instanceof WXBridge) {
-                final WXBridge bridge = (WXBridge) mBridgeManager.mWXBridge;
-                bridge.nativeUpdateGlobalConfig(globalConfig);
-              }
-            }
-          }
-          if(globalConfig.contains(WXWsonJSONSwitch.WSON_OFF)){
-            WXWsonJSONSwitch.USE_WSON = false;
-          }else{
-            WXWsonJSONSwitch.USE_WSON = true;
-          }
-        }
-      };
-      if(mBridgeManager != null && mBridgeManager.isJSFrameworkInit()){
-        mBridgeManager.post(runnable);
-      }else{
-        runnable.run();
-      }
-    }
-  }
-
-  public
-  @Nullable
-  Looper getJSLooper() {
-    Looper ret = null;
-    if (mJSThread != null) {
-      ret = mJSThread.getLooper();
-    }
-    return ret;
-  }
-
-  public void notifySerializeCodeCache() {
-    post(new Runnable() {
-      @Override
-      public void run() {
-        if (!isJSFrameworkInit())
-          return;
-
-        invokeExecJS("", null, METHOD_NOTIFY_SERIALIZE_CODE_CACHE, new WXJSObject[0]);
-      }
-    });
-  }
-
-  public void takeJSHeapSnapshot(String filename) {
-    Message msg = mJSHandler.obtainMessage();
-    msg.obj = filename;
-    msg.what = WXJSBridgeMsgType.TAKE_HEAP_SNAPSHOT;
-    msg.setTarget(mJSHandler);
-    msg.sendToTarget();
-  }
-
-  public static class TimerInfo {
-
-    public String callbackId;
-    public long time;
-    public String instanceId;
-  }
-
-  public int callCreateBody(String pageId, String componentType, String ref,
-                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
-                            float[] margins, float[] paddings, float[] borders) {
-
-    if (TextUtils.isEmpty(pageId) || TextUtils.isEmpty(componentType) || TextUtils.isEmpty(ref)) {
-      WXLogUtils.d("[WXBridgeManager] call callCreateBody arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(pageId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callCreateBody",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callCreateBody >>>> pageId:").append(pageId)
-              .append(", componentType:").append(componentType).append(", ref:").append(ref)
-              .append(", styles:").append(styles == null ? "{}" : styles.toString())
-              .append(", attributes:").append(attributes)
-              .append(", events:").append(events);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(pageId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(pageId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionCreateBody(instance, ref, componentType,
-                styles, attributes, events, margins, paddings, borders);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callCreateBody exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(pageId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callCreateBody",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callAddElement(String pageId, String componentType, String ref, int index, String parentRef,
-                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
-                            float[] margins, float[] paddings, float[] borders,boolean willLayout) {
-    if (TextUtils.isEmpty(pageId) || TextUtils.isEmpty(componentType) || TextUtils.isEmpty(ref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callAddElement arguments is null");
-      }
-      WXExceptionUtils.commitCriticalExceptionRT(pageId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callAddElement",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callAddElement >>>> pageId:").append(pageId)
-              .append(", componentType:").append(componentType).append(", ref:").append(ref).append(", index:").append(index)
-              .append(", parentRef:").append(parentRef)
-              .append(", styles:").append(styles == null ? "{}" : styles.toString())
-              .append(", attributes:").append(attributes)
-              .append(", events:").append(events);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(pageId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(pageId);
-      if (instance != null) {
-        final GraphicActionAddElement action = new GraphicActionAddElement(instance, ref, componentType, parentRef, index,
-            styles, attributes, events, margins, paddings, borders);
-        if(willLayout) {
-          instance.addInActiveAddElementAction(ref, action);
-        }else{
-          WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(pageId, action);
-        }
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callAddElement exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(pageId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callAddElement",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callRemoveElement(String instanceId, String ref) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callRemoveElement arguments is null");
-      }
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRemoveElement",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callRemoveElement >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionRemoveElement(instance, ref);
-        if(instance.getInActiveAddElementAction(ref)!=null){
-          instance.removeInActiveAddElmentAction(ref);
-        }
-        else {
-          WXSDKManager.getInstance().getWXRenderManager()
-              .postGraphicAction(action.getPageId(), action);
-        }
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callRemoveElement exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRemoveElement",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callMoveElement(String instanceId, String ref, String parentref, int index) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref) || TextUtils.isEmpty(parentref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callMoveElement arguments is null");
-      }
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callMoveElement",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callMoveElement >>>> instanceId:").append(instanceId)
-              .append(", parentref:").append(parentref)
-              .append(", index:").append(index)
-              .append(", ref:").append(ref);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionMoveElement(instance, ref, parentref, index);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callMoveElement exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callMoveElement",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callAddEvent(String instanceId, String ref, String event) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref) || TextUtils.isEmpty(event)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callAddEvent arguments is null");
-      }
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callAddEvent",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callAddEvent >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref)
-              .append(", event:").append(event);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        new GraphicActionAddEvent(instance, ref, event).executeActionOnRender();
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callAddEvent exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callAddEvent",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    // get next tick
-    getNextTick(instanceId);
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callRemoveEvent(String instanceId, String ref, String event) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref) || TextUtils.isEmpty(event)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callRemoveEvent arguments is null");
-      }
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRemoveEvent",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callRemoveEvent >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref)
-              .append(", event:").append(event);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        new GraphicActionRemoveEvent(instance, ref, event).executeActionOnRender();
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callRemoveEvent exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRemoveEvent",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    // get next tick
-    getNextTick(instanceId);
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callUpdateStyle(String instanceId, String ref, HashMap<String, Object> styles,
-                             HashMap<String, String> paddings,
-                             HashMap<String, String> margins,
-                             HashMap<String, String> borders) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callUpdateStyle arguments is null");
-      }
-
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateStyle",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callUpdateStyle >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref).append(", styles:").append(styles == null ? "{}" : styles.toString())
-              .append(", paddings:").append(paddings.toString())
-                      .append(", margins:").append(margins.toString())
-                              .append(", borders:").append(borders.toString());
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionUpdateStyle(instance, ref, styles, paddings, margins, borders);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callUpdateStyle exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateStyle",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callUpdateAttrs(String instanceId, String ref, HashMap<String, String> attrs) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callUpdateAttrs arguments is null");
-      }
-
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateAttrs",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callUpdateAttrs >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref).append(", attrs:").append(attrs.toString());
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionUpdateAttr(instance, ref, attrs);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callUpdateAttrs exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateAttrs",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  private void setExceedGPULimitComponentsInfo(String instanceId,String ref,GraphicSize layoutSize){
-    float limit = WXRenderManager.getOpenGLRenderLimitValue();
-    if(limit > 0 && (layoutSize.getHeight() > limit || layoutSize.getWidth() > limit)){
-      JSONObject ext = new JSONObject();
-      WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(instanceId,ref);
-      ext.put("GPU limit",String.valueOf(limit));
-      ext.put("component.width",String.valueOf(layoutSize.getWidth()));
-      ext.put("component.height",String.valueOf(layoutSize.getHeight()));
-      if (component.getComponentType() != null && !component.getComponentType().isEmpty()) {
-        ext.put("component.type", component.getComponentType());
-      }
-      if (component.getStyles() != null && !component.getStyles().isEmpty()) {
-        ext.put("component.style", component.getStyles().toString());
-      }
-      if (component.getAttrs() != null && !component.getAttrs().isEmpty()) {
-        ext.put("component.attr", component.getAttrs().toString());
-      }
-      if (component.getEvents() != null && !component.getEvents().isEmpty()) {
-        ext.put("component.event", component.getEvents().toString());
-      }
-      if (component.getMargin() != null) {
-        ext.put("component.margin", component.getMargin().toString());
-      }
-      if (component.getPadding() != null) {
-        ext.put("component.padding", component.getPadding().toString());
-      }
-      if (component.getBorder() != null) {
-        ext.put("component.border", component.getBorder().toString());
-      }
-      WXSDKManager.getInstance().getSDKInstance(instanceId).setComponentsInfoExceedGPULimit(ext);
-    }
-  }
-
-  public int callAddChildToRichtext(String instanceId, String nodeType, String ref, String parentRef, String richTextRef,
-                                    HashMap<String, String> styles, HashMap<String, String> attrs){
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callAddChildToRichtext arguments is null");
-      }
-
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callAddChildToRichtext",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callAddChildToRichtext >>>> instanceId:").append(instanceId)
-              .append(", nodeType:").append(nodeType).append(", ref:").append(ref).append(", parentRef:")
-              .append(parentRef).append(", richTextRef:").append(richTextRef).append(", styles:")
-              .append(styles.toString()).append(", attrs:").append(attrs.toString());
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionAddChildToRichtext(instance,nodeType,ref,parentRef,richTextRef,styles,attrs
-        );
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callAddChildToRichtext exception: ", WXLogUtils.getStackTrace(e));
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callAddChildToRichtext",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callRemoveChildFromRichtext(String instanceId, String ref, String parentRef, String richTextRef){
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callRemoveChildFromRichtext arguments is null");
-      }
-
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRemoveChildFromRichtext",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callRemoveChildFromRichtext >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref).append(", parentRef:").append(parentRef).append(", richTextRef:").append(richTextRef);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionRemoveChildFromRichtext(instance, ref, parentRef, richTextRef);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callRemoveChildFromRichtext exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRemoveChildFromRichtext",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callUpdateRichtextStyle(String instanceId, String ref, HashMap<String, String> styles, String parentRef, String richTextRef){
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callUpdateRichtextStyle arguments is null");
-      }
-
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateRichtextStyle",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callUpdateRichtextStyle >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref).append(", styles:").append(styles.toString()).append(", parentRef:")
-              .append(parentRef).append(", richTextRef:").append(richTextRef);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionUpdateRichtextStyle(instance, ref, styles, parentRef, richTextRef);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callUpdateRichtextStyle exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateRichtextStyle",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-  public int callUpdateRichtextChildAttr(String instanceId, String ref, HashMap<String, String> attrs, String parentRef, String richTextRef){
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
-      if (WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("[WXBridgeManager] call callUpdateRichtextChildAttr arguments is null");
-      }
-
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateRichtextChildAttr",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callUpdateRichtextChildAttr >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref).append(", attrs:").append(attrs.toString()).append(", parentRef:")
-              .append(parentRef).append(", richTextRef:").append(richTextRef);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        final BasicGraphicAction action = new GraphicActionUpdateRichtextAttr(instance, ref, attrs, parentRef, richTextRef);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callUpdateRichtextChildAttr exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateRichtextChildAttr",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callLayout(String pageId, String ref, int top, int bottom, int left, int right, int height, int width, boolean isRTL, int index) {
-
-    if (TextUtils.isEmpty(pageId) || TextUtils.isEmpty(ref)) {
-        if (WXEnvironment.isApkDebugable()){
-            WXLogUtils.d("[WXBridgeManager] call callLayout arguments is null");
-        }
-
-      WXExceptionUtils.commitCriticalExceptionRT(pageId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callLayout",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callLayout >>>> instanceId:").append(pageId)
-            .append(", ref:").append(ref).append(", height:").append(height).append(", width:").append(width)
-              .append(", top:").append(top)
-              .append(", bottom:").append(bottom)
-              .append(", left:").append(left)
-              .append(", right:").append(right);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(pageId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(pageId);
-      if (instance != null) {
-        GraphicSize size = new GraphicSize(width, height);
-        GraphicPosition position = new GraphicPosition(left, top, right, bottom);
-        setExceedGPULimitComponentsInfo(pageId,ref,size);
-        GraphicActionAddElement addAction = instance.getInActiveAddElementAction(ref);
-        if(addAction!=null) {
-          addAction.setRTL(isRTL);
-          addAction.setSize(size);
-          addAction.setPosition(position);
-          if(!TextUtils.equals(ref, WXComponent.ROOT)) {
-            addAction.setIndex(index);
-          }
-          WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(pageId, addAction);
-          instance.removeInActiveAddElmentAction(ref);
-        }
-        else {
-          final BasicGraphicAction action = new GraphicActionLayout(instance, ref, position, size, isRTL);
-          WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-        }
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callLayout exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(pageId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callLayout",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callAppendTreeCreateFinish(String instanceId, String ref) {
-
-    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
-      WXLogUtils.d("[WXBridgeManager] call callAppendTreeCreateFinish arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callAppendTreeCreateFinish",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callAppendTreeCreateFinish >>>> instanceId:").append(instanceId)
-              .append(", ref:").append(ref);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      GraphicActionAppendTreeCreateFinish action = new GraphicActionAppendTreeCreateFinish(instance, ref);
-      WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(instanceId, action);
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callAppendTreeCreateFinish exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callAppendTreeCreateFinish",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callCreateFinish(String instanceId) {
-
-    if (TextUtils.isEmpty(instanceId)) {
-      WXLogUtils.d("[WXBridgeManager] call callCreateFinish arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callCreateFinish",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callCreateFinish >>>> instanceId:").append(instanceId);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      long start = System.currentTimeMillis();
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        instance.getApmForInstance().onStage("callCreateFinish");
-        instance.firstScreenCreateInstanceTime(start);
-        GraphicActionCreateFinish action = new GraphicActionCreateFinish(instance);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(instanceId, action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callCreateFinish exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callCreateFinish",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public int callRenderSuccess(String instanceId) {
-
-    if (TextUtils.isEmpty(instanceId)) {
-      WXLogUtils.d("[WXBridgeManager] call callRenderSuccess arguments is null");
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRenderSuccess",
-              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
-      return IWXBridge.INSTANCE_RENDERING_ERROR;
-    }
-
-    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
-      mLodBuilder.append("[WXBridgeManager] callRenderSuccess >>>> instanceId:").append(instanceId);
-      WXLogUtils.d(mLodBuilder.substring(0));
-      mLodBuilder.setLength(0);
-    }
-
-    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    try {
-      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-      if (instance != null) {
-        instance.getApmForInstance().onStage("callRenderSuccess");
-        GraphicActionRenderSuccess action = new GraphicActionRenderSuccess(instance);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(instanceId, action);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXBridgeManager] callRenderSuccess exception: ", e);
-      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRenderSuccess",
-              WXLogUtils.getStackTrace(e), null);
-    }
-
-    return IWXBridge.INSTANCE_RENDERING;
-  }
-
-  public ContentBoxMeasurement getMeasurementFunc(String instanceId, long renderObjectPtr) {
-    ContentBoxMeasurement contentBoxMeasurement = null;
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (instance != null) {
-      contentBoxMeasurement = instance.getContentBoxMeasurement(renderObjectPtr);
-    }
-    return contentBoxMeasurement;
-  }
-
-  public void bindMeasurementToRenderObject(long ptr){
-    if (isJSFrameworkInit()) {
-      mWXBridge.bindMeasurementToRenderObject(ptr);
-    }
-  }
-
-
-  /**
-   * Native: Layout
-   * @param instanceId
-   * @return
-   */
-  @UiThread
-  public boolean notifyLayout(String instanceId) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      return mWXBridge.notifyLayout(instanceId);
-    }
-    return false;
-  }
-
-  @UiThread
-  public void forceLayout(String instanceId) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.forceLayout(instanceId);
-    }
-  }
-
-  /**
-   * native: OnInstanceClose
-   * should be called on JSThread
-   * @param instanceId
-   */
-  public void onInstanceClose(String instanceId) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.onInstanceClose(instanceId);
-    }
-  }
-
-  /**
-   * native: SetDefaultHeightAndWidthIntoRootDom
-   * @param instanceId
-   * @param defaultWidth
-   * @param defaultHeight
-   */
-  public void setDefaultRootSize(final String instanceId, final float defaultWidth, final float defaultHeight, final boolean isWidthWrapContent, final boolean isHeightWrapContent) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setDefaultHeightAndWidthIntoRootDom(instanceId, defaultWidth, defaultHeight, isWidthWrapContent, isHeightWrapContent);
-    }
-  }
-
-  public void setRenderContentWrapContentToCore(boolean wrap, final String instanceId) {
-    if (isJSFrameworkInit()) {
-      mWXBridge.setRenderContainerWrapContent(wrap, instanceId);
-    }
-  }
-
-  public void setStyleWidth(String instanceId, String ref, float value) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setStyleWidth(instanceId, ref, value);
-    }
-  }
-
-  public void setStyleHeight(String instanceId, String ref, float value) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setStyleHeight(instanceId, ref, value);
-    }
-  }
-
-  public long[] getFirstScreenRenderTime(String instanceId) {
-    if (isJSFrameworkInit()) {
-      return mWXBridge.getFirstScreenRenderTime(instanceId);
-    }
-    return new long[]{0, 0, 0};
-  }
-
-  public long[] getRenderFinishTime(String instanceId) {
-    if (isJSFrameworkInit()) {
-      return mWXBridge.getRenderFinishTime(instanceId);
-    }
-    return new long[]{0, 0, 0};
-  }
-
-  public void setDeviceDisplay(final String instanceId, final float deviceWidth, final float deviceHeight, final float scale) {
-    post(new Runnable() {
-      @Override
-      public void run() {
-        mWXBridge.setDeviceDisplay(instanceId, deviceWidth, deviceHeight, scale);
-      }
-    });
-  }
-
-  public void updateInitDeviceParams(final String width, final String height, final String density, final String statusHeight){
-    if(!isJSFrameworkInit()){
-      return;
-    }
-    post(new Runnable() {
-      @Override
-      public void run() {
-        mWXBridge.updateInitFrameworkParams(WXConfig.deviceWidth, width, WXConfig.deviceWidth);
-      }
-    });
-    post(new Runnable() {
-      @Override
-      public void run() {
-        mWXBridge.updateInitFrameworkParams(WXConfig.deviceHeight, height, WXConfig.deviceHeight);
-      }
-    });
-
-    post(new Runnable() {
-      @Override
-      public void run() {
-        mWXBridge.updateInitFrameworkParams(WXConfig.scale,  density, WXConfig.scale);
-      }
-    });
-
-    if(statusHeight != null){
-      post(new Runnable() {
-        @Override
-        public void run() {
-          mWXBridge.updateInitFrameworkParams(WXConfig.androidStatusBarHeight,  statusHeight, WXConfig.androidStatusBarHeight);
-        }
-      });
-    }
-  }
-
-  public void setMargin(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setMargin(instanceId, ref, edge, value);
-    }
-  }
-
-  public void setPadding(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setPadding(instanceId, ref, edge, value);
-    }
-  }
-
-  public void setPosition(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setPosition(instanceId, ref, edge, value);
-    }
-  }
-
-  public void markDirty(String instanceId, String ref, boolean dirty) {
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.markDirty(instanceId, ref, dirty);
-    }
-  }
-  public void setViewPortWidth(String instanceId,float viewPortWidth){
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setViewPortWidth(instanceId,viewPortWidth);
-    }
-  }
-  public void setPageArgument(String instanceId,String key,String value){
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setPageArgument(instanceId,key,value);
-    }
-  }
-  public void reloadPageLayout(String instanceId){
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.reloadPageLayout(instanceId);
-    }
-  }
-
-  public void setDeviceDisplayOfPage(String instanceId,float width,float height){
-    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
-      mWXBridge.setDeviceDisplayOfPage(instanceId,width,height);
-    }
-  }
-
-  public int callHasTransitionPros(String instanceId, String ref, HashMap<String, String> styles) {
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(instanceId, ref);
-    if (null == component || null == component.getTransition() || null == component.getTransition().getProperties()) {
-      return IWXBridge.DESTROY_INSTANCE;
-    }
-
-    for(String property : component.getTransition().getProperties()){
-      if(styles.containsKey(property)){
-        return IWXBridge.INSTANCE_RENDERING;
-      }
-    }
-    return IWXBridge.INSTANCE_RENDERING_ERROR;
-  }
-
-  public void registerCoreEnv(String key, String value) {
-    if (isJSFrameworkInit())
-      mWXBridge.registerCoreEnv(key, value);
-    else
-      mWeexCoreEnvOptions.put(key, value);
-  }
-
-  private void onJsFrameWorkInitSuccees() {
-    for (Map.Entry<String, String> entry : mWeexCoreEnvOptions.entrySet()) {
-      mWXBridge.registerCoreEnv(entry.getKey(), entry.getValue());
-    }
-    mWeexCoreEnvOptions.clear();
-  }
-
-  public  String getWeexCoreThreadStackTrace(){
-    if (null == mJSThread){
-      return "null == mJSThread";
-    }
-    StringBuilder stringBuilder = new StringBuilder();
-
-    try {
-      stringBuilder.append(String.format("Thread Name: '%s'\n", mJSThread.getName()));
-      stringBuilder.append(String.format(Locale.ENGLISH,"\"%s\" prio=%d tid=%d %s\n", mJSThread.getName(), mJSThread.getPriority(), mJSThread.getId(), mJSThread.getState()));
-
-      for (StackTraceElement e: mJSThread.getStackTrace()){
-        stringBuilder.append(String.format("\tat %s\n", e.toString()));
-      }
-    } catch (Exception var8) {
-      Log.e("weex", "getJSThreadStackTrace error:", var8);
-    }
-    return stringBuilder.toString();
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXDebugJsBridge.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXDebugJsBridge.java
deleted file mode 100644
index 7b58416..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXDebugJsBridge.java
+++ /dev/null
@@ -1,101 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import com.alibaba.fastjson.JSON;
-import com.taobao.weex.utils.WXWsonJSONSwitch;
-import com.taobao.weex.wson.WsonUtils;
-
-/**
- * Created by darin on 27/03/2018.
- */
-
-public class WXDebugJsBridge {
-
-    public native void resetWXBridge(Object bridge, String className);
-
-    public native void jsHandleSetJSVersion(String jsVersion);
-
-    public native void jsHandleReportException(String instanceId, String func, String exceptionString);
-
-    public native void jsHandleCallNative(String instanceId, byte[] tasks, String callback);
-
-    public void jsHandleCallNativeModule(String instanceId, String module, String method, byte[] arguments, byte[] options) {
-        jsHandleCallNativeModule(instanceId, module, method,
-                WXWsonJSONSwitch.convertJSONToWsonIfUseWson(arguments), WXWsonJSONSwitch.convertJSONToWsonIfUseWson(options), true);
-    }
-
-    public native void jsHandleCallNativeModule(String instanceId, String module, String method, byte[] arguments, byte[] options, boolean h5);
-
-    public void jsHandleCallNativeComponent(String instanceId, String componentRef, String method, byte[] arguments, byte[] options){
-        jsHandleCallNativeComponent(instanceId, componentRef, method, WXWsonJSONSwitch.convertJSONToWsonIfUseWson(arguments), WXWsonJSONSwitch.convertJSONToWsonIfUseWson(options), true);
-    }
-
-
-    public native void jsHandleCallNativeComponent(String instanceId, String componentRef, String method, byte[] arguments, byte[] options, boolean from);
-
-    public void jsHandleCallAddElement(String instanceId, String ref, String dom, String index){
-        jsHandleCallAddElement(instanceId, ref, WsonUtils.toWson(JSON.parse(dom)), index, true);
-    }
-
-    public native void jsHandleCallAddElement(String instanceId, String ref, byte[] dom, String index, boolean h5);
-
-    public native void jsHandleSetTimeout(String callbackId, String time);
-
-    public native void jsHandleCallNativeLog(byte[] str_array);
-
-    public void jsHandleCallCreateBody(String pageId, String domStr){
-        jsHandleCallCreateBody(pageId, WsonUtils.toWson(JSON.parse(domStr)), true);
-    }
-
-    public native void jsHandleCallCreateBody(String pageId, byte[] domStr, boolean h5);
-
-    public native void jsHandleCallUpdateFinish(String instanceId, byte[] tasks, String callback);
-
-    public native void jsHandleCallCreateFinish(String pageId);
-
-    public native void jsHandleCallRefreshFinish(String instanceId, byte[] tasks, String callback);
-
-    public void jsHandleCallUpdateAttrs(String pageId, String ref, String data){
-        jsHandleCallUpdateAttrs(pageId, ref, WsonUtils.toWson(JSON.parseObject(data)), true);
-    }
-
-    public native void jsHandleCallUpdateAttrs(String pageId, String ref, byte[] data, boolean h5);
-
-    public void jsHandleCallUpdateStyle(String pageId, String ref, String data){
-        byte[] data1 = WsonUtils.toWson(JSON.parseObject(data));
-        jsHandleCallUpdateStyleNative(pageId, ref, data1, true);
-    }
-
-    public native void jsHandleCallUpdateStyleNative(String pageId, String ref, byte[] data, boolean h5);
-
-    public native void jsHandleCallRemoveElement(String pageId, String ref);
-
-    public native void jsHandleCallMoveElement(String pageId, String ref, String parentRef, String index_str);
-
-    public native void jsHandleCallAddEvent(String pageId, String ref, String event);
-
-    public native void jsHandleCallRemoveEvent(String pageId, String ref, String event);
-
-    public native void jsHandleSetInterval(String instanceId, String callbackId, String time);
-
-    public native void jsHandleClearInterval(String instanceId, String callbackId);
-
-    public native void jsHandleCallGCanvasLinkNative(String contextId, int type, String val);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXHashMap.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXHashMap.java
deleted file mode 100644
index 1296af0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXHashMap.java
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import android.text.TextUtils;
-
-import java.util.HashMap;
-import java.util.Stack;
-
-/**
- * HashMap for Weex
- */
-public class WXHashMap<K, V> extends HashMap<K, V> {
-
-  private static final long serialVersionUID = 4294272345728974369L;
-
-  private Stack<String> instancesStack = new Stack<String>();
-  private String mTag;
-
-  @Override
-  public V put(K key, V value) {
-    if (key != null && key.toString() != null) {
-      if (instancesStack.contains(key)) {
-        instancesStack.remove(key);
-      }
-      instancesStack.push(key.toString());
-    }
-    return super.put(key, value);
-  }
-
-  @Override
-  public V remove(Object key) {
-    return super.remove(key);
-  }
-
-  public V removeFromMapAndStack(Object key) {
-    instancesStack.remove(key);
-    return super.remove(key);
-  }
-
-  /**
-   * Get instance Id of the top of the stack
-   *
-   * @return
-   */
-  public String getStackTopInstanceId() {
-    return instancesStack.isEmpty() ? "" : instancesStack.pop();
-  }
-
-  /**
-   * Move instanceId to the top of the stack
-   *
-   * @param id
-   */
-  public void setStackTopInstance(String id) {
-    if (!TextUtils.isEmpty(id)) {
-      instancesStack.remove(id);
-      instancesStack.push(id);
-    }
-  }
-
-  public Stack<String> getInstanceStack() {
-    return instancesStack;
-  }
-
-  public String getTag() {
-    return mTag;
-  }
-
-  public void setTag(String tag) {
-    this.mTag = tag;
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXJSObject.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXJSObject.java
deleted file mode 100644
index 56ce501..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXJSObject.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-
-import com.taobao.weex.utils.WXJsonUtils;
-
-public class WXJSObject {
-
-    public static final int NUMBER = 1;
-    public static final int String = 2;
-    public static final int JSON = 3;
-    public static final int WSON = 4;
-
-    public Object data;
-    public int type;
-    public String key;
-
-    public WXJSObject(int type, Object data) {
-        this.type = type;
-        this.data = data;
-    }
-
-    public WXJSObject(int type, Object data, String key) {
-        this.type = type;
-        this.data = data;
-        this.key = key;
-    }
-
-    public WXJSObject(Object object) {
-
-        if(null == object){
-            type= String;
-            data = "";
-            return;
-        }
-
-        data = object;
-        if (object instanceof Integer) {
-            type = NUMBER;
-            data = (double) (Integer) object;
-        } else if (object instanceof Double) {
-            type = NUMBER;
-        } else if (object instanceof Float) {
-            type = NUMBER;
-            data = (double) ((Float) object).intValue();
-        } else if (object instanceof String) {
-            type = String;
-        } else if (object instanceof Object) {
-            type = JSON;
-            data = WXJsonUtils.fromObjectToJSONString(object,true);
-        }
-    }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXModuleManager.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXModuleManager.java
deleted file mode 100644
index f544123..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXModuleManager.java
+++ /dev/null
@@ -1,535 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import android.content.Intent;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-import android.view.Menu;
-
-import com.alibaba.fastjson.JSONArray;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.common.Destroyable;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXException;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.ui.config.ConfigModuleFactory;
-import com.taobao.weex.ui.module.WXDomModule;
-import com.taobao.weex.ui.module.WXTimerModule;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.cache.RegisterCache;
-
-import java.io.Serializable;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map;
-import java.util.Map.Entry;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.ConcurrentMap;
-
-/**
- * Manager class for weex module. There are two types of modules in weex, one is instance-level module,
- * the other is global-level module. Instance-level module will be created every time an instance
- * is created, while global-level module will be singleton in {@link com.taobao.weex.WXSDKEngine}.
- */
-public class WXModuleManager {
-
-  /**
-   * module class object dictionary
-   */
-  private static volatile ConcurrentMap<String, ModuleFactoryImpl> sModuleFactoryMap = new ConcurrentHashMap<>();
-  private static Map<String, WXModule> sGlobalModuleMap = new HashMap<>();
-  private static Map<String, WXDomModule> sDomModuleMap = new HashMap<>();
-
-
-  /**
-   * module object dictionary
-   * K : instanceId, V : Modules
-   */
-  private static Map<String, Map<String, WXModule>> sInstanceModuleMap = new ConcurrentHashMap<>();
-
-
-  public static boolean registerModule(Map<String, RegisterCache.ModuleCache> moduleCacheMap) {
-    if (moduleCacheMap.isEmpty())
-      return true;
-
-    final Iterator<Entry<String, RegisterCache.ModuleCache>> iterator = moduleCacheMap.entrySet().iterator();
-    WXBridgeManager.getInstance()
-            .postWithName(new Runnable() {
-              @Override
-              public void run() {
-                Map<String, Object> modules = new HashMap<>();
-
-                while (iterator.hasNext()) {
-                  Entry<String, RegisterCache.ModuleCache> next = iterator.next();
-                  RegisterCache.ModuleCache value = next.getValue();
-                  String moduleName = value.name;
-                  if (TextUtils.equals(moduleName, WXDomModule.WXDOM)) {
-                    WXLogUtils.e("Cannot registered module with name 'dom'.");
-                    continue;
-                  }
-
-                  if (sModuleFactoryMap != null && sModuleFactoryMap.containsKey(moduleName)) {
-                    WXLogUtils.w("WXComponentRegistry Duplicate the Module name: " + moduleName);
-                  }
-                  ModuleFactory factory = value.factory;
-                  try {
-                    registerNativeModule(moduleName, factory);
-                  } catch (WXException e) {
-                    WXLogUtils.e("registerNativeModule" + e);
-                  }
-
-                  if (value.global) {
-                    try {
-                      WXModule wxModule = factory.buildInstance();
-                      wxModule.setModuleName(moduleName);
-                      sGlobalModuleMap.put(moduleName, wxModule);
-                    } catch (Exception e) {
-                      WXLogUtils.e(moduleName + " class must have a default constructor without params. ", e);
-                    }
-                  }
-
-                  try {
-                    sModuleFactoryMap.put(moduleName, new ModuleFactoryImpl(factory));
-                  } catch (Throwable e) {
-
-                  }
-                  modules.put(moduleName, factory.getMethods());
-                }
-                WXSDKManager.getInstance().registerModules(modules);
-              }
-            },null,"registerModule From Cache");
-    return true;
-  }
-
-  /**
-   * Register module to JavaScript and Android
-   */
-  public static boolean registerModule(final String moduleName, final ModuleFactory factory, final boolean global) throws WXException {
-    if (moduleName == null || factory == null) {
-      return false;
-    }
-
-    if (TextUtils.equals(moduleName,WXDomModule.WXDOM)) {
-      WXLogUtils.e("Cannot registered module with name 'dom'.");
-      return false;
-    }
-
-    if(RegisterCache.getInstance().cacheModule(moduleName,factory,global)) {
-      return true;
-    }
-
-    //execute task in js thread to make sure register order is same as the order invoke register method.
-    WXBridgeManager.getInstance()
-            .postWithName(new Runnable() {
-              @Override
-              public void run() {
-                if (sModuleFactoryMap != null && sModuleFactoryMap.containsKey(moduleName)) {
-                  WXLogUtils.w("WXComponentRegistry Duplicate the Module name: " + moduleName);
-                }
-                try {
-                  registerNativeModule(moduleName, factory);
-                } catch (WXException e) {
-                  WXLogUtils.e("registerNativeModule" + e);
-                }
-
-                if (global) {
-                  try {
-                    WXModule wxModule = factory.buildInstance();
-                    wxModule.setModuleName(moduleName);
-                    sGlobalModuleMap.put(moduleName, wxModule);
-                  } catch (Exception e) {
-                    WXLogUtils.e(moduleName + " class must have a default constructor without params. ", e);
-                  }
-                }
-
-                registerJSModule(moduleName, factory);
-
-                try {
-                  sModuleFactoryMap.put(moduleName, new ModuleFactoryImpl(factory));
-                } catch (Throwable e) {
-
-                }
-              }
-            },null,"registerModule");
-    return true;
-
-  }
-
-  static boolean registerNativeModule(String moduleName, ModuleFactory factory) throws WXException {
-    if (factory == null) {
-      return false;
-    }
-
-    try {
-      if (!sModuleFactoryMap.containsKey(moduleName) ) {
-        sModuleFactoryMap.put(moduleName, new ModuleFactoryImpl(factory));
-      }
-    }catch (ArrayStoreException e){
-      e.printStackTrace();
-      //ignore:
-      //may throw this exception:
-      //java.lang.String cannot be stored in an array of type java.util.HashMap$HashMapEntry[]
-
-      WXLogUtils.e("[WXModuleManager] registerNativeModule Error moduleName:"  + moduleName + " Error:" + e.toString());
-    }
-    return true;
-  }
-
-  static boolean registerJSModule(String moduleName, ModuleFactory factory) {
-    Map<String, Object> modules = new HashMap<>();
-    modules.put(moduleName, factory.getMethods());
-    WXSDKManager.getInstance().registerModules(modules);
-    return true;
-  }
-
-  static Object callModuleMethod(final String instanceId, String moduleStr, String methodStr, JSONArray args) {
-    ModuleFactory factory = sModuleFactoryMap.get(moduleStr).mFactory;
-    if(factory == null){
-      WXLogUtils.e("[WXModuleManager] module factory not found.");
-      return null;
-    }
-    final WXModule wxModule = findModule(instanceId, moduleStr,factory);
-    if (wxModule == null) {
-      return null;
-    }
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    wxModule.mWXSDKInstance = instance;
-
-    final Invoker invoker = factory.getMethodInvoker(methodStr);
-    try {
-      if(instance != null) {
-        IWXUserTrackAdapter userTrackAdapter = WXSDKManager.getInstance().getIWXUserTrackAdapter();
-        if(userTrackAdapter != null) {
-          HashMap<String, Serializable> data = new HashMap<String, Serializable>();
-          data.put(IWXUserTrackAdapter.MONITOR_ERROR_CODE, "101");
-          data.put(IWXUserTrackAdapter.MONITOR_ARG, moduleStr + "." + methodStr);
-          data.put(IWXUserTrackAdapter.MONITOR_ERROR_MSG, instance.getBundleUrl());
-          userTrackAdapter.commit(instance.getContext(), null, IWXUserTrackAdapter.INVOKE_MODULE, null, data);
-        }
-        return dispatchCallModuleMethod(instance,wxModule,args,invoker);
-      } else {
-        WXLogUtils.e("callModuleMethod >>> instance is null");
-        return null;
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("callModuleMethod >>> invoke module:" + moduleStr + ", method:" + methodStr + " failed. ", e);
-      return null;
-    } finally {
-      if (wxModule instanceof WXDomModule || wxModule instanceof WXTimerModule) {
-        wxModule.mWXSDKInstance = null;
-      }
-    }
-  }
-
-  private static Object dispatchCallModuleMethod(@NonNull WXSDKInstance instance, @NonNull WXModule wxModule,
-                                                 @NonNull JSONArray args, @NonNull Invoker invoker) throws Exception{
-    if(!instance.isPreRenderMode()) {
-      return instance.getNativeInvokeHelper().invoke(wxModule,invoker,args);
-    }
-    // we are in preRender mode
-    if(invoker.isRunOnUIThread()) {/*ASYNC CALL*/
-//      DOMAction moduleInvocationAction = Actions.getModuleInvocationAction(wxModule,args,invoker);
-//      WXSDKManager.getInstance().getWXDomManager().postAction(instance.getInstanceId(), moduleInvocationAction,false);
-      return null;
-    } else {/*SYNC CALL*/
-      return instance.getNativeInvokeHelper().invoke(wxModule,invoker,args);
-    }
-  }
-
-  public static boolean hasModule(String module) {
-    return sGlobalModuleMap.containsKey(module) || sModuleFactoryMap.containsKey(module);
-  }
-
-  private static WXModule findModule(String instanceId, String moduleStr,ModuleFactory factory) {
-    // find WXModule
-    WXModule wxModule = sGlobalModuleMap.get(moduleStr);
-
-    //not global module
-    if (wxModule == null) {
-      Map<String, WXModule> moduleMap = sInstanceModuleMap.get(instanceId);
-      if (moduleMap == null) {
-        moduleMap = new ConcurrentHashMap<>();
-        sInstanceModuleMap.put(instanceId, moduleMap);
-      }
-      // if cannot find the Module, create a new Module and save it
-      wxModule = moduleMap.get(moduleStr);
-      if (wxModule == null) {
-        try {
-          if(factory instanceof ConfigModuleFactory){
-            WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-            wxModule = ((ConfigModuleFactory) factory).buildInstance(instance);
-          }else{
-            wxModule = factory.buildInstance();
-          }
-          wxModule.setModuleName(moduleStr);
-        } catch (Exception e) {
-          WXLogUtils.e(moduleStr + " module build instace failed.", e);
-          return null;
-        }
-        moduleMap.put(moduleStr, wxModule);
-      }
-    }
-
-    return wxModule;
-  }
-
-  /**Hook Activity life cycle callback begin***/
-
-
-  public static void onActivityCreate(String instanceId){
-
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onActivityCreate();
-        } else {
-          WXLogUtils.w("onActivityCreate can not find the " + key + " module");
-        }
-      }
-    }
-
-  }
-
-  public static void onActivityStart(String instanceId){
-
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onActivityStart();
-        } else {
-          WXLogUtils.w("onActivityStart can not find the " + key + " module");
-        }
-      }
-    }
-  }
-
-  public static void onActivityPause(String instanceId){
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onActivityPause();
-        } else {
-          WXLogUtils.w("onActivityPause can not find the " + key + " module");
-        }
-      }
-    }
-  }
-
-  public static void onActivityResume(String instanceId){
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onActivityResume();
-        } else {
-          WXLogUtils.w("onActivityResume can not find the " + key + " module");
-        }
-      }
-    }
-  }
-
-  public static void onActivityStop(String instanceId){
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onActivityStop();
-        } else {
-          WXLogUtils.w("onActivityStop can not find the " + key + " module");
-        }
-      }
-    }
-  }
-
-  public static void onActivityDestroy(String instanceId){
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onActivityDestroy();
-        } else {
-          WXLogUtils.w("onActivityDestroy can not find the " + key + " module");
-        }
-      }
-    }
-  }
-
-  public static boolean onActivityBack(String instanceId){
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          return module.onActivityBack();
-        } else {
-          WXLogUtils.w("onActivityCreate can not find the " + key + " module");
-        }
-      }
-    }
-    return false;
-  }
-
-  public static void onActivityResult(String instanceId,int requestCode, int resultCode, Intent data){
-
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onActivityResult(requestCode, resultCode, data);
-        } else {
-          WXLogUtils.w("onActivityResult can not find the " + key + " module");
-        }
-      }
-    }
-  }
-
-  public static boolean onCreateOptionsMenu(String instanceId,Menu menu) {
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onCreateOptionsMenu(menu);
-        } else {
-          WXLogUtils.w("onActivityResult can not find the " + key + " module");
-        }
-      }
-    }
-    return false;
-  }
-
-  public static void onRequestPermissionsResult(String instanceId ,int requestCode, String[] permissions, int[] grantResults) {
-    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
-    if(modules!=null) {
-      for (String key : modules.keySet()) {
-        WXModule module = modules.get(key);
-        if (module != null) {
-          module.onRequestPermissionsResult(requestCode, permissions, grantResults);
-        } else {
-          WXLogUtils.w("onActivityResult can not find the " + key + " module");
-        }
-      }
-    }
-  }
-
-  public static void destroyInstanceModules(String instanceId) {
-    sDomModuleMap.remove(instanceId);
-    Map<String, WXModule> moduleMap = sInstanceModuleMap.remove(instanceId);
-    if (moduleMap == null || moduleMap.size() < 1) {
-      return;
-    }
-    Iterator<Entry<String, WXModule>> iterator = moduleMap.entrySet().iterator();
-    Entry<String, WXModule> entry;
-    while (iterator.hasNext()) {
-      entry = iterator.next();
-      WXModule module = entry.getValue();
-      if(module instanceof Destroyable){
-        ((Destroyable)module).destroy();
-      }
-
-    }
-  }
-
-  public static void createDomModule(WXSDKInstance instance){
-    if(instance != null) {
-      sDomModuleMap.put(instance.getInstanceId(), new WXDomModule(instance));
-    }
-  }
-
-  public static void destoryDomModule(String instanceID){
-    sDomModuleMap.remove(instanceID);
-  }
-
-  public static WXDomModule getDomModule(String instanceId){
-    return sDomModuleMap.get(instanceId);
-  }
-
-  public static void reload(){
-    if (sModuleFactoryMap != null && sModuleFactoryMap.size() > 0) {
-      for (Map.Entry<String, ModuleFactoryImpl> entry : sModuleFactoryMap.entrySet()) {
-        try {
-          registerJSModule(entry.getKey(), entry.getValue().mFactory);
-        } catch (Throwable e) {
-
-        }
-      }
-    }
-  }
-
-  /**
-   * registerWhenCreateInstance
-   */
-  public static void registerWhenCreateInstance(){
-    if (sModuleFactoryMap != null && sModuleFactoryMap.size() > 0) {
-      for (Map.Entry<String, ModuleFactoryImpl> entry : sModuleFactoryMap.entrySet()) {
-        try {
-          if (!entry.getValue().hasRigster) {
-            registerJSModule(entry.getKey(), entry.getValue().mFactory);
-          }
-        } catch (Throwable e) {
-
-        }
-      }
-    }
-  }
-
-  /**
-   * resetAllModuleState
-   */
-  public static void resetAllModuleState() {
-    if (sModuleFactoryMap != null && sModuleFactoryMap.size() > 0) {
-      for (Map.Entry<String, ModuleFactoryImpl> entry : sModuleFactoryMap.entrySet()) {
-        entry.getValue().hasRigster = false;
-      }
-    }
-  }
-
-  /**
-   * resetModuleState
-   * @param module
-   * @param state
-   */
-  public static void resetModuleState(String module, boolean state) {
-    if (sModuleFactoryMap != null && sModuleFactoryMap.size() > 0) {
-      for (Map.Entry<String, ModuleFactoryImpl> entry : sModuleFactoryMap.entrySet()) {
-        try {
-          if (entry.getKey() != null && entry.getKey().equals(module)) {
-            entry.getValue().hasRigster = state;
-          }
-        } catch (Throwable e) {
-
-        }
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXParams.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXParams.java
deleted file mode 100644
index a20b20f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXParams.java
+++ /dev/null
@@ -1,303 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.base.CalledByNative;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.io.Serializable;
-import java.util.HashMap;
-import java.util.Map;
-
-public class WXParams implements Serializable {
-
-  private String platform;
-  private String osVersion;
-  private String appVersion;
-  private String weexVersion;
-  private String deviceModel;
-  private String appName;
-  private String deviceWidth;
-  private String deviceHeight;
-  private String shouldInfoCollect;
-  private String logLevel;
-  private String needInitV8;
-  private String cacheDir;
-  private String useSingleProcess;
-  private String crashFilePath;
-  private String libJssPath;
-  private String layoutDirection;
-
-  private String libJscPath;
-  private String libIcuPath;
-  private String libLdPath;
-  private String libJsbPath;
-
-  private Map<String, String> options;
-
-  @CalledByNative
-  public Object getOptions() {
-    return options;
-  }
-
-  public void setOptions(Map<String, String> options) {
-    this.options = options;
-  }
-
-  public String getShouldInfoCollect() {
-    return shouldInfoCollect;
-  }
-
-  public void setShouldInfoCollect(String shouldInfoCollect) {
-    this.shouldInfoCollect = shouldInfoCollect;
-  }
-
-  @CalledByNative
-  public String getPlatform() {
-    return platform;
-  }
-
-  public void setPlatform(String platform) {
-    this.platform = platform;
-  }
-
-  public void setCacheDir(String cache) {
-    this.cacheDir = cache;
-  }
-
-  @CalledByNative
-  public String getCacheDir() {
-    return this.cacheDir;
-  }
-
-  @CalledByNative
-  public String getOsVersion() {
-    return osVersion;
-  }
-
-  public void setOsVersion(String osVersion) {
-    this.osVersion = osVersion;
-  }
-
-  @CalledByNative
-  public String getAppVersion() {
-    return appVersion;
-  }
-
-  public void setAppVersion(String appVersion) {
-    this.appVersion = appVersion;
-  }
-
-  @CalledByNative
-  public String getWeexVersion() {
-    return weexVersion;
-  }
-
-  public void setWeexVersion(String weexVersion) {
-    this.weexVersion = weexVersion;
-  }
-
-  @CalledByNative
-  public String getDeviceModel() {
-    return deviceModel;
-  }
-
-  public void setDeviceModel(String deviceModel) {
-    this.deviceModel = deviceModel;
-  }
-
-  @CalledByNative
-  public String getLayoutDirection() {return layoutDirection;}
-
-  public void setLayoutDirection(String direction) { this.layoutDirection = direction; }
-
-  @CalledByNative
-  public String getAppName() {
-    return appName;
-  }
-
-  public void setAppName(String appName) {
-    this.appName = appName;
-  }
-
-  @CalledByNative
-  public String getDeviceWidth() {
-    return deviceWidth;
-  }
-
-  @CalledByNative
-  public boolean getReleaseMap() {
-    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
-    if (null == adapter){
-      return false;
-    }
-    String doRelease = adapter.getConfigWhenInit("wxapm","release_map","true");
-    WXLogUtils.e("getReleaseMap:"+doRelease);
-    return "true".equalsIgnoreCase(doRelease);
-  }
-
-
-  /**
-   * Device should not be set manually, instead it suppose to represent the width of device and
-   * initialized automatically.
-   * @param deviceWidth
-   */
-  @Deprecated
-  public void setDeviceWidth(String deviceWidth) {
-    this.deviceWidth = deviceWidth;
-  }
-
-  @CalledByNative
-  public String getDeviceHeight() {
-    return deviceHeight;
-  }
-
-  public void setDeviceHeight(String deviceHeight) {
-    this.deviceHeight = deviceHeight;
-  }
-
-  public String getLogLevel() {
-    if(logLevel == null){
-      return "";
-    }
-    return logLevel;
-  }
-
-  @CalledByNative
-  public String getUseSingleProcess() {
-    WXLogUtils.e("getUseSingleProcess is running " + useSingleProcess);
-    return useSingleProcess;
-  }
-
-  public void setUseSingleProcess(String useSingleProcess) {
-    this.useSingleProcess = useSingleProcess;
-  }
-
-  public void setLogLevel(String logLevel) {
-    this.logLevel = logLevel;
-  }
-
-  public String getNeedInitV8() {
-    if(needInitV8 ==null){
-      return "";
-    }
-    return this.needInitV8;
-  }
-
-  public void setNeedInitV8(boolean need) {
-    if (need) {
-      this.needInitV8 = "1";
-    } else {
-      this.needInitV8 = "0";
-    }
-  }
-
-  public void setCrashFilePath(String crashFilePath) {
-    WXLogUtils.e("WXParams","setCrashFilePath: " + crashFilePath);
-    this.crashFilePath = crashFilePath;
-  }
-
-  @CalledByNative
-  public String getCrashFilePath() {
-    WXLogUtils.e("WXParams", "getCrashFilePath:" + crashFilePath);
-    return this.crashFilePath;
-  }
-
-  @CalledByNative
-  public String getLibJssPath() {
-    WXLogUtils.e("getLibJssPath is running " + libJssPath);
-    return libJssPath;
-  }
-
-  @CalledByNative
-  public String getLibJsbPath() {
-    WXLogUtils.e("getLibJsbPath is running " + libJsbPath);
-    return libJsbPath;
-  }
-
-  public void setLibJsbPath(String libJsbPath) {
-    this.libJsbPath = libJsbPath;
-  }
-
-  @CalledByNative
-  public String getLibJscPath() {
-    WXLogUtils.e("getLibJscPath is running " + libJscPath);
-    return libJscPath;
-  }
-  public void setLibJscPath(String libJscPath) {
-    this.libJscPath = libJscPath;
-  }
-  public void setLibJssPath(String libJssPath) {
-    this.libJssPath = libJssPath;
-  }
-  @CalledByNative
-  public String getLibIcuPath() {
-    WXLogUtils.e("getLibIcuPath is running " + libIcuPath);
-    return libIcuPath;
-  }
-
-  public void setLibIcuPath(String libIcuPath) {
-    this.libIcuPath = libIcuPath;
-  }
-
-  @CalledByNative
-  public String getLibLdPath() {
-    WXLogUtils.e("getLibLdPath is running " + libLdPath);
-    return libLdPath;
-  }
-
-  public void setLibLdPath(String libLdPath) {
-    this.libLdPath = libLdPath;
-  }
-
-  @CalledByNative
-  public String getUseRunTimeApi() {
-    return String.valueOf(WXEnvironment.sUseRunTimeApi);
-  }
-
-  public Map<String, Object> toMap() {
-    HashMap<String, Object> map  = new HashMap<>();
-    map.put("appName", appName);
-    map.put("appVersion", appVersion);
-    map.put("cacheDir", cacheDir);
-    map.put("deviceHeight", deviceHeight);
-    map.put("deviceModel", deviceModel);
-    map.put("deviceWidth", deviceWidth);
-    map.put("layoutDirection", layoutDirection);
-    map.put("libJssPath", libJssPath);
-    map.put("logLevel", logLevel);
-    map.put("needInitV8", needInitV8);
-    map.put("osVersion", osVersion);
-    map.put("platform", platform);
-    map.put("useSingleProcess", useSingleProcess);
-    map.put("shouldInfoCollect", shouldInfoCollect);
-    map.put("weexVersion", weexVersion);
-    map.put("crashFilePath", crashFilePath);
-    map.put("libJscPath", libJscPath);
-    map.put("libIcuPath", libIcuPath);
-    map.put("libLdPath", libLdPath);
-    map.put("options", options);
-    map.put("useRunTimeApi",WXEnvironment.sUseRunTimeApi);
-    map.put("__enable_native_promise__",!WXEnvironment.sUseRunTimeApi);
-    return map;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXServiceManager.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXServiceManager.java
deleted file mode 100644
index 7b052cc..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXServiceManager.java
+++ /dev/null
@@ -1,99 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import android.text.TextUtils;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.common.WXJSService;
-
-import java.util.HashMap;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-
-public class WXServiceManager {
-
-    private static volatile ConcurrentHashMap<String, WXJSService> sInstanceJSServiceMap = new ConcurrentHashMap<>();
-
-    public static boolean registerService(String name, String serviceScript, Map<String, Object> options) {
-        if (TextUtils.isEmpty(name) || TextUtils.isEmpty(serviceScript)) return false;
-
-        String param1 = "register: global.registerService, unregister: global.unregisterService";
-        String param2 = "serviceName: \"" + name + "\"";
-        for (String key: options.keySet()) {
-            // TODO - why always string?
-            Object value = options.get(key);
-            if (value instanceof  String) {
-                param2 += ", \'" + key + "\': \'" + value + "\'";
-            } else {
-                param2 += ", \'" + key + "\': " + value;
-            }
-        }
-        String serviceJs = String.format(";(function(service, options){ ;%s; })({ %s }, { %s });", serviceScript, param1, param2);
-
-        WXJSService service = new WXJSService();
-        service.setName(name);
-        service.setScript(serviceScript);
-        service.setOptions(options);
-        sInstanceJSServiceMap.put(name, service);
-
-        WXBridgeManager.getInstance().execJSService(serviceJs);
-        return true;
-    }
-
-    public static boolean unRegisterService(String name) {
-        if (TextUtils.isEmpty(name)) return false;
-
-        if(WXEnvironment.isApkDebugable()) {
-            sInstanceJSServiceMap.remove(name);
-        }
-
-        String js = String.format("global.unregisterService( \"%s\" );", name);
-        WXBridgeManager.getInstance().execJSService(js);
-        return true;
-    }
-
-
-    public static void execAllCacheJsService() {
-        for (String serviceName: sInstanceJSServiceMap.keySet()) {
-            WXJSService service = sInstanceJSServiceMap.get(serviceName);
-            registerService(service.getName(), service.getScript(), service.getOptions());
-        }
-    }
-
-    public static WXJSService getService(String serviceName) {
-        if (sInstanceJSServiceMap != null) {
-            return sInstanceJSServiceMap.get(serviceName);
-        }
-        return null;
-    }
-
-    public static void reload() {
-        if(sInstanceJSServiceMap != null && sInstanceJSServiceMap.size() > 0) {
-            WXBridgeManager.getInstance().post(new Runnable() {
-                @Override
-                public void run() {
-                    for (Map.Entry<String, WXJSService> entry : sInstanceJSServiceMap.entrySet()) {
-                        WXJSService service = entry.getValue();
-                        registerService(service.getName(), service.getScript(), service.getOptions());
-                    }
-                }
-            });
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXTask.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXTask.java
deleted file mode 100644
index c236ba6..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXTask.java
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import com.taobao.weex.common.IWXObject;
-
-import java.util.ArrayList;
-
-/**
- * Weex JS Native task
- */
-public class WXTask implements IWXObject {
-
-  /**
-   * Native module
-   */
-  public String module;
-
-  /**
-   * The method of native module
-   */
-  public String method;
-
-  /**
-   * The method parameters
-   */
-  public ArrayList<String> args;
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/bridge/WXValidateProcessor.java b/android/sdk/src/main/java/com/taobao/weex/bridge/WXValidateProcessor.java
deleted file mode 100644
index 86be2b1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/bridge/WXValidateProcessor.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by fengjunjie
- */
-public interface WXValidateProcessor {
-
-    WXModuleValidateResult onModuleValidate(WXSDKInstance wxsdkInstance, String moduleStr,
-                                            String methodStr, JSONArray params,
-                                            JSONObject options);
-
-    WXComponentValidateResult onComponentValidate(WXSDKInstance wxsdkInstance,
-                                                  String componentName,
-                                                  WXComponent parentComponent);
-
-    boolean needValidate(String bundleUrl);
-
-    class WXComponentValidateResult {
-
-        public boolean isSuccess;
-
-        public String replacedComponent;
-
-        public JSONObject validateInfo;
-
-    }
-
-    class WXModuleValidateResult {
-
-        public boolean isSuccess;
-
-        public JSONObject validateInfo;
-
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/Constants.java b/android/sdk/src/main/java/com/taobao/weex/common/Constants.java
deleted file mode 100644
index ad00f12..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/Constants.java
+++ /dev/null
@@ -1,388 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public class Constants {
-
-  public interface Orientation {
-
-    int HORIZONTAL = 0;
-    int VERTICAL = 1;
-  }
-
-  public interface Weex {
-    String REF = "ref";
-    String INSTANCEID = "instanceid";
-    String TYPE = "type";
-  }
-
-  public interface Name {
-
-    String DEFAULT_WIDTH = "defaultWidth";
-    String DEFAULT_HEIGHT = "defaultHeight";
-    String HREF = "href";
-    String WIDTH = "width";
-    String MIN_WIDTH = "minWidth";
-    String MAX_WIDTH = "maxWidth";
-    String HEIGHT = "height";
-    String MIN_HEIGHT = "minHeight";
-    String MAX_HEIGHT = "maxHeight";
-    String ALIGN_ITEMS = "alignItems";
-    String ALIGN_SELF = "alignSelf";
-    String FLEX = "flex";
-    String FLEX_DIRECTION = "flexDirection";
-    String JUSTIFY_CONTENT = "justifyContent";
-    String FLEX_WRAP = "flexWrap";
-
-    String MARGIN = "margin";
-    String MARGIN_TOP = "marginTop";
-    String MARGIN_LEFT = "marginLeft";
-    String MARGIN_RIGHT = "marginRight";
-    String MARGIN_BOTTOM = "marginBottom";
-    String PADDING = "padding";
-    String PADDING_TOP = "paddingTop";
-    String PADDING_LEFT = "paddingLeft";
-    String PADDING_RIGHT = "paddingRight";
-    String PADDING_BOTTOM = "paddingBottom";
-
-    String LEFT = "left";
-    String TOP = "top";
-    String RIGHT = "right";
-    String BOTTOM = "bottom";
-
-
-    String BACKGROUND_COLOR = "backgroundColor";
-    String BACKGROUND_IMAGE = "backgroundImage";
-    String OPACITY = "opacity";
-    String BORDER_RADIUS = "borderRadius";
-    String BORDER_WIDTH = "borderWidth";
-    String BORDER_COLOR = "borderColor";
-    String BORDER_STYLE = "borderStyle";
-    String BORDER_TOP_WIDTH = "borderTopWidth";
-    String BORDER_RIGHT_WIDTH = "borderRightWidth";
-    String BORDER_BOTTOM_WIDTH = "borderBottomWidth";
-    String BORDER_LEFT_WIDTH = "borderLeftWidth";
-    String BORDER_TOP_COLOR = "borderTopColor";
-    String BORDER_RIGHT_COLOR = "borderRightColor";
-    String BORDER_BOTTOM_COLOR = "borderBottomColor";
-    String BORDER_LEFT_COLOR = "borderLeftColor";
-    String BORDER_TOP_LEFT_RADIUS = "borderTopLeftRadius";
-    String BORDER_TOP_RIGHT_RADIUS = "borderTopRightRadius";
-    String BORDER_BOTTOM_RIGHT_RADIUS = "borderBottomRightRadius";
-    String BORDER_BOTTOM_LEFT_RADIUS = "borderBottomLeftRadius";
-    String BORDER_RIGHT_STYLE = "borderRightStyle";
-    String BORDER_BOTTOM_STYLE = "borderBottomStyle";
-    String BORDER_LEFT_STYLE = "borderLeftStyle";
-    String BORDER_TOP_STYLE = "borderTopStyle";
-    String BOX_SHADOW = "boxShadow";
-    String SHADOW_QUALITY = "shadowQuality";
-
-    String POSITION = "position";
-
-    String KEEP_SCROLL_POSITION = "keepScrollPosition";
-
-    String TEXT_DECORATION = "textDecoration";
-    String TEXT_ALIGN = "textAlign";
-    String FONT_WEIGHT = "fontWeight";
-    String FONT_STYLE = "fontStyle";
-    String FONT_SIZE = "fontSize";
-    String COLOR = "color";
-    String LINES = "lines";
-    String FONT_FAMILY = "fontFamily";
-    String TEXT_OVERFLOW = "textOverflow";
-    String ELLIPSIS = "ellipsis";
-    String LINE_HEIGHT = "lineHeight";
-    String DISABLED = "disabled";
-    String VALUE = "value";
-    String IMAGE_QUALITY = "imageQuality";
-    String FILTER = "filter";
-    String QUALITY = "quality";
-    String SRC = "src";
-    String SOURCE = "source";
-    String PLACE_HOLDER = "placeHolder";
-    String RESIZE_MODE = "resizeMode";
-    String AUTO_RECYCLE = "autoBitmapRecycle";
-    String SHOW_INDICATORS = "showIndicators";
-    String AUTO_PLAY = "autoPlay";
-    String AUTOPLAY = "autoplay";
-    String CONTROLS = "controls";
-    String ZORDERTOP = "zOrderTop";
-    String SCROLL_DIRECTION = "scrollDirection";
-    String SCOPE = "scope";
-    String RECYCLE = "recycle";
-    String LOADMORERETRY = "loadmoreretry";
-    String LOADMOREOFFSET = "loadmoreoffset";
-    String RECYCLE_IMAGE = "recycleImage";
-    String LAYOUT = "layout";
-    String SPAN_OFFSETS = "spanOffsets";
-    String COLUMN_WIDTH = "columnWidth";
-    String COLUMN_COUNT = "columnCount";
-    String COLUMN_GAP = "columnGap";
-    String SHOW_SCROLLBAR = "showScrollbar";
-    String LEFT_GAP= "leftGap";
-    String RIGHT_GAP= "rightGap";
-    String OVERFLOW = "overflow";
-    String TYPE = "type";
-    String PLACEHOLDER = "placeholder";
-    String PLACEHOLDER_COLOR = "placeholderColor";
-    String AUTOFOCUS = "autofocus";
-    String SINGLELINE = "singleline";
-    String MAX_LENGTH = "maxLength";
-    String MAXLENGTH = "maxlength";
-    String ROWS = "rows";
-    String CHECKED = "checked";
-    String ANIMATING = "animating";
-    String VISIBILITY = "visibility";
-    String ITEM_COLOR = "itemColor";
-    String ITEM_SELECTED_COLOR = "itemSelectedColor";
-    String ITEM_SIZE = "itemSize";
-    String DISPLAY = "display";
-    String SHOW_LOADING = "show-loading";
-    String SUFFIX = "suffix";
-    String RESIZE = "resize";
-    String IMAGE_SHARPEN = "imageSharpen";
-    String SHARPEN = "sharpen";
-    String PREFIX = "prefix";
-    String INDEX = "index";
-    String INTERVAL = "interval";
-    String PLAY_STATUS = "playStatus";
-    String FONT_FACE = "fontFace";
-    String MAX = "max";
-    String MIN = "min";
-    String NAV_BAR_VISIBILITY = "hidden";
-    String OFFSET_X_ACCURACY = "offsetXAccuracy";
-    String OFFSET_X_RATIO = "offsetXRatio";
-    String ELEVATION = "elevation";
-    String PERSPECTIVE = "perspective";
-    String SCROLLABLE = "scrollable";
-    String DRAGGABLE = "draggable";
-    String DISTANCE_Y = "dy";
-    String PULLING_DISTANCE = "pullingDistance";
-    String VIEW_HEIGHT = "viewHeight";
-    String PREVENT_MOVE_EVENT = "preventMoveEvent";
-    String SELECTION_START = "selectionStart";
-    String SELECTION_END = "selectionEnd";
-    String OFFSET_ACCURACY = "offsetAccuracy";
-    String CONTENT_SIZE = "contentSize";
-    String CONTENT_OFFSET = "contentOffset";
-    String ISDRAGGING = "isDragging";
-    String X = "x";
-    String Y = "y";
-    String RETURN_KEY_TYPE = "returnKeyType";
-    String OFFSET = "offset";
-    String ANIMATED = "animated";
-    String STABLE = "stable";
-    String TRANSFORM = "transform";
-    String TRANSFORM_ORIGIN = "transformOrigin";
-    String KEEP_INDEX = "keepIndex";
-    String KEEP_SELECTION_INDEX = "keepSelectionIndex";
-
-    String INSERT_CELL_ANIMATION = "insertAnimation";
-    String DELETE_CELL_ANIMATION = "deleteAnimation";
-    String AUTO = "auto";
-    String NORMAL = "normal";
-    String ARIA_LABEL = "ariaLabel";
-    String ARIA_HIDDEN = "ariaHidden";
-    String ROLE = "role";
-
-    String LAYERLIMIT = "layerLimit";
-    String LAYER_LIMIT = "layer-limit";
-
-    String DIRECTION = "direction";
-    String RTL = "rtl";
-
-    String STICKY_OFFSET = "stickyOffset";
-    String HAS_FIXED_SIZE = "hasFixedSize";
-    String KEEP_POSITION_LAYOUT_DELAY = "keepPositionLayoutDelay";
-
-    String OVERFLOW_HIDDEN_HEIGHT = "overflowHiddenHeight";
-    String OVERFLOW_HIDDEN_WIDTH = "overflowHiddenWidth";
-
-    String PRIORITY  = "priority";
-
-    String STRATEGY  = "strategy";
-
-    String ALLOW_COPY_PASTE = "allowCopyPaste";
-    String INCLUDE_FONT_PADDING = "includeFontPadding";
-    String ENABLE_COPY = "enableCopy";
-
-    String PAGE_ENABLED = "pagingEnabled";
-    String PAGE_SIZE = "pageSize";
-
-
-
-    interface  Recycler{
-      String LIST_DATA = "listData";
-      String LIST_DATA_ITEM  ="alias";
-      String LIST_DATA_ITEM_INDEX = "index";
-      String LIST_DATA_TEMPLATE_SWITCH_KEY = "switch";
-      String SLOT_TEMPLATE_CASE = "case";
-      String SLOT_TEMPLATE_DEFAULT = "default";
-      String CELL_INDEX = "cellIndex";
-      String TYPE_INDEX = "typeIndex";
-    }
-
-
-    String VIF_FALSE = "ifFalse";
-    String UNDEFINED = "undefined";
-    String FLAT = "flat";
-    String RIPPLE_ENABLED = "rippleEnabled";
-
-    String SHOULD_STOP_PROPAGATION_INIT_RESULT = "shouldStopPropagationInitResult";
-    String SHOULD_STOP_PROPAGATION_INTERVAL = "shouldStopPropagationInterval";
-
-
-    String NEST_SCROLLING_ENABLED = "nestedScrollingEnabled";
-
-    String ORIENTATION  = "orientation";
-  }
-
-  public interface Value {
-
-    int DENSITY = 3;
-    int NAV_BAR_SHOWN = 0;
-    int NAV_BAR_HIDDEN = 1;
-    int AUTO = -1;
-    int COLUMN_GAP_NORMAL = 32;
-    int COLUMN_COUNT_NORMAL = 1;
-    String MULTI_COLUMN = "multi-column";
-    String GRID = "grid";
-    String STICKY = "sticky";
-    String FIXED = "fixed";
-    String LEFT = "left";
-    String RIGHT = "right";
-    String CENTER = "center";
-    String BOLD = "bold";
-    String ITALIC = "italic";
-    String ORIGINAL = "original";
-    String LOW = "low";
-    String NORMAL = "normal";
-    String HIGH = "high";
-    String VISIBLE = "visible";
-    String HIDDEN = "hidden";
-    String TEXT = "text";
-    String PASSWORD = "password";
-    String TEL = "tel";
-    String EMAIL = "email";
-    String URL = "url";
-    String DATE = "date";
-    String TIME = "time";
-    String DATETIME = "datetime";
-    String PLAY = "play";
-    String PAUSE = "pause";
-    String STOP = "stop";
-    String DIRECTION_LEFT = "left";
-    String DIRECTION_RIGHT = "right";
-    String DIRECTION_UP = "up";
-    String DIRECTION_DOWN = "down";
-    String NUMBER = "number";
-
-    String NONE = "none";
-    String DEFAULT = "default";
-
-    String HORIZONTAL = "horizontal";
-  }
-
-  public interface Event {
-
-    String CLICK = "click";
-    String APPEAR = "appear";
-    String DISAPPEAR = "disappear";
-    String LOADMORE = "loadmore";
-    String FOCUS = "focus";
-    String BLUR = "blur";
-    String INPUT = "input";
-    String VIEWAPPEAR = "viewappear";
-    String VIEWDISAPPEAR = "viewdisappear";
-    String START = "start";
-    String PAUSE = "pause";
-    String FINISH = "finish";
-    String FAIL = "fail";
-    String ERROR = "error";
-    String RECEIVEDTITLE = "receivedtitle";
-    String PAGEFINISH = "pagefinish";
-    String PAGESTART = "pagestart";
-    String ONREFRESH = "refresh";
-    String ONLOADING = "loading";
-    String ONLOAD = "load";
-    String CHANGE = "change";
-    String ONPULLING_DOWN = "pullingdown";
-    String ONPULLING_UP = "pullingup";
-    String SCROLL = "scroll";
-    String SCROLL_START = "scrollstart";
-    String SCROLL_END = "scrollend";
-    String CLICKBACKITEM = "clickbackitem";
-    String RESUME_EVENT = "WXApplicationDidBecomeActiveEvent";
-    String PAUSE_EVENT = "WXApplicationWillResignActiveEvent";
-    String RETURN = "return";
-    String KEYBOARD = "keyboard";
-
-    String UNSTICKY = "unsticky";
-    String STICKY = "sticky";
-
-    String ON_TRANSITION_END = "transitionEnd";
-
-    String LAYEROVERFLOW = "layeroverflow";
-
-    interface SLOT_LIFECYCLE {
-      String CREATE = "create";
-      String ATTACH = "attach";
-      String DETACH = "detach";
-      String DESTORY = "destroy";
-    }
-
-    String STOP_PROPAGATION = "stopPropagation";
-    String STOP_PROPAGATION_RAX = "stoppropagation";
-    String ONMESSAGE = "message";
-    String NATIVE_BACK = "nativeback";
-  }
-
-  public interface PSEUDO {
-    String ACTIVE = ":active";
-    String ENABLED = ":enabled";
-    String DISABLED = ":disabled";
-    String FOCUS = ":focus";
-  }
-
-  public interface Scheme {
-
-    String FILE = "file";
-    String HTTPS = "https";
-    String HTTP = "http";
-    String LOCAL = "local";
-    String DATA = "data";
-  }
-
-  public interface CodeCache {
-    String URL = "bundleUrl";
-    String DIGEST = "bundleDigest";
-    String PATH = "codeCachePath";
-    String BANNER_DIGEST = "digest";
-    String SAVE_PATH = "v8";
-  }
-
-  public interface TimeFunction {
-    String LINEAR = "linear";
-    String EASE_IN_OUT = "ease-in-out";
-    String EASE_IN = "ease-in";
-    String EASE_OUT = "ease-out";
-    String EASE = "ease";
-    String CUBIC_BEZIER = "cubic-bezier";
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/Destroyable.java b/android/sdk/src/main/java/com/taobao/weex/common/Destroyable.java
deleted file mode 100644
index 5f5fa1c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/Destroyable.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-/**
- * Created by sospartan on 5/20/16.
- */
-public interface Destroyable {
-    public void destroy();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/ICheckBindingScroller.java b/android/sdk/src/main/java/com/taobao/weex/common/ICheckBindingScroller.java
deleted file mode 100644
index b90137a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/ICheckBindingScroller.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.common;
-
-/**
- * Created by zhengshihan on 2017/6/5.
- */
-
-public interface ICheckBindingScroller {
-  boolean isNeedScroller(String ref,Object option);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/IWXBridge.java b/android/sdk/src/main/java/com/taobao/weex/common/IWXBridge.java
deleted file mode 100755
index d0727b1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/IWXBridge.java
+++ /dev/null
@@ -1,234 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import com.taobao.weex.bridge.ResultCallback;
-import com.taobao.weex.bridge.WXJSObject;
-import com.taobao.weex.bridge.WXParams;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.layout.ContentBoxMeasurement;
-import java.util.HashMap;
-import java.util.HashSet;
-
-/**
- * Bridge interface, native bridge and debug bridge both need to implement this interface
- */
-public interface IWXBridge extends IWXObject {
-
-  int DESTROY_INSTANCE = -1;
-  int INSTANCE_RENDERING = 1;
-  int INSTANCE_RENDERING_ERROR = 0;
-
-  /**
-   * init Weex
-   *
-   * @param framework assets/main.js
-   * @return
-   */
-  int initFramework(String framework, WXParams params);
-
-
-  /**
-   * init Weex
-   *
-   * @param framework assets/main.js
-   * @return
-   */
-  int initFrameworkEnv(String framework, WXParams params, String cacheDir, boolean pieSupport);
-
-
-  /**
-   * Update InitFramework Params
-   * */
-  void updateInitFrameworkParams(String key, String value, String desc);
-
-
-  void setLogType(float type, boolean isPerf);
-
-  void refreshInstance(String instanceId, String namespace, String function, WXJSObject[] args);
-
-  /**
-   * execute javascript function
-   */
-  int execJS(String instanceId, String namespace, String function, WXJSObject[] args);
-
-  /**
-   * execute javascript function with asynchronous callback
-   */
-  void execJSWithCallback(String instanceId, String namespace, String function, WXJSObject[] args, ResultCallback callback);
-
-  int execJSService(String javascript);
-
-  /**
-   * take the heap snapshot and serialize the heap to a local file.
-   *
-   * @param filename
-   */
-  void takeHeapSnapshot(String filename);
-
-  /**
-   * createInstance
-   * @param instanceId
-   * @param namespace
-   * @param function
-   * @param args
-   * @return
-   */
-  int createInstanceContext(String instanceId, String namespace, String function, WXJSObject[] args);
-
-  /**
-   * destoryInstance
-   * @param instanceId
-   * @param namespace
-   * @param function
-   * @param args
-   * @return
-   */
-  int destoryInstance(String instanceId, String namespace, String function, WXJSObject[] args);
-
-  /**
-   * execJSOnInstance
-   * @param instanceId
-   * @param script
-   * @param type
-   * @return
-   */
-  String execJSOnInstance(String instanceId, String script, int type);
-
-  /**
-   * js call native
-   */
-  int callNative(String instanceId, byte[] tasks, String callback);
-
-
-  int callNative(String instanceId, String tasks, String callback);
-
-  void reportJSException(String instanceId, String func, String exception);
-
-  Object callNativeModule(String instanceId, String module, String method, byte[] arguments, byte[] options);
-
-  void callNativeComponent(String instanceId, String ref, String method, byte[] arguments, byte[] options);
-
-  int callUpdateFinish(String instanceId, byte[] tasks, String callback);
-
-  int callRefreshFinish(String instanceId, byte[] tasks, String callback);
-
-  void reportServerCrash(String instanceId, String crashFile);
-
-
-  int callCreateBody(String instanceId, String componentType, String ref,
-                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
-                            float[] margins, float[] paddings, float[] borders);
-
-  int callAddElement(String instanceId, String componentType, String ref, int index, String parentRef,
-                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
-                            float[] margins, float[] paddings, float[] borders, boolean willLayout);
-
-  int callRemoveElement(String instanceId, String ref);
-
-  int callMoveElement(String instanceId, String ref, String parentref, int index);
-
-  int callAddEvent(String instanceId, String ref, String event);
-
-  int callRemoveEvent(String instanceId, String ref, String event);
-
-  int callUpdateStyle(String instanceId, String ref,
-                             HashMap<String, Object> styles,
-                             HashMap<String, String> paddings,
-                             HashMap<String, String> margins,
-                             HashMap<String, String> borders);
-
-  int callUpdateAttrs(String instanceId, String ref,
-                      HashMap<String, String> attrs);
-
-  int callAddChildToRichtext(String instanceId, String nodeType, String ref, String parentRef, String richTextRef,
-                             HashMap<String, String> styles, HashMap<String, String> attrs);
-
-  int callRemoveChildFromRichtext(String instanceId, String ref, String parentRef, String richTextRef);
-
-  int callUpdateRichtextStyle(String instanceId, String ref, HashMap<String, String> styles, String parentRef, String richTextRef);
-
-  int callUpdateRichtextChildAttr(String instanceId, String ref, HashMap<String, String> attrs, String parentRef, String richTextRef);
-
-  int callLayout(String instanceId, String ref, int top, int bottom, int left, int right, int height, int width, boolean isRTL, int index);
-
-  int callCreateFinish(String instanceId);
-
-  int callRenderSuccess(String instanceId);
-
-  int callAppendTreeCreateFinish(String instanceId, String ref);
-
-  int callHasTransitionPros(String instanceId, String ref, HashMap<String, String> styles);
-
-  ContentBoxMeasurement getMeasurementFunc(String instanceId, long renderObjectPtr);
-
-  void bindMeasurementToRenderObject(long ptr);
-
-  void setRenderContainerWrapContent(boolean wrap, String instanceId);
-
-  long[] getFirstScreenRenderTime(String instanceId);
-
-  long[] getRenderFinishTime(String instanceId);
-
-  void setDefaultHeightAndWidthIntoRootDom(String instanceId, float defaultWidth, float defaultHeight, boolean isWidthWrapContent, boolean isHeightWrapContent);
-
-  void onInstanceClose(String instanceId);
-
-  void forceLayout(String instanceId);
-
-  boolean notifyLayout(String instanceId);
-
-  void setStyleWidth(String instanceId, String ref, float value);
-
-  void setStyleHeight(String instanceId, String ref, float value);
-
-  void setMargin(String instanceId, String ref, CSSShorthand.EDGE edge, float value);
-
-  void setPadding(String instanceId, String ref, CSSShorthand.EDGE edge, float value);
-
-  void setPosition(String instanceId, String ref, CSSShorthand.EDGE edge, float value);
-
-  void markDirty(String instanceId, String ref, boolean dirty);
-
-  void setDeviceDisplay(String instanceId, float width, float height, float scale);
-
-  void registerCoreEnv(String key, String value);
-
-  void reportNativeInitStatus(String statusCode, String errorMsg);
-
-  void setTimeoutNative(String callbackId, String time);
-
-  void setJSFrmVersion(String version);
-
-  void resetWXBridge(boolean remoteDebug);
-
-  void setInstanceRenderType(String instanceId, String renderType);
-
-  void removeInstanceRenderType(String instanceId);
-
-  void setPageArgument(String instanceId, String key, String value);
-
-  void setViewPortWidth(String instanceId,float viewPortWidth);
-
-  void reloadPageLayout(String instanceId);
-
-  void setDeviceDisplayOfPage(String instanceId, float width, float height);
-
-  void setPageDirty(String instanceId, boolean dirty);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/IWXDebugConfig.java b/android/sdk/src/main/java/com/taobao/weex/common/IWXDebugConfig.java
deleted file mode 100644
index 4833ef9..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/IWXDebugConfig.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.common;
-
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.bridge.WXDebugJsBridge;
-
-public interface IWXDebugConfig {
-
-  WXBridgeManager getWXJSManager();
-
-  WXDebugJsBridge getWXDebugJsBridge();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/IWXObject.java b/android/sdk/src/main/java/com/taobao/weex/common/IWXObject.java
deleted file mode 100644
index 6629040..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/IWXObject.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public interface IWXObject {
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/OnWXScrollListener.java b/android/sdk/src/main/java/com/taobao/weex/common/OnWXScrollListener.java
deleted file mode 100644
index af84d42..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/OnWXScrollListener.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import android.support.v7.widget.RecyclerView;
-import android.view.View;
-
-
-public interface OnWXScrollListener {
-
-  /**
-   * The  view is not currently scrolling.
-   */
-  int IDLE = RecyclerView.SCROLL_STATE_IDLE;
-  /**
-   * The view is currently being dragged by outside input such as user touch input.
-   */
-  int DRAGGING = RecyclerView.SCROLL_STATE_DRAGGING;
-  /**
-   * The view is currently animating to a final position while not under
-   * outside control.
-   */
-  int SETTLING = RecyclerView.SCROLL_STATE_SETTLING;
-
-  /**
-   * Callback method to be invoked when the view has been scrolled. This will be
-   * called after the scroll has completed.
-   * <p>
-   * This callback will also be called if visible item range changes after a layout
-   * calculation. In that case, dx and dy will be 0.
-   *
-   */
-  void onScrolled(View view, int x, int y);
-
-  /**
-   * Callback method to be invoked when view's scroll state changes.
-   *
-   */
-  void onScrollStateChanged(View view, int x, int y, int newState);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/RenderTypes.java b/android/sdk/src/main/java/com/taobao/weex/common/RenderTypes.java
deleted file mode 100644
index 0d7d83a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/RenderTypes.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.common;
-
-public class RenderTypes {
-
-    public static final String RENDER_TYPE_NATIVE = "platform";
-
-    public static final String RENDER_TYPE_HERON = "heron";
-    public static final String RENDER_TYPE_HERON_URL_PARAM = "wx_heron=true";
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/TypeModuleFactory.java b/android/sdk/src/main/java/com/taobao/weex/common/TypeModuleFactory.java
deleted file mode 100644
index 636e325..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/TypeModuleFactory.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.bridge.MethodInvoker;
-import com.taobao.weex.bridge.ModuleFactory;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.lang.annotation.Annotation;
-import java.lang.reflect.Method;
-import java.util.HashMap;
-import java.util.Map;
-import java.util.Set;
-
-/**
- * Use class
- * Created by sospartan on 6/17/16.
- */
-public class TypeModuleFactory<T extends WXModule> implements ModuleFactory<T> {
-  public static final String TAG = "TypeModuleFactory";
-  Class<T> mClazz;
-  Map<String, Invoker> mMethodMap;
-
-  public TypeModuleFactory(Class<T> clz) {
-    mClazz = clz;
-  }
-
-  private void generateMethodMap() {
-    if(WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d(TAG, "extractMethodNames:" + mClazz.getSimpleName());
-    }
-    HashMap<String, Invoker> methodMap = new HashMap<>();
-    try {
-      for (Method method : mClazz.getMethods()) {
-        // iterates all the annotations available in the method
-        for (Annotation anno : method.getDeclaredAnnotations()) {
-          if (anno != null) {
-            if(anno instanceof JSMethod) {
-              JSMethod methodAnnotation = (JSMethod) anno;
-              String name = JSMethod.NOT_SET.equals(methodAnnotation.alias())? method.getName():methodAnnotation.alias();
-              methodMap.put(name, new MethodInvoker(method, methodAnnotation.uiThread()));
-              break;
-            }else if(anno instanceof WXModuleAnno) {
-              WXModuleAnno methodAnnotation = (WXModuleAnno)anno;
-              methodMap.put(method.getName(), new MethodInvoker(method,methodAnnotation.runOnUIThread()));
-              break;
-            }
-          }
-        }
-      }
-    } catch (Throwable e) {
-      WXLogUtils.e("[WXModuleManager] extractMethodNames:", e);
-    }
-    mMethodMap = methodMap;
-  }
-
-
-  @Override
-  public T buildInstance() throws IllegalAccessException, InstantiationException {
-    return mClazz.newInstance();
-  }
-
-  @Override
-  public String[] getMethods() {
-    if (mMethodMap == null) {
-      generateMethodMap();
-    }
-    Set<String> keys = mMethodMap.keySet();
-    return keys.toArray(new String[keys.size()]);
-  }
-
-  @Override
-  public Invoker getMethodInvoker(String name) {
-    if (mMethodMap == null) {
-      generateMethodMap();
-    }
-    return mMethodMap.get(name);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXCompatModule.java b/android/sdk/src/main/java/com/taobao/weex/common/WXCompatModule.java
deleted file mode 100644
index 9b59d4a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXCompatModule.java
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import android.app.Activity;
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.support.v4.content.LocalBroadcastManager;
-
-import com.taobao.weex.WXEnvironment;
-
-/**
- * Created by lixinke on 16/10/10.
- */
-
-public abstract class WXCompatModule extends WXModule implements Destroyable {
-
-  private ModuleReceive mModuleReceive;
-
-  public WXCompatModule() {
-    mModuleReceive = new ModuleReceive(this);
-    LocalBroadcastManager.getInstance(WXEnvironment.getApplication())
-        .registerReceiver(mModuleReceive, new IntentFilter(WXModule.ACTION_ACTIVITY_RESULT));
-    LocalBroadcastManager.getInstance(WXEnvironment.getApplication())
-        .registerReceiver(mModuleReceive, new IntentFilter(WXModule.ACTION_REQUEST_PERMISSIONS_RESULT));
-  }
-
-  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
-  }
-
-  public void onActivityResult(int requestCode, int resultCode, Intent data) {
-  }
-
-  @Override
-  public void destroy() {
-    LocalBroadcastManager.getInstance(WXEnvironment.getApplication())
-        .unregisterReceiver(mModuleReceive);
-  }
-
-  static class ModuleReceive extends BroadcastReceiver {
-
-    private WXCompatModule mWXCompatModule;
-
-    ModuleReceive(WXCompatModule module) {
-      mWXCompatModule = module;
-    }
-
-    @Override
-    public void onReceive(Context context, Intent intent) {
-      String action = intent.getAction();
-      switch (action) {
-        case WXModule.ACTION_ACTIVITY_RESULT:
-          int requestCode = intent.getIntExtra(WXModule.REQUEST_CODE, -1);
-          int resultCode = intent.getIntExtra(WXModule.RESULT_CODE, Activity.RESULT_OK);
-          mWXCompatModule.onActivityResult(requestCode, resultCode, intent);
-          break;
-        case WXModule.ACTION_REQUEST_PERMISSIONS_RESULT:
-          requestCode = intent.getIntExtra(WXModule.REQUEST_CODE, -1);
-          String[] permissions = intent.getStringArrayExtra(WXModule.PERMISSIONS);
-          int[] grantResults = intent.getIntArrayExtra(WXModule.GRANT_RESULTS);
-          mWXCompatModule.onRequestPermissionsResult(requestCode, permissions, grantResults);
-          break;
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXConfig.java b/android/sdk/src/main/java/com/taobao/weex/common/WXConfig.java
deleted file mode 100644
index 5fc6ef7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXConfig.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public interface WXConfig {
-
-  String os = "os";
-  String osName = "osName";
-  String appVersion="appVersion";
-  String cacheDir = "cacheDir";
-  String devId="devId";
-  String sysVersion="sysVersion";
-  String sysModel="sysModel";
-  String weexVersion="weexVersion";
-  String appName="appName";
-  String appGroup="appGroup";
-  String externalUserAgent="externalUserAgent";
-  String logLevel="logLevel";
-  String scale = "scale";
-  String layoutDirection = "layoutDirection";
-  String debugMode = "debugMode";
-  String androidStatusBarHeight = "androidStatusBarHeight";
-  String deviceHeight = "deviceHeight";
-  String deviceWidth = "deviceWidth";
-
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXErrorCode.java b/android/sdk/src/main/java/com/taobao/weex/common/WXErrorCode.java
deleted file mode 100644
index 2434c12..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXErrorCode.java
+++ /dev/null
@@ -1,341 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.common;
-
-
-public enum WXErrorCode {
-
-
-  /*
-   * environment
-   **/
-  /**
-   * Failure for load so library
-   */
-  WX_ERR_LOAD_SO("-2001", "load so error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * Failure for load JSLib
-   */
-  WX_ERR_LOAD_JSLIB("-2002", "unzip JSLib error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * So library corrupted
-   */
-  WX_ERR_BAD_SO("-2003", "so size error, to reload apk so",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * Failure for extract and copy so from apk
-   */
-  WX_ERR_COPY_FROM_APK("-2007", "system load so error，copy from APK also error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * jsBridge
-   **/
-  /**
-   * Error for JavaScript function parameter
-   */
-  WX_ERR_JSFUNC_PARAM("-2009", "JS params error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * Error for parsing JSON object
-   */
-  WX_ERR_JSON_OBJECT("-2008", "transform JSON->OBJ  error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * Failure for invoking JavaScript function
-   */
-  WX_ERR_INVOKE_NATIVE("-2012", "Native-> Call ->JS  error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * Failure for executing JavaScript function.
-   */
-  WX_ERR_JS_EXECUTE("-2013", "JavaScript execute error!",ErrorType.JS_ERROR,ErrorGroup.JS),
-
-
-  /*
-   * domModule
-   **/
-  WX_SUCCESS("0", "successful",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for createBody
-   */
-  WX_ERR_DOM_CREATEBODY("-2100", "createBody error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for updateAttrs
-   */
-  WX_ERR_DOM_UPDATEATTRS("-2101", "updateAttrs error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for updateAttr
-   */
-  WX_ERR_DOM_UPDATESTYLE("-2102", "updateStyle error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for addElement
-   */
-  WX_ERR_DOM_ADDELEMENT("-2103", "addElement error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for removeElement
-   */
-  WX_ERR_DOM_REMOVEELEMENT("-2104", "removeElement error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for moveElement
-   */
-  WX_ERR_DOM_MOVEELEMENT("-2105", "moveElement error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for addEvent
-   */
-  WX_ERR_DOM_ADDEVENT("-2106", "addEvent error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for removeEvent
-   */
-  WX_ERR_DOM_REMOVEEVENT("-2107", "removeEvent error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for invoking createFinish
-   */
-  WX_ERROR_DOM_CREATEFINISH("-2108", "createFinish error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for invoking refreshFinish
-   */
-  WX_ERROR_DOM_REFRESHFINISH("-2109", "refreshFinish error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Failure for scrollToElement
-   */
-  WX_ERR_DOM_SCROLLTO("-2110", "scrollToElement",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   *
-   */
-  WX_ERR_RELOAD_PAGE("-2111", "reloadPage",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERR_RELOAD_PAGE_EXCEED_LIMIT("-2114", "RELOAD_PAGE_EXCEED_LIMIT",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERROR_WHITE_SCREEN("-2116", "WHITE_SCREEN",ErrorType.RENDER_ERROR,ErrorGroup.JS),
-  WHITE_SCREEN_RESPONSE_TIMEOUT("-2117", "WHITE_SCREEN_RESPONSE_TIMEOUT",ErrorType.RENDER_ERROR,ErrorGroup.JS),
-  WHITE_SCREEN_REBOOT_EXCEED_LIMIT("-2118", "WHITE_SCREEN_REBOOT_EXCEED_LIMIT",ErrorType.RENDER_ERROR,ErrorGroup.JS),
-
-  /**
-   *
-   */
-  WX_ERR_JSC_CRASH("-2112", "weexjscCrash",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   *dom actions invalid for native
-   */
-  WX_ERR_FIRST_DOM_ACTION_EXCEPTION("-2113", "dom action is invalid ",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * JS Bundle download error
-   */
-
-  WX_ERR_JSDOWNLOAD_START("-2201", "js bundle download start",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERR_JSBUNDLE_DOWNLOAD("-2299", "js bundle download err",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERR_JSBUNDLE_EMPTY("-2203", "js bundle empty",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERR_JSDOWNLOAD_END("-2299", "js bundle download end",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  // for js framework
-  WX_JS_FRAMEWORK_INIT_SUCCESS("-1000", "js framework success",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_JS_FRAMEWORK_REINIT_SUCCESS("-1001", "js framework reinit success",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * JS Framework run error
-   */
-  WX_ERR_JS_FRAMEWORK("-1002", "js framework error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERR_JS_REINIT_FRAMEWORK("-1003", "js reinit framework error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * Single progress init error
-   */
-  WX_ERR_SINGLE_PROCESS_DLOPEN_FILE_NOT_EXIST("-1004", "so file does not exist",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERR_SINGLE_PROCESS_DLOPEN_FLAIED("-1005", "dlopen so file failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERR_SINGLE_PROCESS_DLSYM_FAILED("-1006", "find function from so file failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_ERR_SINGLE_PROCESS_JS_FRAMEWORK("-1007", "js framework  init singleProcess failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_JS_FRAMEWORK_INIT_MULPROCESS_FAILED("-1008", "js framework init multiProcess failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_JS_FRAMEWORK_REINIT_MULPROCESS_FAILED("-1009", "js framework reinit multiProcess failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_JS_FRAMEWORK_INIT_FAILED("-1010", "js framework init failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_JS_FRAMEWORK_INIT_SINGLE_PROCESS_SUCCESS("-1011", "js framework init success in single process",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  WX_JS_FRAMEWORK_INIT_FAILED_PARAMS_NULL("-1012", "js framework init failed due to params null",ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-  WX_JS_FRAMEWORK_INIT_FAILED_FIND_ICU_TIMEOUT("-1013", "find icu failed",ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-
-  /**
-   * WX Key Exception Commit RT SDK Init
-   */
-  WX_KEY_EXCEPTION_SDK_INIT("-9000", "[WX_KEY_EXCEPTION_SDK_INIT]",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT("-9001", "[WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT] for android cpu is x86",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_SDK_INIT_TABLE_NOT_SUPPORT("-9002", "[WX_KEY_EXCEPTION_SDK_INIT_TABLE_NOT_SUPPORT] for device isTabletDevice",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_SDK_INIT_JSFM_INIT_FAILED("-9003", "[WX_KEY_EXCEPTION_SDK_INIT_JSFM_INIT_FAILED] for jsfm init failed|detail error is:",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * WX Key Exception Commit RT Register
-   */
-  WX_KEY_EXCEPTION_INVOKE_BRIDGE("-9100", "[WX_KEY_EXCEPTION_INVOKE_BRIDGE]",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_INVOKE_REGISTER_CONTENT_FAILED("-9101", "[WX_KEY_EXCEPTION_INVOKE_REGISTER_CONTENT_FAILED] details",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_INVOKE_JSSERVICE_EXECUTE("-9102", "[WX_KEY_EXCEPTION_INVOKE_JSSERVICE_EXECUTE] details",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_INVOKE_REGISTER_MODULES("-9103", "[WX_KEY_EXCEPTION_INVOKE_REGISTER_MODULES] details",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT("-9104", "[WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT] details",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-  /**
-   * WX Key Exception Commit Bundle Js Download
-   */
-  WX_KEY_EXCEPTION_JS_DOWNLOAD("-9200", "[WX_KEY_EXCEPTION_JS_DOWNLOAD]|",ErrorType.DOWN_LOAD_ERROR,ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_JS_DOWNLOAD_FAILED("-9201", "[WX_KEY_EXCEPTION_JS_DOWNLOAD_FAILED] | details",ErrorType.DOWN_LOAD_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * WX Key Exception Commit RT JsBridge eg. js excute runtime error
-   */
-  WX_KEY_EXCEPTION_WXBRIDGE("-9400", "[js excute runtime error] detail js stack -> ",ErrorType.JS_ERROR,ErrorGroup.JS),
-  WX_KEY_EXCEPTION_WXBRIDGE_EXCEPTION("-9401", "[js excute runtime error] detail js stack -> ",ErrorType.JS_ERROR,ErrorGroup.JS),
-
-  /**
-   * renderErrorCode
-   */
-  WX_RENDER_ERR_JS_CREATE_INSTANCE("-9600", "white screen cause create instance failed,check js stack ->",ErrorType.RENDER_ERROR,ErrorGroup.JS),
-  WX_RENDER_ERR_JS_CREATE_INSTANCE_CONTEXT("-9700", "white screen cause create instanceContext failed,check js stack ->",ErrorType.RENDER_ERROR,ErrorGroup.JS),
-  WX_RENDER_ERR_LAYER_OVERFLOW("-9602", "WX_RENDER_ERR_LAYER_OVERFLOW", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-  WX_RENDER_ERR_NULL_KEY("-9603", "WX_RENDER_ERR_NULL_KEY", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-  WX_RENDER_ERR_NATIVE_RUNTIME("-9604", "WX_RENDER_ERR for js error", ErrorType.RENDER_ERROR, ErrorGroup.NATIVE),
-  WX_RENDER_ERR_COMPONENT_NOT_REGISTER("-9605", "WX_RENDER_ERR_COMPONENT_NOT_REGISTER", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-  WX_RENDER_ERR_COMPONENT_ATTR_KEY("-9606", "The key passed to Component.updateAttr() is not string", ErrorType.NATIVE_ERROR, ErrorGroup.JS),
-  WX_RENDER_ERR_BRIDGE_ARG_NULL("-9610", "WX_RENDER_ERR_BRIDGE_ARG_NULL", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-  WX_RENDER_ERR_CONTAINER_TYPE("-9611", "WX_RENDER_ERR_CONTAINER_TYPE", ErrorType.JS_ERROR,ErrorGroup.JS),
-  WX_RENDER_ERR_TRANSITION("-9616", "WX_RENDER_ERR_TRANSITION", ErrorType.JS_ERROR, ErrorGroup.JS),
-  WX_RENDER_ERR_INSTANCE_ID_NULL("-9618", "WX_RENDER_ERR_INSTANCE_ID_NULL", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-  WX_RENDER_ERR_LIST_INVALID_COLUMN_COUNT("-9619", "WX_RENDER_ERR_LIST_INVALID_COLUMNJ_CONUNT", ErrorType.JS_ERROR, ErrorGroup.JS),
-  WX_RENDER_ERR_TEXTURE_SETBACKGROUND("-9620", "WX_RENDER_ERR_TEXTURE_SETBACKGROUND", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-  WX_RENDER_WAR_GPU_LIMIT_LAYOUT("-9621", "WX_RENDER_WAR_GPU_LIMIT_LAYOUT", ErrorType.JS_ERROR,ErrorGroup.JS),
-
-  WX_KEY_EXCEPTION_HERON("Heron_-9900", "Error of Heron engine: ", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
-  WX_KEY_EXCEPTION_HERON_RENDER("Heron_-9901", "Render error of Heron engine: ", ErrorType.RENDER_ERROR, ErrorGroup.NATIVE),
-
-  WX_KEY_EXCEPTION_NO_BUNDLE_TYPE("-9801", "Fatal Error : No bundle type in js bundle head, cause white screen or memory leak!!", ErrorType.JS_ERROR, ErrorGroup.JS),
-  /**
-   * degrade code.
-   */
-  WX_DEGRAD_ERR("-1000", "degradeToH5|Weex DegradPassivity ->",ErrorType.DEGRAD_ERROR,ErrorGroup.JS),
-
-  /**
-   * degrade for instance create failed, once this case occured,detail js stack and other specific
-   * cause need track into errmsg.
-   */
-  WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED("-1001", "degradeToH5|createInstance fail|wx_create_instance_error",ErrorType.DEGRAD_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * degrade for network failed download js bundle.once this case occured,network requist response header
-   * and statuscode need track into errmsg.
-   */
-  WX_DEGRAD_ERR_NETWORK_BUNDLE_DOWNLOAD_FAILED("-1002", "|wx_network_error|js bundle download failed",ErrorType.DOWN_LOAD_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * degrade for network failed for bundlejs is unbroken , once this case occured,network requist response header
-   * and statuscode need track into errmsg.
-   */
-  WX_DEGRAD_ERR_NETWORK_CHECK_CONTENT_LENGTH_FAILED("-1003", "degradeToH5|wx_network_error|js bundle content-length check failed",ErrorType.DEGRAD_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * degrade for Response header Content-Type is null or not "application/javascript".
-   * once this case occured,network requist response header and statuscode need track into errmsg.
-   */
-  WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR("-1004", "degradeToH5|wx_user_intercept_error |Content-Type is not application/javascript, " +
-          "Weex render template must be javascript, please check your request!",ErrorType.DEGRAD_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * degrade for other reason. such as white screen which block error for some unknown reason.
-   * once this case occured,detail msg need track.
-   */
-  WX_DEGRAD_ERR_OTHER_CAUSE_DEGRADTOH5("-1005", "degradeToH5|for other reason|",ErrorType.DEGRAD_ERROR,ErrorGroup.NATIVE),
-
-
-  WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED_JS("-1006", "degradeToH5|createInstance fail|wx_create_instance_error",ErrorType.DEGRAD_ERROR,ErrorGroup.JS),
-
-  WX_DEGRAD_EAGLE_RENDER_ERROR ("Eagle_-1007", "degradeToH5|eagleRenderErr", ErrorType.DEGRAD_ERROR, ErrorGroup.NATIVE),
-
-  WX_ERR_HASH_MAP_TMP("-10010", "WX_ERR_HASH_MAP_TMP",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
-
-  /**
-   * TEST
-   */
-
-  WX_ERR_TEST("test", "test",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE);
-
-  private String errorCode;
-  private String errorMsg;
-  private String appendMsg="";
-  private String args;
-  private ErrorType mErrorType;
-  private ErrorGroup mErrorGroup;
-
-  WXErrorCode(String errorCode, String errorMsg,ErrorType errorType,ErrorGroup errorGroup) {
-    this.errorCode = errorCode;
-    this.errorMsg = errorMsg;
-    this.mErrorType = errorType;
-    this.mErrorGroup = errorGroup;
-  }
-
-  public void appendErrMsg(String err) {
-    appendMsg=err;
-  }
-
-  public String getErrorCode() {
-    return this.errorCode;
-  }
-
-  public String getErrorMsg() {
-    StringBuilder builder=new StringBuilder(errorMsg);
-    builder.append(appendMsg);
-    return builder.toString();
-  }
-
-  public ErrorType getErrorType() {
-    return mErrorType;
-  }
-
-  public ErrorGroup getErrorGroup() {
-    return mErrorGroup;
-  }
-
-  public String getArgs() {
-    return args;
-  }
-
-  public void setArgs(String args) {
-    this.args = args;
-  }
-
-  public enum ErrorType{
-    JS_ERROR,
-    NATIVE_ERROR,
-    RENDER_ERROR,
-    DEGRAD_ERROR,
-    DOWN_LOAD_ERROR
-  }
-
-  public enum ErrorGroup{
-    JS,
-    NATIVE
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXException.java b/android/sdk/src/main/java/com/taobao/weex/common/WXException.java
deleted file mode 100644
index 28d8da1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXException.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public class WXException extends Exception {
-
-  private static final long serialVersionUID = 7265837506862157379L;
-
-  public WXException(String msg) {
-    super(msg);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXImageSharpen.java b/android/sdk/src/main/java/com/taobao/weex/common/WXImageSharpen.java
deleted file mode 100644
index 8a6b38e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXImageSharpen.java
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public enum WXImageSharpen {
-  UNSHARPEN,
-  SHARPEN
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXImageStrategy.java b/android/sdk/src/main/java/com/taobao/weex/common/WXImageStrategy.java
deleted file mode 100644
index 31524b2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXImageStrategy.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import android.widget.ImageView;
-
-import com.taobao.weex.WXSDKInstance;
-
-import java.util.Map;
-
-public class WXImageStrategy {
-
-
-  /**
-   * <strong>Never!</strong>
-   * <strong>Never!</strong>
-   * <strong>Never!</strong>
-   * Never use this flag, ImageView has done all the job of clipping!
-   * There is no method to read this flag any more.
-   * This field will be removed when it's appropriate.
-   */
-  @Deprecated
-  public boolean isClipping;
-
-  /**
-   * Whether to sharp the image. The default is false.
-   */
-  public boolean isSharpen;
-
-  /**
-   * The blur radius of the image. 0 means no blur.
-   * */
-  public int blurRadius;
-
-  public String placeHolder;
-
-  /**
-   * running weex instanceId
-   * @see WXSDKInstance#mInstanceId
-   */
-  public String instanceId;
-
-  public WXImageStrategy()
-  {
-
-  }
-
-  public WXImageStrategy(String instanceId)
-  {
-    this.instanceId = instanceId;
-  }
-
-
-  public ImageListener getImageListener() {
-    return imageListener;
-  }
-
-  public void setImageListener(ImageListener imageListener) {
-    this.imageListener = imageListener;
-  }
-
-  ImageListener imageListener;
-
-  public interface ImageListener{
-    public void onImageFinish(String url,ImageView imageView,boolean  result,Map extra);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXInstanceWrap.java b/android/sdk/src/main/java/com/taobao/weex/common/WXInstanceWrap.java
deleted file mode 100644
index 46c6274..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXInstanceWrap.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.JSMethod;
-
-/**
- * Report template error.
- */
-public class WXInstanceWrap extends WXModule {
-
-  @JSMethod
-  public void error(String type, String code, String info) {
-    if (mWXSDKInstance != null) {
-      WXSDKInstance root = mWXSDKInstance;
-      if(info != null && info.contains("downgrade_to_root")){
-        while (root.getParentInstance() != null){
-          root = root.getParentInstance();
-        }
-      }
-      root.onRenderError(type + "|" + code, info);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXJSBridgeMsgType.java b/android/sdk/src/main/java/com/taobao/weex/common/WXJSBridgeMsgType.java
deleted file mode 100644
index 3a66e26..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXJSBridgeMsgType.java
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public class WXJSBridgeMsgType {
-
-  public static final int SET_TIMEOUT = 0x01;
-  public static final int NATIVE_CALL = 0x02;
-  public static final int FIRE_EVENT = 0x03;
-  public static final int CALLBACK = 0x04;
-  public static final int CALL_JS = 0x05;
-  public static final int CALL_JS_BATCH = 0x06;
-  public static final int INIT_FRAMEWORK = 0x07;
-  public static final int REGISTER_COMPONENTS = 0x08;
-  public static final int REGISTER_MODULES = 0x09;
-  public static final int REFRESH_INSTANCE = 0x0a;
-  public static final int MODULE_TIMEOUT = 0x0b;
-  public static final int MODULE_INTERVAL = 0x0c;
-  public static final int TAKE_HEAP_SNAPSHOT = 0x0d;
-
-  public static final int RELOAD_PAGE_NATIVE = 0x0e;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXJSEngineListener.java b/android/sdk/src/main/java/com/taobao/weex/common/WXJSEngineListener.java
deleted file mode 100644
index 10d2aec..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXJSEngineListener.java
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public interface WXJSEngineListener {
-
-  void createInstanceSuccess(String instanceId);
-
-  void destroyInstanceSuccess(String instanceId);
-
-  void createInstanceFailed(String instanceId);
-
-  void destroyInstanceFailed(String instanceId);
-
-  void fireEvent(boolean success, String instanceId, String ref, String type);
-
-  void callback(boolean success, String instanceId, String funcId, String data);
-
-  void initFramework(boolean success, String version, double jslibSize);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXJSExceptionInfo.java b/android/sdk/src/main/java/com/taobao/weex/common/WXJSExceptionInfo.java
deleted file mode 100644
index 105d224..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXJSExceptionInfo.java
+++ /dev/null
@@ -1,142 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.common;
-
-
-import com.taobao.weex.WXEnvironment;
-
-import java.util.Map;
-
-public class WXJSExceptionInfo {
-
-  /**
-   * instance id
-   */
-  private String mInstanceId;
-  /**
-   * The URL where the exception occurred
-   */
-  private String mBundleUrl;
-  /**
-   * error code
-   */
-  private WXErrorCode mErrCode;
-  /**
-   * The function name of the exception
-   */
-  private String mFunction;
-  /**
-   * Exception details
-   */
-  private String mException;
-
-  /**
-   * Extended field
-   */
-  private Map<String,String> mExtParams;
-
-  /**
-   * weex sdk version
-   */
-  private String mWeexVersion = WXEnvironment.WXSDK_VERSION;
-
-  public long time;
-
-  /**
-   * js framework verison
-   */
-  private String mJsFrameworkVersion = WXEnvironment.JS_LIB_SDK_VERSION;
-
-  public WXJSExceptionInfo(String instanceId, String bundleUrl, WXErrorCode errCode, String function, String exception, Map<String,String> extParams) {
-    this.mInstanceId = instanceId;
-    this.mBundleUrl = bundleUrl;
-    this.mErrCode = errCode;
-    this.mFunction = function;
-    this.mException = exception;
-    this.mExtParams = extParams;
-    this.time = System.currentTimeMillis();
-  }
-
-  public String getInstanceId() {
-    return mInstanceId;
-  }
-
-  public void setInstanceId(String instanceId) {
-    mInstanceId = instanceId;
-  }
-
-  public String getBundleUrl() {
-    return mBundleUrl;
-  }
-
-  public void setBundleUrl(String bundleUrl) {
-    mBundleUrl = bundleUrl;
-  }
-
-  public WXErrorCode getErrCode() {
-    return mErrCode;
-  }
-
-  public void setErrCode(WXErrorCode errCode) {
-    mErrCode = errCode;
-  }
-
-  public String getFunction() {
-    return mFunction;
-  }
-
-  public void setFunction(String function) {
-    mFunction = function;
-  }
-
-  public String getException() {
-    return mException;
-  }
-
-  public void setException(String exception) {
-    mException = exception;
-  }
-
-  public Map<String, String> getExtParams() {
-    return mExtParams;
-  }
-
-  public void setExtParams(Map<String, String> extParams) {
-    mExtParams = extParams;
-  }
-
-  public String getWeexVersion() {
-    return mWeexVersion;
-  }
-
-
-  public String getJsFrameworkVersion() {
-    return mJsFrameworkVersion;
-  }
-
-
-  @Override
-  public String toString() {
-    return new StringBuilder()
-        .append(" errCode:").append(null == mErrCode?"unSetErrorCode":mErrCode.getErrorCode())
-        .append(",function:").append(null == mFunction?"unSetFuncName":mFunction)
-        .append(",exception:").append(null == mException?"unSetException":mException)
-        .toString();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXJSService.java b/android/sdk/src/main/java/com/taobao/weex/common/WXJSService.java
deleted file mode 100644
index 8cc4350..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXJSService.java
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import java.util.HashMap;
-import java.util.Map;
-
-public class WXJSService implements IWXObject {
-    private String name;
-    private String script;
-    private Map<String, Object> options = new HashMap<>();
-
-    public String getName() { return name; }
-    public void setName(String name) {
-        this.name = name;
-    }
-
-    public String getScript() { return script; }
-    public void setScript(String script) {
-        this.script = script;
-    }
-
-    public Map<String, Object> getOptions() { return options; }
-    public void setOptions(Map<String, Object> options) {
-        this.options = options;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXModule.java b/android/sdk/src/main/java/com/taobao/weex/common/WXModule.java
deleted file mode 100644
index 2c029aa..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXModule.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import android.content.Intent;
-import android.text.TextUtils;
-import android.view.Menu;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * All modules must extend this class
- */
-public abstract class WXModule implements IWXObject {
-
-  public static final String ACTION_ACTIVITY_RESULT = "actionActivityResult";
-  public static final String ACTION_REQUEST_PERMISSIONS_RESULT = "actionRequestPermissionsResult";
-  public static final String REQUEST_CODE = "requestCode";
-  public static final String RESULT_CODE = "resultCode";
-  public static final String PERMISSIONS = "permissions";
-  public static final String GRANT_RESULTS = "grantResults";
-
-
-  public WXSDKInstance mWXSDKInstance;
-  private String mModuleName;
-
-
-  protected final WXComponent findComponent(String ref){
-    if(mWXSDKInstance != null && ref != null){
-      return WXSDKManager.getInstance()
-          .getWXRenderManager()
-          .getWXComponent(mWXSDKInstance.getInstanceId(), ref);
-    }
-    return null;
-  }
-
-  /** hook the Activity life cycle to Instance module**/
-  public void onActivityResult(int requestCode, int resultCode, Intent data){}
-
-  public void onActivityCreate(){}
-
-  public void onActivityStart(){}
-
-  public void onActivityPause(){}
-
-  public void onActivityResume(){}
-
-  public void onActivityStop(){}
-
-  public void onActivityDestroy(){}
-
-  public boolean onActivityBack() {return false;}
-
-  public boolean onCreateOptionsMenu(Menu menu){return false;}
-
-  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {}
-
-    /** end **/
-
-  private Map<String, List<String>> mEvents = new HashMap<>();
-  private Map<String, Boolean> mKeepAlives = new HashMap<>();
-
-
-
-  @JSMethod
-  public void addEventListener(String eventName, String callback, Map<String, Object> options) {
-    if (TextUtils.isEmpty(eventName) || TextUtils.isEmpty(callback)) {
-      return;
-    }
-    boolean isOnce = false;
-    if (options != null && options.size() > 0 && options.containsKey("once")) {
-      Object temp = options.get("once");
-      if (WXUtils.getBoolean(temp,false)) {
-        isOnce = true;
-      }
-    }
-    mKeepAlives.put(callback, isOnce);
-    if(mEvents.get(eventName)==null){
-      mEvents.put(eventName,new ArrayList<String>());
-    }
-    mEvents.get(eventName).add(callback);
-  }
-
-  @JSMethod
-  public void removeAllEventListeners(String eventName) {
-    if (mEvents.containsKey(eventName)) {
-      List<String> callbacks = mEvents.remove(eventName);
-      for(String callback:callbacks){
-        mKeepAlives.remove(callback);
-      }
-    }
-  }
-
-  /**
-   * Check whether the EventName has been registered
-   */
-  public List<String> getEventCallbacks(String eventName) {
-    return mEvents.get(eventName);
-  }
-
-  public boolean isOnce(String callback){
-    return mKeepAlives.get(callback);
-  }
-
-  public String getModuleName() {
-    return mModuleName;
-  }
-
-  public void setModuleName(String moduleName) {
-    mModuleName = moduleName;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXModuleAnno.java b/android/sdk/src/main/java/com/taobao/weex/common/WXModuleAnno.java
deleted file mode 100644
index 7812453..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXModuleAnno.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import com.taobao.weex.annotation.JSMethod;
-
-import java.lang.annotation.Inherited;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-
-/** Use {@link JSMethod} instead. **/
-@Retention(RetentionPolicy.RUNTIME)
-@Inherited
-@Deprecated
-public @interface WXModuleAnno {
-
-  @Deprecated
-  boolean moduleMethod() default true;
-
-  boolean runOnUIThread() default true;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXPerformance.java b/android/sdk/src/main/java/com/taobao/weex/common/WXPerformance.java
deleted file mode 100644
index aeb1ffb..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXPerformance.java
+++ /dev/null
@@ -1,568 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.common;
-
-import android.support.annotation.RestrictTo;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-
-@Deprecated
-public class WXPerformance {
-
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  public enum Dimension {
-    JSLibVersion,
-    WXSDKVersion,
-    pageName,
-    spm,
-    scheme,
-    cacheType,
-    requestType,
-    networkType,
-    connectionType,
-    zcacheInfo,
-    wxContainerName,
-    wxInstanceType,
-    wxParentPage,
-    wxdim1,
-    wxdim2,
-    wxdim3,
-    wxdim4,
-    wxdim5,
-    bizType,
-    templateUrl,
-    useScroller
-  }
-
-  public enum Measure {
-    /**
-     * range : [min,max)
-     */
-    JSLibSize(0D, Double.MAX_VALUE),
-    //normal 300ms.. first install apk 30s ?
-    JSLibInitTime(0D, 80000D),
-    SDKInitTime(0D, 120000D),
-    SDKInitInvokeTime(0D, 5000D),
-    SDKInitExecuteTime(0D, 5000D),
-    JSTemplateSize(0D, 5000D),
-    pureNetworkTime(0D, 15000D),
-    networkTime(0D, 15000D),
-    fsCreateInstanceTime(0D, 3000D),
-    fsCallJsTotalTime(0D, 5000D),
-    fsCallJsTotalNum(0D, Double.MAX_VALUE),
-    fsCallNativeTotalTime(0D, 5000D),
-    fsCallNativeTotalNum(0D, Double.MAX_VALUE),
-    fsCallEventTotalNum(0D, Double.MAX_VALUE),
-    fsComponentCount(0D,100000D),
-    fsComponentCreateTime(0D,Double.MAX_VALUE),
-    fsRenderTime(0D, 5000D),
-    fsRequestNum(0D, 100D),
-    callCreateFinishTime(0D, 10000D),
-    cellExceedNum(0D, Double.MAX_VALUE),
-    communicateTotalTime(0D, 5000D),
-    maxDeepViewLayer(0D, Double.MAX_VALUE),
-    maxDeepVDomLayer(0D, Double.MAX_VALUE),
-    componentCount(0D, 1000000),
-    componentCreateTime(0D,Double.MAX_VALUE),
-    avgFps(0D, 61D),
-    timerCount(0D, Double.MAX_VALUE),
-
-    MaxImproveMemory(0D, Double.MAX_VALUE),
-    BackImproveMemory(0D, Double.MAX_VALUE),
-    PushImproveMemory(0D, Double.MAX_VALUE),
-    measureTime1(0D, Double.MAX_VALUE),
-    measureTime2(0D, Double.MAX_VALUE),
-    measureTime3(0D, Double.MAX_VALUE),
-    measureTime4(0D, Double.MAX_VALUE),
-    measureTime5(0D, Double.MAX_VALUE),
-
-    callBridgeTime(0D, Double.MAX_VALUE),
-    cssLayoutTime(0D, Double.MAX_VALUE),
-    parseJsonTime(0D, Double.MAX_VALUE),
-
-    communicateTime(0D, 5000D),
-    screenRenderTime(0D, 5000D),
-    totalTime(0D, 5000D),
-    localReadTime(0D, 5000D),
-    templateLoadTime(0D, 5000D),
-    packageSpendTime(0D, 5000D),
-    syncTaskTime(0D, 5000D),
-    actualNetworkTime(0D, 5000D),
-    firstScreenJSFExecuteTime(0D, 5000D),
-    //..
-
-    fluency(0D, 101D),
-    imgSizeCount(0D, 2000D),
-    interactionTime(0D,10000D),
-    interactionViewAddCount(0D, Double.MAX_VALUE),
-    interactionViewAddLimitCount(0D, Double.MAX_VALUE),
-    newFsRenderTime(0D, 10000D);
-
-    private double mMinRange, mMaxRange;
-
-    Measure(double min, double max) {
-      this.mMinRange = min;
-      this.mMaxRange = max;
-    }
-
-    public double getMinRange() {
-      return mMinRange;
-    }
-
-    public double getMaxRange() {
-      return mMaxRange;
-    }
-  }
-
-  public static final String DEFAULT = "default";
-
-  @RestrictTo(RestrictTo.Scope.LIBRARY_GROUP)
-  public static final String CACHE_TYPE = "cacheType";
-
-  public static final int VIEW_LIMIT_HEIGHT = WXViewUtils.getScreenHeight() /3*2;
-  public static final int VIEW_LIMIT_WIDTH = WXViewUtils.getScreenWidth() /3*2;
-  public static boolean TRACE_DATA = WXEnvironment.isApkDebugable();
-
-  /**
-   * No longer needed.
-   */
-  @Deprecated
-  public String bizType = "weex";
-
-  /**
-   * Use {@link #pageName} instead.
-   */
-  @Deprecated
-  public String templateUrl;
-
-  @RestrictTo(RestrictTo.Scope.LIBRARY_GROUP)
-  public String cacheType = "none";
-
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  public long renderTimeOrigin;
-
-  public long renderUnixTimeOrigin;
-
-  public long fsRenderTime;
-
-  public long callCreateFinishTime;
-
-  public long interactionTime;
-
-  public long interactionRealUnixTime;
-
-  public int interactionViewAddCount;
-
-  public int interactionViewAddLimitCount;
-
-  public long newFsRenderTime;
-
-  public int localInteractionViewAddCount;
-
-  /**
-   * Time used for
-   * {@link com.taobao.weex.bridge.WXBridgeManager#createInstance(String, String, Map, String)}
-   */
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  public long callCreateInstanceTime;
-
-
-  public long fsCallJsTotalTime;
-
-  public int fsCallJsTotalNum;
-
-  public long fsCallNativeTotalTime;
-
-  public int fsCallNativeTotalNum;
-
-  public int fsRequestNum;
-
-  public int fsComponentCount;
-
-  public int fsComponentCreateTime;
-
-  public int cellExceedNum;
-
-  public int timerInvokeCount;
-
-  public int fsCallEventTotalNum;
-
-  public long avgFPS;
-  public double fluency = 100D;
-
-  public long backImproveMemory;
-
-
-  /**
-   * Time spent for reading, time unit is ms.
-   */
-  public double localReadTime;
-
-  /**
-   * Name of the page
-   */
-  public String pageName = DEFAULT;
-
-  /**
-   * Size of JavaScript framework, the unit is KB
-   */
-  public double JSLibSize;
-
-  /**
-   * Time of initial JavaScript library
-   */
-  public long JSLibInitTime;
-
-  /**
-   * Size of JavaScript template
-   */
-  public double JSTemplateSize;
-
-  public long templateLoadTime;
-
-  /**
-   * Use {@link #callCreateInstanceTime} instead.
-   */
-  @Deprecated
-  public long communicateTime;
-
-  /**
-   * Time spent when rendering first screen
-   */
-  public long screenRenderTime;
-
-  /**
-   * Call native Time spent when rendering first screen
-   */
-  public long callBridgeTime;
-
-  /**
-   * Create Instance Time spent when rendering first screen
-   */
-  public long firstScreenJSFExecuteTime;
-
-  /**
-   * Call native Time spent when rendering first screen
-   */
-  public long parseJsonTime;
-
-  /**
-   * CssLayout Time spent when rendering first screen
-   */
-  public long cssLayoutTime;
-
-  /**
-   * Time spent, the unit is micro second
-   */
-  public double totalTime;
-
-  /**
-   * load bundle js time, unite ms
-   */
-  public long networkTime;
-
-  /**
-   * pure network time;
-   */
-  public long pureNetworkTime;
-
-  public long actualNetworkTime;
-  public long packageSpendTime;
-  public long syncTaskTime;
-  /**
-   * view hierarchy
-   */
-  public int maxDeepViewLayer;
-
-  public int maxDeepVDomLayer;
-
-  public double wrongImgSizeCount;
-
-  /**
-   * 1:true
-   * 0:false
-   */
-  public int useScroller = 0;
-
-  /**
-   * component Count
-   */
-  public long componentCount;
-
-  public long componentCreateTime;
-  /**
-   * Version of JavaScript libraray
-   */
-  public String JSLibVersion = WXEnvironment.JS_LIB_SDK_VERSION;
-
-  /**
-   * Version of Weex SDK
-   */
-  public String WXSDKVersion = WXEnvironment.WXSDK_VERSION;
-
-  /**
-   * The detail message of render failure
-   */
-  public String renderFailedDetail;
-
-  /**
-   * Error code
-   */
-  public String errCode;
-
-  /**
-   * Error message
-   */
-  @Deprecated
-  public String errMsg;
-  private StringBuilder mErrMsgBuilder;
-
-  public String args="";
-
-  public String connectionType;
-  public String requestType="other";
-
-  public String zCacheInfo;
-
-  /**
-   *for network tracker
-   */
-
-  /**
-   * TODO These dimensions will be moved to elsewhere
-   */
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  @Deprecated
-  public String wxDims[] = new String[5];
-
-  /**
-   * TODO These dimensions will be moved to elsewhere
-   */
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  @Deprecated
-  public long measureTimes[] = new long[5];
-
-
-  /**
-   * RenderAction
-   */
-  public int mActionAddElementCount = 0;
-  public int mActionAddElementSumTime = 0;
-
-  private String mInstanceId;
-
-  public WXPerformance(String instanceId){
-    mErrMsgBuilder=new StringBuilder();
-    mInstanceId = instanceId;
-  }
-
-  public Map<String, Double> getMeasureMap() {
-    double fsRenderTime;
-    if (this.fsRenderTime != 0) {
-      fsRenderTime = this.fsRenderTime - renderTimeOrigin;
-    } else {
-      if (totalTime != 0) {
-        fsRenderTime = totalTime;
-      } else {
-        fsRenderTime = -1;
-      }
-    }
-    Map<String, Double> quotas = new HashMap<>();
-    quotas.put(Measure.JSLibSize.toString(), JSLibSize);
-    quotas.put(Measure.JSLibInitTime.toString(), (double) JSLibInitTime);
-    quotas.put(Measure.SDKInitTime.toString(), (double) WXEnvironment.sSDKInitTime);
-    quotas.put(Measure.SDKInitInvokeTime.toString(), (double) WXEnvironment.sSDKInitInvokeTime);
-    quotas.put(Measure.SDKInitExecuteTime.toString(), (double) WXEnvironment.sSDKInitExecuteTime);
-    quotas.put(Measure.JSTemplateSize.toString(), JSTemplateSize);
-    quotas.put(Measure.pureNetworkTime.toString(), (double) pureNetworkTime);
-    quotas.put(Measure.networkTime.toString(), (double) networkTime);
-    quotas.put(Measure.fsCreateInstanceTime.toString(), (double) callCreateInstanceTime);
-    quotas.put(Measure.fsCallJsTotalTime.toString(), (double) fsCallJsTotalTime);
-    quotas.put(Measure.fsCallJsTotalNum.toString(), (double) fsCallJsTotalNum);
-    quotas.put(Measure.fsCallNativeTotalTime.toString(), (double) fsCallNativeTotalTime);
-    quotas.put(Measure.fsCallNativeTotalNum.toString(), (double) fsCallNativeTotalNum);
-    quotas.put(Measure.fsComponentCount.toString(),(double)fsComponentCount);
-    quotas.put(Measure.fsComponentCreateTime.toString(),(double)fsComponentCreateTime);
-    quotas.put(Measure.fsRenderTime.toString(), fsRenderTime);
-    quotas.put(Measure.fsRequestNum.toString(), (double) fsRequestNum);
-    quotas.put(Measure.communicateTotalTime.toString(), totalTime);
-    quotas.put(Measure.maxDeepViewLayer.toString(), (double) maxDeepViewLayer);
-    quotas.put(Measure.maxDeepVDomLayer.toString(), (double) maxDeepVDomLayer);
-    quotas.put(Measure.componentCount.toString(), (double) componentCount);
-    quotas.put(Measure.componentCreateTime.toString(),(double)componentCreateTime);
-    quotas.put(Measure.cellExceedNum.toString(), (double) cellExceedNum);
-    quotas.put(Measure.timerCount.toString(), (double) timerInvokeCount);
-    quotas.put(Measure.avgFps.toString(), (double) avgFPS);
-    quotas.put(Measure.fluency.toString(), fluency);
-    quotas.put(Measure.MaxImproveMemory.toString(), 0D);
-    quotas.put(Measure.BackImproveMemory.toString(), (double) backImproveMemory);
-    quotas.put(Measure.PushImproveMemory.toString(), 0D);
-
-    quotas.put(Measure.fsCallEventTotalNum.toString(), (double) fsCallEventTotalNum);
-    quotas.put(Measure.callCreateFinishTime.toString(), (double) callCreateFinishTime);
-    quotas.put(Measure.imgSizeCount.toString(), wrongImgSizeCount);
-    quotas.put(Measure.interactionTime.toString(), (double) interactionTime);
-    quotas.put(Measure.interactionViewAddCount.toString(), (double) interactionViewAddCount);
-    quotas.put(Measure.interactionViewAddLimitCount.toString(), (double) interactionViewAddLimitCount);
-    quotas.put(Measure.newFsRenderTime.toString(), (double) newFsRenderTime);
-
-    quotas.put(Measure.callBridgeTime.toString(), (double) callBridgeTime);
-    quotas.put(Measure.cssLayoutTime.toString(), (double) cssLayoutTime);
-    quotas.put(Measure.parseJsonTime.toString(), (double) parseJsonTime);
-
-    // TODO the following attribute is no longer needed and will be deleted soon.
-    quotas.put(Measure.screenRenderTime.toString(), (double) screenRenderTime);
-    quotas.put(Measure.communicateTime.toString(), (double) communicateTime);
-    quotas.put(Measure.localReadTime.toString(), localReadTime);
-    quotas.put(Measure.templateLoadTime.toString(), (double) templateLoadTime);
-    quotas.put(Measure.firstScreenJSFExecuteTime.toString(), (double) firstScreenJSFExecuteTime);
-    quotas.put(Measure.actualNetworkTime.toString(), (double) actualNetworkTime);
-    quotas.put(Measure.syncTaskTime.toString(), (double) syncTaskTime);
-    quotas.put(Measure.packageSpendTime.toString(), (double) packageSpendTime);
-
-    // TODO These attribute will be moved to elsewhere
-    quotas.put(Measure.measureTime1.toString(), (double) measureTimes[0]);
-    quotas.put(Measure.measureTime2.toString(), (double) measureTimes[1]);
-    quotas.put(Measure.measureTime3.toString(), (double) measureTimes[2]);
-    quotas.put(Measure.measureTime4.toString(), (double) measureTimes[3]);
-    quotas.put(Measure.measureTime5.toString(), (double) measureTimes[4]);
-    return quotas;
-  }
-
-  public Map<String, String> getDimensionMap() {
-    Map<String, String> quotas = new HashMap<>();
-    quotas.put(Dimension.JSLibVersion.toString(), JSLibVersion);
-    quotas.put(Dimension.WXSDKVersion.toString(), WXSDKVersion);
-    quotas.put(Dimension.pageName.toString(), pageName);
-    quotas.put(Dimension.requestType.toString(), requestType);
-    quotas.put(Dimension.networkType.toString(), "unknown");
-    quotas.put(Dimension.connectionType.toString(), connectionType);
-    quotas.put(Dimension.zcacheInfo.toString(), zCacheInfo);
-    quotas.put(Dimension.cacheType.toString(), cacheType);
-    quotas.put(Dimension.useScroller.toString(), String.valueOf(useScroller));
-
-    WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
-    String keyActivity = WXInstanceApm.KEY_PAGE_PROPERTIES_CONTAINER_NAME;
-    quotas.put(keyActivity, null == sdkInstance? "unKnow" : sdkInstance.getContainerInfo().get(keyActivity));
-    String keyType = WXInstanceApm.KEY_PAGE_PROPERTIES_INSTANCE_TYPE;
-    quotas.put(keyType,sdkInstance == null ?"unKnow": sdkInstance.getContainerInfo().get(keyType));
-    String keyParentPae = WXInstanceApm.KEY_PAGE_PROPERTIES_PARENT_PAGE;
-    quotas.put(keyParentPae,null == sdkInstance ?"unKnow":sdkInstance.getContainerInfo().get(keyParentPae));
-
-    // TODO These attribute will be moved to elsewhere
-    // Extra Dimension for 3rd developers.
-    quotas.put(Dimension.wxdim1.toString(), wxDims[0]);
-    quotas.put(Dimension.wxdim2.toString(), wxDims[1]);
-    quotas.put(Dimension.wxdim3.toString(), wxDims[2]);
-    quotas.put(Dimension.wxdim4.toString(), wxDims[3]);
-    quotas.put(Dimension.wxdim5.toString(), wxDims[4]);
-
-    // TODO the following attribute is no longer needed and will be deleted soon.
-    quotas.put(Dimension.bizType.toString(), bizType);
-    quotas.put(Dimension.templateUrl.toString(), templateUrl);
-    return quotas;
-  }
-
-  public static String[] getDimensions() {
-    List<String> ret = new LinkedList<>();
-    for (Dimension dimension : Dimension.values()) {
-      ret.add(dimension.toString());
-    }
-    return ret.toArray(new String[ret.size()]);
-  }
-
-  public static String[] getMeasures() {
-    List<String> ret = new LinkedList<>();
-    for (Measure measure : Measure.values()) {
-      ret.add(measure.toString());
-    }
-    return ret.toArray(new String[ret.size()]);
-  }
-
-  @Override
-  public String toString() {
-    if (WXEnvironment.isApkDebugable()) {
-      return "bizType:" + bizType + ",pageName:" + pageName + ",templateLoadTime" + templateLoadTime
-              + ",localReadTime:" + localReadTime + ",JSLibInitTime:" + JSLibInitTime
-              + ",JSLibSize:" + JSLibSize + ",templateUrl" + templateUrl
-              + ",JSTemplateSize:" + JSTemplateSize + ",communicateTime:" + communicateTime
-              + ",screenRenderTime:" + screenRenderTime
-              + ",firstScreenJSFExecuteTime:" + firstScreenJSFExecuteTime
-              + ",componentCount:" + componentCount
-              + ",syncTaskTime:" + syncTaskTime
-              + ",pureNetworkTime:" + pureNetworkTime
-              + ",networkTime:" + networkTime
-              + ",actualNetworkTime:" + actualNetworkTime
-              + ",packageSpendTime:" + packageSpendTime
-              + ",connectionType:" + connectionType
-              + ",requestType:" + requestType
-              + ",initInvokeTime:" + WXEnvironment.sSDKInitInvokeTime + ",initExecuteTime:" + WXEnvironment.sSDKInitExecuteTime
-              + ",SDKInitTime:" + WXEnvironment.sSDKInitTime
-              + ",totalTime:" + totalTime + ",JSLibVersion:" + JSLibVersion + ",WXSDKVersion:" + WXSDKVersion
-              + ",errCode:" + errCode + ",renderFailedDetail:" + renderFailedDetail
-              + ",arg:" + args
-              + ",errMsg:" + getErrMsg();
-    }
-    return super.toString();
-  }
-
-  public String getPerfData() {
-    return "networkTime:" + networkTime
-            + " actualNetworkTime:" + actualNetworkTime
-            + " connectionType:" + connectionType
-            + " requestType:" + requestType
-            + " firstScreenRenderTime:" + screenRenderTime
-            + " firstScreenJSFExecuteTime:" + firstScreenJSFExecuteTime
-            + " componentCount:" + componentCount
-            + " JSTemplateSize:" + JSTemplateSize
-            + " SDKInitTime:" + WXEnvironment.sSDKInitTime
-            + " totalTime:" + totalTime
-            + " JSLibVersion:" + JSLibVersion
-            + " WXSDKVersion:" + WXSDKVersion
-            + " pageName:" + pageName
-            + " useScroller:" + useScroller;
-
-  }
-
-  public String getErrMsg() {
-    return mErrMsgBuilder.toString();
-  }
-
-  public void appendErrMsg(CharSequence msg) {
-    mErrMsgBuilder.append(msg);
-  }
-
-  public void beforeInstanceRender(String instanceId) {
-    renderTimeOrigin = System.currentTimeMillis();
-    renderUnixTimeOrigin = WXUtils.getFixUnixTime();
-  }
-
-  public void afterInstanceDestroy(String instanceId) {
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXRefreshData.java b/android/sdk/src/main/java/com/taobao/weex/common/WXRefreshData.java
deleted file mode 100644
index bc01224..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXRefreshData.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public class WXRefreshData {
-
-  public String data;
-
-  public boolean isDirty;
-
-  public WXRefreshData(String data, boolean isDirty) {
-    this.data = data;
-    this.isDirty = isDirty;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXRenderStrategy.java b/android/sdk/src/main/java/com/taobao/weex/common/WXRenderStrategy.java
deleted file mode 100644
index 52ce118..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXRenderStrategy.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public enum WXRenderStrategy {
-  APPEND_ASYNC("APPEND_ASYNC"),
-  APPEND_ONCE("APPEND_ONCE"),
-  DATA_RENDER("DATA_RENDER"),
-  DATA_RENDER_BINARY("DATA_RENDER_BINARY"),
-  JSON_RENDER("JSON_RENDER");
-
-
-  private String flag;
-
-  WXRenderStrategy(String flag) {
-    this.flag = flag;
-  }
-
-  public String getFlag() {
-    return flag;
-  }
-}
-
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXRequest.java b/android/sdk/src/main/java/com/taobao/weex/common/WXRequest.java
deleted file mode 100644
index e266a96..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXRequest.java
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import com.taobao.weex.WXSDKInstance;
-
-import java.util.Map;
-
-public class WXRequest {
-
-  /**
-   * The request parameter
-   */
-  public Map<String, String> paramMap;
-
-  /**
-   * The request URL
-   */
-  public String url;
-  /**
-   * The request method
-   */
-  public String method;
-  /**
-   * The request body
-   */
-  public String body;
-
-  /**
-   * The request time out
-   */
-  public int timeoutMs = WXRequest.DEFAULT_TIMEOUT_MS;
-
-  /**
-   * The default timeout
-   */
-  public static final int DEFAULT_TIMEOUT_MS = 3000;
-
-  /**
-   * running weex instanceId
-   * @see WXSDKInstance#mInstanceId
-   */
-  public String instanceId;;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXRequestListener.java b/android/sdk/src/main/java/com/taobao/weex/common/WXRequestListener.java
deleted file mode 100644
index a9631dd..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXRequestListener.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-
-public interface WXRequestListener {
-
-  void onSuccess(int requestType, Object context, WXResponse response);
-
-  void onError(int requestType, Object context, WXResponse response);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXResponse.java b/android/sdk/src/main/java/com/taobao/weex/common/WXResponse.java
deleted file mode 100644
index f72eedb..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXResponse.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import java.util.Map;
-
-public class WXResponse {
-
-  /**
-   * Status code
-   */
-  public String statusCode;
-
-  /**
-   * Byte stream fetched from the connection
-   */
-  public String data;
-
-  public byte[] originalData;
-
-  /**
-   * Server internal error
-   */
-  public String errorCode;
-
-  /**
-   * Server error message
-   */
-  public String errorMsg;
-
-  /**
-   * Message for toast
-   */
-  public String toastMsg;
-
-  /**
-   * Parameter for further extension.
-   */
-  public Map<String, Object> extendParams;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXRuntimeException.java b/android/sdk/src/main/java/com/taobao/weex/common/WXRuntimeException.java
deleted file mode 100644
index 7063bdf..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXRuntimeException.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-public class WXRuntimeException extends RuntimeException {
-
-  private static final long serialVersionUID = 5732315311747521491L;
-
-  public WXRuntimeException(String e) {
-    super(e);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXThread.java b/android/sdk/src/main/java/com/taobao/weex/common/WXThread.java
deleted file mode 100644
index f8afc56..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXThread.java
+++ /dev/null
@@ -1,202 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import android.os.Handler;
-import android.os.Handler.Callback;
-import android.os.HandlerThread;
-import android.os.Message;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.tools.LogDetail;
-
-import java.lang.ref.WeakReference;
-
-import static com.taobao.weex.utils.tools.TimeCalculator.PLATFORM_ANDROID;
-
-/**
- * Thread used in weex
- */
-public class WXThread extends HandlerThread {
-
-  private Handler mHandler;
-
-  static class SafeRunnable implements Runnable {
-
-    static final String TAG = "SafeRunnable";
-    private LogDetail mTimelineLog = null;
-    private WeakReference<WXSDKInstance> mInstance;
-    final Runnable mTask;
-    SafeRunnable(Runnable task){
-      this(task,null);
-    }
-
-    SafeRunnable(Runnable task, String taskName){
-      this(task,null, taskName);
-    }
-
-    SafeRunnable(Runnable runnable, WXSDKInstance instance, String taskName) {
-      mTask = runnable;
-      if(taskName != null) {
-        mTimelineLog = new LogDetail();
-        mTimelineLog.info.platform = PLATFORM_ANDROID;
-        mTimelineLog.name(taskName);
-        mInstance = new WeakReference<>(instance);
-      }
-    }
-
-    @Override
-    public void run() {
-      try {
-        if(mTask != null) {
-          if (mTimelineLog != null)
-            mTimelineLog.taskStart();
-          mTask.run();
-          if (mTimelineLog != null)
-            mTimelineLog.taskEnd();
-        }
-      }catch (Throwable e){
-        //catch everything may throw from exection.
-        if(WXEnvironment.isApkDebugable()){
-          WXLogUtils.e(TAG,"SafeRunnable run throw expection:"+e.getMessage());
-          throw e;
-        }
-        WXLogUtils.w(TAG, e);
-      }
-
-      if (mTimelineLog != null) {
-        if(mInstance != null) {
-          WXSDKInstance wxsdkInstance = mInstance.get();
-          if(wxsdkInstance != null) {
-            wxsdkInstance.mTimeCalculator.addLog(mTimelineLog);
-          }
-        }
-      }
-
-    }
-  }
-
-  static class SafeCallback implements Callback {
-    static final String TAG = "SafeCallback";
-
-    final Callback mCallback;
-    SafeCallback(Callback cb){
-      mCallback = cb;
-    }
-
-    @Override
-    public boolean handleMessage(Message msg) {
-      boolean result = false;
-      try{
-        if(mCallback != null){
-          result = mCallback.handleMessage(msg);
-        }
-      }catch (Throwable e){
-        //catch everything may throw from exection.
-        if(WXEnvironment.isApkDebugable()){
-          WXLogUtils.e(TAG,"SafeCallback handleMessage throw expection:"+e.getMessage());
-          throw e;
-        }
-      }
-      return result;
-    }
-  }
-
-  /**
-   * Secure Runnable to prevent throw during execution.
-   * NOTE: DO NOT use this method to wrap runnable that may be removed by {@link Handler#removeCallbacks(Runnable)}
-   * @param runnable
-   * @return
-   */
-  public static Runnable secure(Runnable runnable){
-    return secure(runnable, null, null);
-  }
-
-
-  public static Runnable secure(Runnable runnable, WXSDKInstance instance, String runnableName){
-    if(runnable == null || runnable instanceof SafeRunnable){
-      return runnable;
-    }
-    return new SafeRunnable(runnable,instance, runnableName);
-  }
-
-  public static Callback secure(Callback callback){
-    if(callback == null || callback instanceof SafeCallback){
-      return callback;
-    }
-
-    return new SafeCallback(callback);
-  }
-
-  /**
-   * @param name name of thread
-   */
-  public WXThread(String name) {
-    super(name);
-    start();
-    mHandler = new Handler(getLooper());
-  }
-
-
-  public WXThread(String name, Callback callback) {
-    super(name);
-    start();
-    mHandler = new Handler(getLooper(), secure(callback));
-  }
-
-  /**
-   * @param name name of thread
-   * @param priority The priority to run the thread at. The value supplied must be from
-   *                 {@link android.os.Process} and not from java.lang.Thread.
-   */
-  public WXThread(String name, int priority, Callback callback) {
-    super(name, priority);
-    start();
-    mHandler = new Handler(getLooper(), secure(callback));
-  }
-
-  /**
-   * @param name name of thread
-   * @param priority The priority to run the thread at. The value supplied must be from
-   *                 {@link android.os.Process} and not from java.lang.Thread.
-   */
-  public WXThread(String name, int priority) {
-    super(name, priority);
-    start();
-    mHandler = new Handler(getLooper());
-  }
-
-  public Handler getHandler() {
-    return mHandler;
-  }
-
-  public boolean isWXThreadAlive() {
-    return (mHandler != null && getLooper() != null && isAlive());
-  }
-
-  @Override
-  public boolean quit() {
-    if (mHandler != null) {
-      mHandler.removeCallbacksAndMessages(null);
-    }
-    return super.quit();
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/common/WXWorkThreadManager.java b/android/sdk/src/main/java/com/taobao/weex/common/WXWorkThreadManager.java
deleted file mode 100644
index ed4df79..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/common/WXWorkThreadManager.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-
-/**
- * Class for managing work thread.
- *
- * <p>
- *  This class is for internal purpose,
- *  please don't use it directly unless you know what you are doing.
- * </p>
- */
-@RestrictTo(Scope.LIBRARY_GROUP)
-public class WXWorkThreadManager {
-
-  private ExecutorService singleThreadExecutor;
-
-  public WXWorkThreadManager() {
-    singleThreadExecutor = Executors.newSingleThreadExecutor();
-  }
-
-  public void post(Runnable task) {
-    if (singleThreadExecutor != null)
-      singleThreadExecutor.execute(task);
-  }
-
-  /**
-   * Destroy current instance
-   */
-  public void destroy() {
-    if (singleThreadExecutor != null)
-      singleThreadExecutor.shutdown();
-    singleThreadExecutor = null;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/CSSConstants.java b/android/sdk/src/main/java/com/taobao/weex/dom/CSSConstants.java
deleted file mode 100755
index 221d046..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/CSSConstants.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.dom;
-
-public class CSSConstants {
-
-  public static final float UNDEFINED = Float.NaN;
-
-  public static boolean isUndefined(float value) {
-    return Float.compare(value, UNDEFINED) == 0;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/CSSShorthand.java b/android/sdk/src/main/java/com/taobao/weex/dom/CSSShorthand.java
deleted file mode 100644
index 3037d99..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/CSSShorthand.java
+++ /dev/null
@@ -1,120 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.dom;
-
-import android.support.annotation.NonNull;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.text.TextUtils;
-import com.taobao.weex.dom.CSSShorthand.CSSProperty;
-import java.util.Arrays;
-
-public class CSSShorthand<T extends Enum<? extends CSSProperty>> implements Cloneable {
-
-  interface CSSProperty{
-  }
-
-  public static enum EDGE implements CSSProperty{
-    TOP, BOTTOM, LEFT, RIGHT, ALL;
-  }
-
-  public static enum CORNER implements CSSProperty{
-    BORDER_TOP_LEFT, BORDER_TOP_RIGHT,
-    BORDER_BOTTOM_RIGHT, BORDER_BOTTOM_LEFT, ALL;
-  }
-
-  public static enum TYPE {
-    MARGIN, PADDING, BORDER;
-  }
-
-  private float[] values;
-
-  public CSSShorthand(float []values){
-    replace(values);
-  }
-
-  public CSSShorthand() {
-    this(false);
-  }
-
-  CSSShorthand(boolean fillWithNaN) {
-    values = new float[Math.max(EDGE.values().length,CORNER.values().length)];
-    if (fillWithNaN) {
-      Arrays.fill(values, Float.NaN);
-    }
-  }
-
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  public void set(@NonNull EDGE edge, float value){
-    setInternal(edge, value);
-  }
-
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  public void set(@NonNull CORNER edge, float value) {
-    setInternal(edge, value);
-  }
-
-  /**
-   * {@link EDGE#ALL} is not supported, 0 will be returned.
-   * @throws IndexOutOfBoundsException
-   * @param edge
-   * @return
-   */
-  public float get(@NonNull EDGE edge){
-    return getInternal(edge);
-  }
-
-  /**
-   * {@link CORNER#ALL} is not supported, 0 will be returned.
-   * @throws IndexOutOfBoundsException
-   * @param edge
-   * @return
-   */
-  public float get(@NonNull CORNER edge) {
-    return getInternal(edge);
-  }
-
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  public final void replace(float []values){
-    this.values = values;
-  }
-
-  @Override
-  public CSSShorthand clone() throws CloneNotSupportedException {
-    return (CSSShorthand) super.clone();
-  }
-
-  private void setInternal(@NonNull Enum<? extends CSSProperty> edge, float value){
-    if (edge == EDGE.ALL || edge == CORNER.ALL) {
-      Arrays.fill(values, value);
-    } else {
-      values[edge.ordinal()] = value;
-    }
-  }
-
-  private float getInternal(@NonNull Enum<? extends CSSProperty> edge){
-    return (edge == EDGE.ALL || edge == CORNER.ALL) ? 0 : values[edge.ordinal()];
-  }
-
-  @Override
-  @RestrictTo(Scope.LIBRARY)
-  public String toString() {
-    return TextUtils.isEmpty(values.toString()) ? "" : Arrays.toString(values);
-  }
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/RenderContext.java b/android/sdk/src/main/java/com/taobao/weex/dom/RenderContext.java
deleted file mode 100644
index 635039f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/RenderContext.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by sospartan on 23/02/2017.
- */
-
-public interface RenderContext {
-  WXSDKInstance getInstance();
-  WXComponent getComponent(String ref);
-  WXComponent unregisterComponent(String ref);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/TextDecorationSpan.java b/android/sdk/src/main/java/com/taobao/weex/dom/TextDecorationSpan.java
deleted file mode 100644
index c7d2579..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/TextDecorationSpan.java
+++ /dev/null
@@ -1,55 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.dom;
-
-
-import android.support.annotation.NonNull;
-import android.text.TextPaint;
-import android.text.style.CharacterStyle;
-import android.text.style.UpdateAppearance;
-
-import com.taobao.weex.ui.component.WXTextDecoration;
-
-public class TextDecorationSpan extends CharacterStyle
-    implements UpdateAppearance {
-
-  private final WXTextDecoration mTextDecoration;
-
-  public TextDecorationSpan(@NonNull WXTextDecoration wxTextDecoration) {
-    this.mTextDecoration = wxTextDecoration;
-  }
-
-  @Override
-  public void updateDrawState(TextPaint tp) {
-    switch (mTextDecoration) {
-      case LINETHROUGH:
-        tp.setUnderlineText(false);
-        tp.setStrikeThruText(true);
-        break;
-      case UNDERLINE:
-        tp.setUnderlineText(true);
-        tp.setStrikeThruText(false);
-        break;
-      case NONE:
-        tp.setUnderlineText(false);
-        tp.setStrikeThruText(false);
-        break;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/WXAttr.java b/android/sdk/src/main/java/com/taobao/weex/dom/WXAttr.java
deleted file mode 100644
index 82f853f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/WXAttr.java
+++ /dev/null
@@ -1,591 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Locale;
-import java.util.Map;
-import java.util.Set;
-
-import android.support.annotation.NonNull;
-import android.support.annotation.UiThread;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.Constants.Name;
-import com.taobao.weex.common.WXImageSharpen;
-import com.taobao.weex.dom.binding.ELUtils;
-import com.taobao.weex.dom.binding.WXStatement;
-import com.taobao.weex.el.parse.Parser;
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import static com.taobao.weex.dom.binding.ELUtils.COMPONENT_PROPS;
-import static com.taobao.weex.dom.binding.ELUtils.EXCLUDES_BINDING;
-import static java.lang.Boolean.parseBoolean;
-
-/**
- * store value of component attribute
- *
- */
-public class WXAttr implements Map<String, Object>,Cloneable {
-
-  private static final long serialVersionUID = -2619357510079360946L;
-
-  /**
-   * static attrs
-   * */
-  private @NonNull Map<String, Object> attr;
-  private Map<String, Object> writeAttr;
-
-  /**
-   * dynamic binding attrs, can be null, only weex use
-   * */
-  private ArrayMap<String, Object>  mBindingAttrs;
-
-  /**
-   * dynamic binding statement for match, can be null, only weex use
-   * */
-  private WXStatement mStatement;
-
-  public WXAttr(){
-    attr = new HashMap<>();
-  }
-
-  public WXAttr(@NonNull Map<String,Object> standardMap) {
-    attr = standardMap;
-  }
-
-  public WXAttr(@NonNull Map<String,Object> standardMap, int extra){
-    attr = standardMap;
-  }
-
-  public static String getPrefix(Map<String, Object> attr) {
-    if (attr == null) {
-      return null;
-    }
-    Object src = attr.get(Constants.Name.PREFIX);
-    if (src == null) {
-      return null;
-    }
-    return src.toString();
-  }
-
-  public static String getSuffix(Map<String, Object> attr) {
-    if (attr == null) {
-      return null;
-    }
-    Object src = attr.get(Constants.Name.SUFFIX);
-    if (src == null) {
-      return null;
-    }
-    return src.toString();
-  }
-
-  /**
-   * Compatible with value、content
-   *
-   * @return
-   */
-  public static String getValue(Map<String, Object> attr) {
-    if (attr == null) {
-      return null;
-    }
-    Object src = attr.get(Constants.Name.VALUE);
-    if (src == null) {
-      src = attr.get("content");
-      if (src == null) {
-        return null;
-      }
-    }
-    return src.toString();
-  }
-
-  public WXImageQuality getImageQuality() {
-    Object obj = containsKey(Name.QUALITY) ? get(Name.QUALITY) : get(Name.IMAGE_QUALITY);
-    WXImageQuality imageQuality = WXImageQuality.AUTO;
-    String value;
-    if (obj != null && !TextUtils.isEmpty(value = obj.toString())) {
-      try {
-        imageQuality = WXImageQuality.valueOf(value.toUpperCase(Locale.US));
-      }catch (IllegalArgumentException e){
-        WXLogUtils.e("Image", "Invalid value image quality. Only low, normal, high, original are valid");
-      }
-    }
-    return imageQuality;
-  }
-
-  public WXImageSharpen getImageSharpen() {
-    Object obj = get(Constants.Name.SHARPEN);
-    if (obj == null) {
-      obj = get(Constants.Name.IMAGE_SHARPEN);
-    }
-    if (obj == null) {
-      return WXImageSharpen.UNSHARPEN;
-    }
-    String imageSharpen = obj.toString();
-    WXImageSharpen waImageSharpen = WXImageSharpen.UNSHARPEN;
-    if (imageSharpen.equals("sharpen")) {
-      waImageSharpen = WXImageSharpen.SHARPEN;
-    }
-
-    return waImageSharpen;
-  }
-
-  public String getImageSrc() {
-    Object src = get(Constants.Name.SRC);
-    if (src == null) {
-      return null;
-    }
-    return src.toString();
-  }
-
-  public boolean canRecycled() {
-    Object obj = get(Constants.Name.RECYCLE);
-    if (obj == null) {
-      return true;
-    }
-    try {
-      return parseBoolean(String.valueOf(obj));
-    } catch (Exception e) {
-      WXLogUtils.e("[WXAttr] recycle:", e);
-    }
-    return true;
-  }
-
-  public boolean showIndicators() {
-    Object obj = get(Constants.Name.SHOW_INDICATORS);
-    if (obj == null) {
-      return true;
-    }
-
-    try {
-      return parseBoolean(String.valueOf(obj));
-    } catch (Exception e) {
-      WXLogUtils.e("[WXAttr] showIndicators:", e);
-    }
-    return true;
-  }
-
-  public boolean autoPlay() {
-    Object obj = get(Constants.Name.AUTO_PLAY);
-    if (obj == null) {
-      return false;
-    }
-
-    try {
-      return parseBoolean(String.valueOf(obj));
-    } catch (Exception e) {
-      WXLogUtils.e("[WXAttr] autoPlay:", e);
-    }
-    return false;
-  }
-
-  public String getScope() {
-    Object src = get(Constants.Name.SCOPE);
-    if (src == null) {
-      return null;
-    }
-    return src.toString();
-  }
-  public String getLoadMoreRetry() {
-    Object src = get(Constants.Name.LOADMORERETRY);
-    if (src == null) {
-      return null;
-    }
-    return src.toString();
-  }
-
-  public String getLoadMoreOffset() {
-    Object src = get(Constants.Name.LOADMOREOFFSET);
-    if (src == null) {
-      return null;
-    }
-    return src.toString();
-  }
-
-  public String optString(String key){
-    if(containsKey(key)){
-      Object value = get(key);
-      if (value instanceof String) {
-        return (String) value;
-      } else if (value != null) {
-        return String.valueOf(value);
-      }
-    }
-    return "";
-  }
-
-  public boolean getIsRecycleImage() {
-    Object obj = get(Constants.Name.RECYCLE_IMAGE);
-    if (obj == null) {
-      return true;
-    }
-
-    try {
-      return parseBoolean(String.valueOf(obj));
-    } catch (Exception e) {
-      WXLogUtils.e("[WXAttr] recycleImage:", e);
-    }
-    return false;
-  }
-  public String getScrollDirection() {
-    Object scrollDirection = get("scrollDirection");
-    if (scrollDirection == null) {
-      return "vertical";
-    }
-    return scrollDirection.toString();
-  }
-
-  public int getOrientation() {
-    String direction = getScrollDirection();
-    if(!TextUtils.isEmpty(direction)){
-      if(direction.equals(Constants.Value.HORIZONTAL)){
-        return Constants.Orientation.HORIZONTAL;
-      }
-    }
-    Object value = get(Name.ORIENTATION);
-    if(value != null && Constants.Value.HORIZONTAL.equals(value.toString())){
-      return Constants.Orientation.HORIZONTAL;
-    }
-    return Constants.Orientation.VERTICAL;
-  }
-
-  public float getElevation(int viewPortW) {
-    Object obj = get(Constants.Name.ELEVATION);
-    float ret = Float.NaN;
-    if (obj != null) {
-      String number = obj.toString();
-      if (!TextUtils.isEmpty(number)) {
-        ret = WXViewUtils.getRealSubPxByWidth(WXUtils.getFloat(number),viewPortW);
-      } else {
-        ret = 0;
-      }
-    }
-    return ret;
-  }
-
-  public float getColumnWidth(){
-
-    Object obj = get(Constants.Name.COLUMN_WIDTH);
-    if (obj == null) {
-      return Constants.Value.AUTO;
-    }
-
-    String value = String.valueOf(obj);
-    if(Constants.Name.AUTO.equals(value)){
-      return Constants.Value.AUTO;
-    }
-
-    try {
-      float columnWidth = Float.parseFloat(value);
-      return columnWidth > 0 ? columnWidth : 0;
-    } catch (Exception e) {
-      WXLogUtils.e("[WXAttr] getColumnWidth:", e);
-    }
-    return Constants.Value.AUTO;
-  }
-
-  public int getColumnCount() {
-
-    Object obj = get(Constants.Name.COLUMN_COUNT);
-    if (obj == null) {
-      return Constants.Value.AUTO;
-    }
-
-    String value = String.valueOf(obj);
-    if(Constants.Name.AUTO.equals(value)){
-      return Constants.Value.AUTO;
-    }
-
-    try {
-      int columnCount = Integer.parseInt(value);
-      return columnCount > 0 ? columnCount : Constants.Value.AUTO;
-    } catch (Exception e) {
-      WXLogUtils.e("[WXAttr] getColumnCount:", e);
-      return Constants.Value.AUTO;
-    }
-  }
-
-  public float getColumnGap() {
-
-    Object obj = get(Constants.Name.COLUMN_GAP);
-    if (obj == null) {
-      return Constants.Value.COLUMN_GAP_NORMAL;
-    }
-
-    String value = String.valueOf(obj);
-    if (Constants.Name.NORMAL.equals(value)) {
-      return Constants.Value.COLUMN_GAP_NORMAL;
-    }
-
-    try {
-      float columnGap = Float.parseFloat(value);
-      return columnGap >= 0 ? columnGap : Constants.Value.AUTO;
-    } catch (Exception e) {
-      WXLogUtils.e("[WXAttr] getColumnGap:", e);
-    }
-    return Constants.Value.COLUMN_GAP_NORMAL;
-  }
-
-  public int getLayoutType(){
-    Object obj = get(Constants.Name.LAYOUT);
-    if (obj == null) {
-      return WXRecyclerView.TYPE_LINEAR_LAYOUT;
-    }
-
-    try {
-      switch(String.valueOf(obj)){
-        case Constants.Value.MULTI_COLUMN :
-          return  WXRecyclerView.TYPE_STAGGERED_GRID_LAYOUT;
-        case Constants.Value.GRID :
-          return  WXRecyclerView.TYPE_GRID_LAYOUT;
-        default:
-          return WXRecyclerView.TYPE_LINEAR_LAYOUT;
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[WXAttr] getLayoutType:", e);
-    }
-    return WXRecyclerView.TYPE_LINEAR_LAYOUT;
-  }
-
-
-  @Override
-  public boolean equals(Object o) {
-    return attr.equals(o);
-  }
-
-  @Override
-  public int hashCode() {
-    return attr.hashCode();
-  }
-
-  @Override
-  public void clear() {
-    attr.clear();
-  }
-
-  @Override
-  public boolean containsKey(Object key) {
-    return attr.containsKey(key);
-  }
-
-  @Override
-  public boolean containsValue(Object value) {
-    return attr.containsValue(value);
-  }
-
-  @NonNull
-  @Override
-  public Set<Entry<String, Object>> entrySet() {
-    return attr.entrySet();
-  }
-
-  @Override
-  public Object get(Object key) {
-    Map<String, Object> temp = writeAttr;
-    if (null != temp) {
-      Object obj = temp.get(key);
-      if (null != obj) {
-        return obj;
-      }
-    }
-    return attr.get(key);
-  }
-
-  @Override
-  public boolean isEmpty() {
-    return attr.isEmpty();
-  }
-
-  @NonNull
-  @Override
-  public Set<String> keySet() {
-    return attr.keySet();
-  }
-
-  @Override
-  public Object put(String key, Object value) {
-    if(addBindingAttrIfStatement(key, value)){
-      return null;
-    }
-    return attr.put(key,value);
-  }
-
-  @Override
-  public void putAll(Map<? extends String, ?> map) {
-    //this.attr.putAll(map);
-    if (this.writeAttr == null) {
-      this.writeAttr = new ArrayMap<>();
-    }
-    this.writeAttr.putAll(map);
-  }
-
-  @Override
-  public Object remove(Object key) {
-    return attr.remove(key);
-  }
-
-  @Override
-  public int size() {
-    return attr.size();
-  }
-
-  @NonNull
-  @Override
-  public Collection<Object> values() {
-    return attr.values();
-  }
-
-  /**
-   * can by null, in most contion without template list, the value is null
-   * */
-  public ArrayMap<String, Object> getBindingAttrs() {
-    return mBindingAttrs;
-  }
-
-  /**
-   * can by null, in most contion without template list, the value is null
-   * */
-  public WXStatement getStatement() {
-    return mStatement;
-  }
-
-
-  public void setBindingAttrs(ArrayMap<String, Object> mBindingAttrs) {
-    this.mBindingAttrs = mBindingAttrs;
-  }
-
-  public void setStatement(WXStatement mStatement) {
-    this.mStatement = mStatement;
-  }
-
-  public void parseStatements(){
-    if(this.attr != null){
-       this.attr = filterStatementsFromAttrs(this.attr);
-    }
-  }
-
-  /**
-   * filter dynamic state ment
-   * */
-  private Map<String, Object> filterStatementsFromAttrs(Map attrs) {
-    if(attrs == null || attrs.size() == 0){
-      return attrs;
-    }
-    Set<Map.Entry<String,Object>> entries = attrs.entrySet();
-    Iterator<Entry<String,Object>> it =  entries.iterator();
-    while (it.hasNext()){
-      Map.Entry<String,Object> entry = it.next();
-      if(COMPONENT_PROPS.equals(entry.getKey())){
-        Object blockValue = ELUtils.bindingBlock(entry.getValue());
-        entry.setValue(blockValue);
-        continue;
-      }
-      if(addBindingAttrIfStatement(entry.getKey(), entry.getValue())){
-        it.remove();
-      }
-    }
-    return attrs;
-  }
-
-  /**
-   * filter dynamic attrs and statements
-   * */
-  private boolean addBindingAttrIfStatement(String key, Object value) {
-    for(String exclude : EXCLUDES_BINDING){
-      if(key.equals(exclude)){
-        return  false;
-      }
-    }
-    if(ELUtils.isBinding(value)){
-      if(mBindingAttrs == null){
-        mBindingAttrs = new ArrayMap<String, Object>();
-      }
-      value = ELUtils.bindingBlock(value);
-      mBindingAttrs.put(key, value);
-      return  true;
-    }
-    if(WXStatement.WX_IF.equals(key)){
-      if(mStatement == null){
-        mStatement = new WXStatement();
-      }
-      if(value != null) {
-        mStatement.put(key, Parser.parse(value.toString()));
-      }
-      return  true;
-    }
-
-    if(WXStatement.WX_FOR.equals(key)){
-      if(mStatement == null){
-        mStatement = new WXStatement();
-      }
-      value = ELUtils.vforBlock(value);
-      if(value != null) {
-        mStatement.put(key, value);
-        return  true;
-      }
-    }
-
-    if(WXStatement.WX_ONCE.equals(key)){
-      if(mStatement == null){
-        mStatement = new WXStatement();
-      }
-      mStatement.put(key, true);
-    }
-    return  false;
-  }
-
-  public void skipFilterPutAll(Map<String,Object> attrs){
-    this.attr.putAll(attrs);
-  }
-
-  @UiThread
-  public void mergeAttr() {
-    if (null != this.writeAttr) {
-      this.attr.putAll(this.writeAttr);
-      this.writeAttr = null;
-    }
-  }
-
-  @Override
-  public WXAttr clone() {
-    WXAttr wxAttr = new WXAttr();
-    wxAttr.skipFilterPutAll(attr);
-    if (mBindingAttrs != null) {
-      wxAttr.mBindingAttrs = new ArrayMap<>(mBindingAttrs);
-    }
-    if (mStatement != null){
-      wxAttr.mStatement = new WXStatement(mStatement);
-    }
-    return wxAttr;
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  @Override
-  public String toString() {
-    return attr.toString();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/WXCustomStyleSpan.java b/android/sdk/src/main/java/com/taobao/weex/dom/WXCustomStyleSpan.java
deleted file mode 100644
index d0c61fe..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/WXCustomStyleSpan.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import android.graphics.Typeface;
-import android.text.TextPaint;
-import android.text.style.MetricAffectingSpan;
-import com.taobao.weex.utils.TypefaceUtil;
-
-public class WXCustomStyleSpan extends MetricAffectingSpan {
-
-  private final int mStyle;
-  private final int mWeight;
-  private final String mFontFamily;
-
-  public WXCustomStyleSpan(int fontStyle, int fontWeight, String fontFamily) {
-    mStyle = fontStyle;
-    mWeight = fontWeight;
-    mFontFamily = fontFamily;
-  }
-
-  @Override
-  public void updateDrawState(TextPaint ds) {
-    TypefaceUtil.applyFontStyle(ds, mStyle, mWeight, mFontFamily);
-  }
-
-  @Override
-  public void updateMeasureState(TextPaint paint) {
-    TypefaceUtil.applyFontStyle(paint, mStyle, mWeight, mFontFamily);
-  }
-
-  /**
-   * Returns {@link Typeface#NORMAL} or {@link Typeface#ITALIC}.
-   */
-  public int getStyle() {
-    return (mStyle == WXStyle.UNSET ? 0 : mStyle);
-  }
-
-  /**
-   * Returns {@link Typeface#NORMAL} or {@link Typeface#BOLD}.
-   */
-  public int getWeight() {
-    return (mWeight == WXStyle.UNSET ? 0 : mWeight);
-  }
-
-  /**
-   * Returns the font family set for this StyleSpan.
-   */
-  public String getFontFamily() {
-    return mFontFamily;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/WXEvent.java b/android/sdk/src/main/java/com/taobao/weex/dom/WXEvent.java
deleted file mode 100644
index 5ee2456..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/WXEvent.java
+++ /dev/null
@@ -1,188 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import android.support.v4.util.ArrayMap;
-
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.dom.binding.ELUtils;
-import com.taobao.weex.dom.binding.JSONUtils;
-
-import java.io.Serializable;
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-
-/**
- * Store value of component event
- */
-public class WXEvent extends ArrayList<String> implements Serializable, Cloneable {
-
-  private static final long serialVersionUID = -8186587029452440107L;
-
-  /**
-   *  event data format
-   *  {
-   *  type: 'appear',
-   *  params: [
-   *  { '@binding': 'index' },
-   *   'static',
-   *   { '@binding': 'item.name' },
-   *  { '@binding': '$event' }
-   *  ]
-   *  }
-   * */
-  public static final String EVENT_KEY_TYPE = "type";
-  public static final String EVENT_KEY_ARGS = "params";
-
-
-  /**
-   * dynamic binding event args, can be null, only weex use
-   * */
-  private ArrayMap mEventBindingArgs;
-  private ArrayMap<String, List<Object>> mEventBindingArgsValues;
-
-
-  @Override
-  public void clear() {
-    if(mEventBindingArgs != null){
-      mEventBindingArgs.clear();
-    }
-    if(mEventBindingArgsValues != null){
-      mEventBindingArgsValues.clear();
-    }
-    super.clear();
-  }
-
-
-  public boolean remove(String o) {
-    if(mEventBindingArgs != null){
-      mEventBindingArgs.remove(o);
-    }
-    if(mEventBindingArgsValues != null){
-      mEventBindingArgsValues.remove(o);
-    }
-    return super.remove(o);
-  }
-
-  /**
-   * can by null
-   * */
-  public ArrayMap getEventBindingArgs() {
-    return mEventBindingArgs;
-  }
-
-
-  public ArrayMap<String, List<Object>> getEventBindingArgsValues() {
-    return mEventBindingArgsValues;
-  }
-
-
-  public void addEvent(Object event) {
-    if(event instanceof CharSequence){
-      if(JSONUtils.isJSON(event.toString())){
-        addEvent(JSONUtils.toJSON(event.toString()));
-        return;
-      }
-      String eventName = event.toString();
-      if(!contains(eventName)){
-        add(eventName);
-      }
-    }else if(event instanceof JSONObject){
-      JSONObject bindings = (JSONObject) event;
-      addBindingEvent(bindings);
-    }
-  }
-
-
-
-  public static String getEventName(Object event){
-    if(event instanceof CharSequence){
-      return event.toString();
-    }else if(event instanceof JSONObject){
-      JSONObject bindings = (JSONObject) event;
-      String eventName = bindings.getString(WXEvent.EVENT_KEY_TYPE);
-      return  eventName;
-    }
-    if(event == null){
-      return  null;
-    }
-    return  event.toString();
-  }
-
-
-  public void parseStatements() {
-     if(!isEmpty()){
-       for(int i=0; i<size(); i++){
-         String event =  get(i);
-         if(JSONUtils.isJSON(event)){
-           JSONObject object = JSONUtils.toJSON(event);
-           String eventName = addBindingEvent(object);
-           set(i, eventName);
-         }
-       }
-     }
-  }
-
-  private String addBindingEvent(JSONObject bindings){
-    String eventName = bindings.getString(WXEvent.EVENT_KEY_TYPE);
-    Object args = bindings.get(WXEvent.EVENT_KEY_ARGS);
-    if (eventName != null) {
-      addBindingArgsEvent(eventName, args);
-    }
-    return eventName;
-  }
-
-  private void addBindingArgsEvent(String eventName, Object args){
-    if(!contains(eventName)){
-      add(eventName);
-    }
-    if(args != null){
-      if(mEventBindingArgs == null){
-        mEventBindingArgs = new ArrayMap();
-      }
-      mEventBindingArgs.put(eventName, ELUtils.bindingBlock(args));
-    }
-  }
-
-  public void putEventBindingArgsValue(String event, List<Object> value){
-    if(mEventBindingArgsValues == null){
-      mEventBindingArgsValues = new ArrayMap();
-    }
-    if(value == null){
-      mEventBindingArgsValues.remove(event);
-    }else{
-      mEventBindingArgsValues.put(event, value);
-    }
-  }
-
-  @Override
-  public WXEvent clone() {
-    WXEvent event = new WXEvent();
-    event.addAll(this);
-    if(mEventBindingArgs != null) {
-      event.mEventBindingArgs = new ArrayMap(mEventBindingArgs);
-    }
-    event.mEventBindingArgsValues = null; //this should not be clone, it dynamic args
-    return  event;
-  }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/WXImageQuality.java b/android/sdk/src/main/java/com/taobao/weex/dom/WXImageQuality.java
deleted file mode 100644
index 6cce8f4..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/WXImageQuality.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-public enum WXImageQuality {
-
-  ORIGINAL,
-
-  LOW,
-
-  NORMAL,
-
-  HIGH,
-
-  AUTO
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/WXLineHeightSpan.java b/android/sdk/src/main/java/com/taobao/weex/dom/WXLineHeightSpan.java
deleted file mode 100644
index 6f58e45..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/WXLineHeightSpan.java
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import android.graphics.Paint;
-import android.text.style.LineHeightSpan;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.utils.WXLogUtils;
-
-public class WXLineHeightSpan implements LineHeightSpan{
-
-  private int lineHeight;
-  public WXLineHeightSpan(int lineHeight){
-    this.lineHeight=lineHeight;
-  }
-
-  @Override
-  public void chooseHeight(CharSequence text, int start, int end, int spanstartv, int v, Paint.FontMetricsInt fm) {
-    if(WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("LineHeight", text + " ; start " + start + "; end " + end + "; spanstartv "
-              + spanstartv + "; v " + v + "; fm " + fm);
-    }
-    int halfLeading=(lineHeight-(fm.descent-fm.ascent))/2;
-    fm.top-=halfLeading;
-    fm.bottom+=halfLeading;
-    fm.ascent-=halfLeading;
-    fm.descent+=halfLeading;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/WXStyle.java b/android/sdk/src/main/java/com/taobao/weex/dom/WXStyle.java
deleted file mode 100644
index 17f549e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/WXStyle.java
+++ /dev/null
@@ -1,559 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import android.graphics.Typeface;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.support.v4.util.ArrayMap;
-import android.text.Layout;
-import android.text.TextUtils;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.binding.ELUtils;
-import com.taobao.weex.ui.component.WXText;
-import com.taobao.weex.ui.component.WXTextDecoration;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import java.util.Collection;
-import java.util.Iterator;
-import java.util.Map;
-import java.util.Set;
-
-/**
- * Store value of component style
- *
- */
-public class WXStyle implements Map<String, Object>,Cloneable {
-
-  private static final long serialVersionUID = 611132641365274134L;
-  public static final int UNSET = -1;
-
-  @NonNull
-  private Map<String,Object> mStyles;
-
-  @Nullable
-  private Map<String,Map<String,Object>> mPesudoStyleMap;// clz_group:{styleMap}
-
-  @Nullable
-  private Map<String,Object> mPesudoResetStyleMap;
-
-  /**
-   * dynamic binding attrs, can be null, only weex use
-   * */
-  private ArrayMap<String, Object>  mBindingStyle;
-
-  public WXStyle(){
-    mStyles = new ArrayMap<>();
-  }
-
-  public WXStyle(Map<String, Object> styles){
-    this.mStyles = styles;
-    processPesudoClasses(this.mStyles);
-  }
-
-  public WXStyle(Map<String, Object> mStyles, boolean byPesudo) {
-    this();
-    this.putAll(mStyles, byPesudo);
-  }
-
-  @Nullable
-  public String getBlur() {
-    if(get(Constants.Name.FILTER) == null) {
-      return null;
-    }
-    return get(Constants.Name.FILTER).toString().trim();
-  }
-
-  /*
-   * text-decoration
-   **/
-  public static WXTextDecoration getTextDecoration(Map<String, Object> style) {
-    Object obj;
-    WXTextDecoration ret;
-    if (style == null || (obj = style.get(Constants.Name.TEXT_DECORATION)) == null) {
-      ret = WXTextDecoration.NONE;
-    } else {
-      String textDecoration = obj.toString();
-      switch (textDecoration) {
-        case "underline":
-          ret = WXTextDecoration.UNDERLINE;
-          break;
-        case "line-through":
-          ret = WXTextDecoration.LINETHROUGH;
-          break;
-        case "none":
-          ret = WXTextDecoration.NONE;
-          break;
-        default:
-          ret = WXTextDecoration.INVALID;
-          break;
-      }
-    }
-    return ret;
-  }
-
-  public static String getTextColor(Map<String, Object> style) {
-    if (style == null) {
-      return "";
-    }
-    Object temp = style.get(Constants.Name.COLOR);
-    return temp == null ? "" : temp.toString();
-  }
-
-  public static int getFontWeight(Map<String, Object> style) {
-    int typeface = android.graphics.Typeface.NORMAL;
-    if (style != null) {
-      Object temp = style.get(Constants.Name.FONT_WEIGHT);
-      if (temp != null) {
-        String fontWeight = temp.toString();
-        switch (fontWeight){
-          case "600":
-          case "700":
-          case "800":
-          case "900":
-          case Constants.Value.BOLD:
-            typeface=Typeface.BOLD;
-            break;
-        }
-      }
-    }
-    return typeface;
-  }
-
-  public static int getFontStyle(Map<String, Object> style) {
-    int typeface = android.graphics.Typeface.NORMAL;
-    if (style == null) {
-      return typeface;
-    }
-    Object temp = style.get(Constants.Name.FONT_STYLE);
-    if (temp == null) {
-      return typeface;
-    }
-    String fontWeight = temp.toString();
-    if (fontWeight.equals(Constants.Value.ITALIC)) {
-      typeface = android.graphics.Typeface.ITALIC;
-    }
-    return typeface;
-  }
-
-  public static int getFontSize(Map<String, Object> style,int viewPortW) {
-    if (style == null) {
-      return (int) WXViewUtils.getRealPxByWidth(WXText.sDEFAULT_SIZE,viewPortW);
-    }
-    int fontSize = WXUtils.getInt(style.get(Constants.Name.FONT_SIZE));
-    if (fontSize <= 0) {
-      fontSize = WXText.sDEFAULT_SIZE;
-    }
-    return (int) WXViewUtils.getRealPxByWidth(fontSize,viewPortW);
-  }
-
-  public static String getFontFamily(Map<String, Object> style) {
-    String fontFamily = null;
-    if (style != null) {
-      Object temp;
-      temp = style.get(Constants.Name.FONT_FAMILY);
-      if (temp != null) {
-        fontFamily = temp.toString();
-      }
-    }
-    return fontFamily;
-  }
-
-  public static Layout.Alignment getTextAlignment(Map<String, Object> style){
-    return getTextAlignment(style, false);
-  }
-
-  public static Layout.Alignment getTextAlignment(Map<String, Object> style, boolean isRTL){
-    Layout.Alignment alignment= isRTL ? Layout.Alignment.ALIGN_OPPOSITE : Layout.Alignment.ALIGN_NORMAL;
-    String textAlign= (String) style.get(Constants.Name.TEXT_ALIGN);
-    if(TextUtils.equals(Constants.Value.LEFT,textAlign)){
-      alignment= Layout.Alignment.ALIGN_NORMAL;
-    }
-    else if(TextUtils.equals(Constants.Value.CENTER,textAlign)){
-      alignment= Layout.Alignment.ALIGN_CENTER;
-    }
-    else if(TextUtils.equals(Constants.Value.RIGHT,textAlign)){
-      alignment= Layout.Alignment.ALIGN_OPPOSITE;
-    }
-    return alignment;
-  }
-
-  public static TextUtils.TruncateAt getTextOverflow(Map<String, Object> style){
-    TextUtils.TruncateAt truncateAt=null;
-    String ellipse = (String) style.get(Constants.Name.TEXT_OVERFLOW);
-    if(TextUtils.equals(Constants.Name.ELLIPSIS,ellipse)){
-      truncateAt = TextUtils.TruncateAt.END;
-    }
-    return truncateAt;
-  }
-
-  public static int getLines(Map<String, Object> style) {
-    return WXUtils.getInt(style.get(Constants.Name.LINES));
-  }
-
-  public static int getLineHeight(Map<String, Object> style,int viewPortW){
-    if (style == null) {
-      return UNSET;
-    }
-    int lineHeight = WXUtils.getInt(style.get(Constants.Name.LINE_HEIGHT));
-    if (lineHeight <= 0) {
-      lineHeight = UNSET;
-      return lineHeight;
-    }
-    return (int) WXViewUtils.getRealPxByWidth(lineHeight,viewPortW);
-  }
-
-  public float getBorderRadius() {
-    float temp = WXUtils.getFloat(get(Constants.Name.BORDER_RADIUS));
-    if (WXUtils.isUndefined(temp)) {
-      return Float.NaN;
-    }
-    return temp;
-  }
-
-  public String getBorderColor() {
-    Object color = get(Constants.Name.BORDER_COLOR);
-    return color == null ? null : color.toString();
-  }
-
-  public String getBorderStyle() {
-    Object borderStyle = get(Constants.Name.BORDER_STYLE);
-    return borderStyle == null ? null : borderStyle.toString();
-  }
-
-  public boolean isSticky() {
-    Object position = get(Constants.Name.POSITION);
-    if (position == null) {
-      return false;
-    }
-    return position.toString().equals(Constants.Value.STICKY);
-  }
-
-  public boolean isFixed() {
-    Object position = get(Constants.Name.POSITION);
-    if (position == null) {
-      return false;
-    }
-    return position.toString().equals(Constants.Value.FIXED);
-  }
-
-  public float getLeft() {
-    float temp = WXUtils.getFloat(get(Constants.Name.LEFT));
-    if (WXUtils.isUndefined(temp)) {
-      return Float.NaN;
-    }
-    return temp;
-  }
-
-  public float getRight() {
-    float temp = WXUtils.getFloat(get(Constants.Name.RIGHT));
-    if (WXUtils.isUndefined(temp)) {
-      return Float.NaN;
-    }
-    return temp;
-  }
-
-  public float getTop() {
-    float temp = WXUtils.getFloat(get(Constants.Name.TOP));
-    if (WXUtils.isUndefined(temp)) {
-      return Float.NaN;
-    }
-    return temp;
-  }
-
-  public float getBottom() {
-    float temp = WXUtils.getFloat(get(Constants.Name.BOTTOM));
-    if (WXUtils.isUndefined(temp)) {
-      return Float.NaN;
-    }
-    return temp;
-  }
-
-  /*
-   * others
-   **/
-  public String getBackgroundColor() {
-    Object temp = get(Constants.Name.BACKGROUND_COLOR);
-    return temp == null ? "" : temp.toString();
-  }
-
-  public int getTimeFontSize() {
-    int fontSize = WXUtils.getInt(get("timeFontSize"));
-    if (fontSize <= 0) {
-      fontSize = WXText.sDEFAULT_SIZE;
-    }
-    return fontSize;
-  }
-
-  public float getOpacity() {
-    Object object = get(Constants.Name.OPACITY);
-    float opacity = 1;
-    if (object == null) {
-      return opacity;
-    }
-    return WXUtils.getFloat(object);
-  }
-
-  public String getOverflow() {
-    Object obj = get(Constants.Name.OVERFLOW);
-    return obj == null ? Constants.Value.VISIBLE : obj.toString();
-  }
-
-  @Override
-  public boolean equals(Object o) {
-    return mStyles.equals(o);
-  }
-
-  @Override
-  public int hashCode() {
-    return mStyles.hashCode();
-  }
-
-  @Override
-  public void clear() {
-    mStyles.clear();
-  }
-
-  @Override
-  public boolean containsKey(Object key) {
-    return mStyles.containsKey(key);
-  }
-
-  @Override
-  public boolean containsValue(Object value) {
-    return mStyles.containsValue(value);
-  }
-
-  @NonNull
-  @Override
-  public Set<Entry<String, Object>> entrySet() {
-    return mStyles.entrySet();
-  }
-
-  @Override
-  public Object get(Object key) {
-    return mStyles.get(key);
-  }
-
-  @Override
-  public boolean isEmpty() {
-    return mStyles.isEmpty();
-  }
-
-  @NonNull
-  @Override
-  public Set<String> keySet() {
-    return mStyles.keySet();
-  }
-
-  @Override
-  public Object put(String key, Object value) {
-    if(addBindingStyleIfStatement(key, value)){
-      return null;
-    }
-    return mStyles.put(key,value);
-  }
-
-  @Override
-  public void putAll(Map<? extends String, ?> map) {
-    this.mStyles.putAll(map);
-  }
-
-  /**
-   * Used by Dom Thread， new and update styles.
-   * @param map
-   * @param byPesudo
-   */
-  public void putAll(Map<? extends String, ?> map, boolean byPesudo) {
-    this.mStyles.putAll(map);
-    if (!byPesudo) {
-      processPesudoClasses(map);
-    }
-  }
-
-  public void updateStyle(Map<? extends String, ?> map, boolean byPesudo){
-      parseBindingStylesStatements(map);
-      putAll(map, byPesudo);
-  }
-
-
-  public Map<String, Object> getPesudoResetStyles() {
-    if(mPesudoResetStyleMap == null){
-      mPesudoResetStyleMap = new ArrayMap<>();
-    }
-    return mPesudoResetStyleMap;
-  }
-
-  public Map<String, Map<String, Object>> getPesudoStyles() {
-    if(mPesudoStyleMap == null){
-      mPesudoStyleMap = new ArrayMap<>();
-    }
-    return mPesudoStyleMap;
-  }
-
-  <T extends String, V> void processPesudoClasses(Map<T, V> styles) {
-    Map<String, Object> tempMap = null;
-    for(Map.Entry<T, V> entry:styles.entrySet()){
-      //Key Format: "style-prop:pesudo_clz1:pesudo_clz2"
-      String key = entry.getKey();
-      int i;
-      if ((i = key.indexOf(":")) > 0) {
-        initPesudoMapsIfNeed(styles);
-        String clzName = key.substring(i);
-        if (clzName.equals(Constants.PSEUDO.ENABLED)) {
-          //enabled, use as regular style
-          String styleKey = key.substring(0, i);
-          if(tempMap == null){
-            tempMap = new ArrayMap<>();
-          }
-          tempMap.put(styleKey, entry.getValue());
-          mPesudoResetStyleMap.put(styleKey, entry.getValue());
-          continue;
-        } else {
-          clzName = clzName.replace(Constants.PSEUDO.ENABLED, "");//remove ':enabled' which is ignored
-        }
-
-        Map<String, Object> stylesMap = mPesudoStyleMap.get(clzName);
-        if (stylesMap == null) {
-          stylesMap = new ArrayMap<>();
-          mPesudoStyleMap.put(clzName, stylesMap);
-        }
-        stylesMap.put(key.substring(0, i), entry.getValue());
-      }
-    }
-
-    if (tempMap != null && !tempMap.isEmpty()) {
-      this.mStyles.putAll(tempMap);
-    }
-  }
-
-  @Override
-  public Object remove(Object key) {
-    return mStyles.remove(key);
-  }
-
-  @Override
-  public int size() {
-    return mStyles.size();
-  }
-
-  @NonNull
-  @Override
-  public Collection<Object> values() {
-    return mStyles.values();
-  }
-
-
-
-  private void initPesudoMapsIfNeed(Map<? extends String, ?> styles){
-    if(mPesudoStyleMap == null){
-      mPesudoStyleMap = new ArrayMap<>();
-    }
-    if(mPesudoResetStyleMap == null){
-      mPesudoResetStyleMap = new ArrayMap<>();
-    }
-    if(mPesudoResetStyleMap.isEmpty()){
-      mPesudoResetStyleMap.putAll(styles);
-    }
-  }
-
-
-
-  public void  parseStatements(){
-    if(this.mStyles != null){
-      this.mStyles = parseBindingStylesStatements(this.mStyles);
-    }
-  }
-
-  /**
-   * filter dynamic state ment
-   * */
-  private Map<String, Object> parseBindingStylesStatements(Map styles) {
-    if(styles == null || styles.size() == 0){
-      return styles;
-    }
-    Set<Map.Entry<String,Object>> entries = styles.entrySet();
-    Iterator<Entry<String,Object>> it =  entries.iterator();
-    while (it.hasNext()){
-      Map.Entry<String,Object> entry = it.next();
-      if(addBindingStyleIfStatement(entry.getKey(), entry.getValue())){
-        if(mPesudoStyleMap != null){
-          mPesudoStyleMap.remove(entry.getKey());
-        }
-        if(mPesudoResetStyleMap != null){
-          mPesudoResetStyleMap.remove(entry.getKey());
-        }
-        it.remove();
-      }
-    }
-    return styles;
-  }
-
-  /**
-   * filter dynamic attrs and statements
-   * */
-  private boolean addBindingStyleIfStatement(String key, Object value) {
-    if(ELUtils.isBinding(value)){
-      if(mBindingStyle == null){
-        mBindingStyle = new ArrayMap<String, Object>();
-      }
-      value = ELUtils.bindingBlock(value);
-      mBindingStyle.put(key, value);
-      return  true;
-    }
-    return  false;
-  }
-
-  public ArrayMap<String, Object> getBindingStyle() {
-    return mBindingStyle;
-  }
-
-  @Override
-  public WXStyle clone(){
-    WXStyle style = new WXStyle();
-    style.mStyles.putAll(this.mStyles);
-    if(mBindingStyle != null){
-      style.mBindingStyle = new ArrayMap<>(mBindingStyle);
-    }
-    if(mPesudoStyleMap != null) {
-      style.mPesudoStyleMap = new ArrayMap<>();
-      for (Entry<String, Map<String, Object>> entry : this.mPesudoStyleMap.entrySet()) {
-        Map<String, Object> valueClone = new ArrayMap<>();
-        valueClone.putAll(entry.getValue());
-        style.mPesudoStyleMap.put(entry.getKey(), valueClone);
-      }
-    }
-
-    if(mPesudoResetStyleMap!=null) {
-      style.mPesudoResetStyleMap = new ArrayMap<>();
-      style.mPesudoResetStyleMap.putAll(this.mPesudoResetStyleMap);
-    }
-
-
-    return style;
-  }
-
-  @Override
-  @RestrictTo(Scope.LIBRARY)
-  public String toString() {
-    return mStyles.toString();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/binding/ELUtils.java b/android/sdk/src/main/java/com/taobao/weex/dom/binding/ELUtils.java
deleted file mode 100644
index 390b611..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/binding/ELUtils.java
+++ /dev/null
@@ -1,127 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.dom.binding;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.el.parse.Parser;
-import com.taobao.weex.el.parse.Token;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.Set;
-
-/**
- * util's for binding and statment
- * Created by jianbai.gbj on 2017/8/17.
- */
-public class ELUtils {
-
-    public static final String BINDING = "@binding";
-    /**
-     * sub template
-     * */
-    public static final String IS_COMPONENT_ROOT = "@isComponentRoot";
-
-
-    public static final String COMPONENT_PROPS = "@componentProps";
-
-    public static final  String[] EXCLUDES_BINDING = {"clickEventParams"};
-
-    /**
-     * @param value check object is binding expression
-     * */
-    public static boolean isBinding(Object value){
-        if(value instanceof JSONObject){
-            JSONObject  object = (JSONObject) value;
-            if(object.containsKey(BINDING)){
-                return  true;
-            }
-        }else if(value instanceof JSONArray){
-            JSONArray array = (JSONArray) value;
-            for(int i=0; i<array.size(); i++){
-                if(isBinding(array.get(i))){
-                    return  true;
-                }
-            }
-        }else if(value instanceof String){
-            return ((String) value).indexOf(BINDING) >= 0;
-        }
-        return  false;
-    }
-
-    /**
-     * parse binding code to block, enable fast execute
-     * */
-    public static Object bindingBlock(Object value){
-        if(value instanceof JSONObject){
-            JSONObject  object = (JSONObject) value;
-            if(object.containsKey(BINDING)){
-                Object binding = object.get(BINDING);
-                if(!(binding instanceof Token)){
-                    object.put(BINDING, Parser.parse(binding.toString()));
-                }
-            }
-            Set<String> keys = object.keySet();
-            for(Object propsKey : keys){
-                if(object.get(propsKey) instanceof  JSONObject
-                        && ((JSONObject)object.get(propsKey)).containsKey(BINDING)){
-                    JSONObject propsValue = (JSONObject) object.get(propsKey);
-                    Object binding = propsValue.get(BINDING);
-                    if(!(binding instanceof Token)){
-                        propsValue.put(BINDING, Parser.parse(binding.toString()));
-                    }
-                }
-            }
-        }else if(value instanceof JSONArray){
-            JSONArray array = (JSONArray) value;
-            for(int i=0; i<array.size(); i++){
-                bindingBlock(array.get(i));
-            }
-        }else if(value instanceof String){
-            String json = value.toString();
-            if(json.startsWith("{")){
-                return bindingBlock(JSON.parseObject(json));
-            }else if(json.startsWith("[")){
-                return bindingBlock(JSON.parseArray(json));
-            }
-        }
-        return  value;
-    }
-
-    public static Object vforBlock(Object vfor){
-        if(vfor instanceof  JSONObject){
-            if(((JSONObject) vfor).containsKey(WXStatement.WX_FOR_LIST)){
-                Object list = ((JSONObject) vfor).get(WXStatement.WX_FOR_LIST);
-                if(!(list instanceof Token)){
-                    ((JSONObject) vfor).put(WXStatement.WX_FOR_LIST, Parser.parse(list.toString()));
-                }
-            }
-        }else if(vfor instanceof  String){
-            return vforBlock(JSONObject.parseObject(vfor.toString()));
-        }else{
-            if(WXEnvironment.isApkDebugable()){
-                WXLogUtils.e("weex", "weex vfor is illegal " + vfor);
-            }
-        }
-        return vfor;
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/binding/JSONUtils.java b/android/sdk/src/main/java/com/taobao/weex/dom/binding/JSONUtils.java
deleted file mode 100644
index 30d72d5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/binding/JSONUtils.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.dom.binding;
-
-import com.alibaba.fastjson.JSONObject;
-
-/**
- * Created by furture on 2018/5/8.
- */
-
-public class JSONUtils {
-
-
-    public static boolean isJSON(Object json){
-        if(json instanceof JSONObject){
-            return true;
-        }
-        if(json instanceof String){
-            return ((String) json).startsWith("{");
-        }
-        return false;
-    }
-
-    public static JSONObject toJSON(Object json){
-        if(json instanceof JSONObject){
-            return (JSONObject) json;
-        }
-        return JSONObject.parseObject(json.toString());
-    }
-
-
-    public static boolean isJSON(String json){
-        return json.startsWith("{");
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/binding/WXStatement.java b/android/sdk/src/main/java/com/taobao/weex/dom/binding/WXStatement.java
deleted file mode 100644
index 6a760cb..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/binding/WXStatement.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.dom.binding;
-
-import android.support.v4.util.ArrayMap;
-import android.support.v4.util.SimpleArrayMap;
-
-/**
- * Created by furture on 2017/8/17.
- * statement expression for template list, like v-if v-for
- */
-public class WXStatement extends ArrayMap<String, Object> implements  Cloneable  {
-
-    /**
-     * v-for statement, like
-     * <code>
-     *     <div v-for="(item, i) in dataset.panels">
-     *     <text>{{i}}: {{item.name}}</text>
-     *     </div>
-     * </code>
-     * json command:
-     * <code>
-     *      attr: {
-     *          '[[repeat]]': {
-     *          '@expression': 'dataList',
-     *          '@index': 'index',
-     *          '@alias': 'item'
-     *         }
-     *      }
-     * </code>
-     * */
-    public static final String WX_FOR = "[[repeat]]";
-    public static final String WX_FOR_INDEX = "@index";
-    public static final String WX_FOR_ITEM = "@alias";
-    public static final String WX_FOR_LIST = "@expression";
-
-
-    /**
-     * v-if statement, like:
-     * <code>
-     *   <p v-if="male">Male</p>
-     * </code>
-     * json command
-     * attr: {
-     *      '[[match]]': 'condition'
-     *    }
-     * */
-    public static final String WX_IF = "[[match]]";
-
-
-    /**
-     * once statement
-     * */
-    public static final  String WX_ONCE = "[[once]]";
-
-    public WXStatement() {
-    }
-
-    public WXStatement(SimpleArrayMap map) {
-        super(map);
-    }
-
-    @Override
-    protected WXStatement clone(){
-        return new WXStatement(this);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/dom/transition/WXTransition.java b/android/sdk/src/main/java/com/taobao/weex/dom/transition/WXTransition.java
deleted file mode 100644
index cc468bb..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/dom/transition/WXTransition.java
+++ /dev/null
@@ -1,762 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.dom.transition;
-
-import android.animation.Animator;
-import android.animation.AnimatorListenerAdapter;
-import android.animation.ArgbEvaluator;
-import android.animation.ObjectAnimator;
-import android.animation.PropertyValuesHolder;
-import android.animation.ValueAnimator;
-import android.graphics.drawable.ColorDrawable;
-import android.os.Handler;
-import android.support.v4.util.ArrayMap;
-import android.support.v4.view.animation.PathInterpolatorCompat;
-import android.text.TextUtils;
-import android.util.Property;
-import android.view.View;
-import android.view.animation.Interpolator;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.Constants;
-//import com.taobao.weex.dom.DOMActionContext;
-//import com.taobao.weex.dom.WXDomHandler;
-//import com.taobao.weex.dom.WXDomObject;
-//import com.taobao.weex.dom.flex.Spacing;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.ui.animation.BackgroundColorProperty;
-import com.taobao.weex.ui.animation.TransformParser;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.SingleFunctionParser;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.ArrayList;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.atomic.AtomicInteger;
-import java.util.regex.Pattern;
-
-import static com.taobao.weex.common.Constants.TimeFunction.CUBIC_BEZIER;
-import static com.taobao.weex.common.Constants.TimeFunction.EASE;
-import static com.taobao.weex.common.Constants.TimeFunction.EASE_IN;
-import static com.taobao.weex.common.Constants.TimeFunction.EASE_IN_OUT;
-import static com.taobao.weex.common.Constants.TimeFunction.EASE_OUT;
-import static com.taobao.weex.common.Constants.TimeFunction.LINEAR;
-
-/**
- *   transition on dom thread
- *   transition-property: height;
- *   transition-duration: .3s;
- *   transition-delay: .05s;
- *   transition-timing-function: ease-in-out;
- *
- *   Created by furture on 2017/10/18.
- */
-public class WXTransition {
-
-    public static final  String TRANSITION_PROPERTY = "transitionProperty";
-    public static final  String TRANSITION_DURATION = "transitionDuration";
-    public static final  String TRANSITION_DELAY = "transitionDelay";
-    public static final  String TRANSITION_TIMING_FUNCTION = "transitionTimingFunction";
-
-    public static final  Pattern PROPERTY_SPLIT_PATTERN = Pattern.compile("\\||,");
-
-
-    /**
-     * layout animation property
-     * */
-    private static final Set<String> LAYOUT_PROPERTIES = new HashSet<>();
-    static {
-        LAYOUT_PROPERTIES.add(Constants.Name.WIDTH);
-        LAYOUT_PROPERTIES.add(Constants.Name.HEIGHT);
-        LAYOUT_PROPERTIES.add(Constants.Name.MARGIN_TOP);
-        LAYOUT_PROPERTIES.add(Constants.Name.MARGIN_BOTTOM);
-        LAYOUT_PROPERTIES.add(Constants.Name.MARGIN_LEFT);
-        LAYOUT_PROPERTIES.add(Constants.Name.MARGIN_RIGHT);
-        LAYOUT_PROPERTIES.add(Constants.Name.LEFT);
-        LAYOUT_PROPERTIES.add(Constants.Name.RIGHT);
-        LAYOUT_PROPERTIES.add(Constants.Name.TOP);
-        LAYOUT_PROPERTIES.add(Constants.Name.BOTTOM);
-        LAYOUT_PROPERTIES.add(Constants.Name.PADDING_LEFT);
-        LAYOUT_PROPERTIES.add(Constants.Name.PADDING_RIGHT);
-        LAYOUT_PROPERTIES.add(Constants.Name.PADDING_TOP);
-        LAYOUT_PROPERTIES.add(Constants.Name.PADDING_BOTTOM);
-    }
-
-    /**
-     * transform animation property, use android system animaton ability
-     * */
-    private static final Set<String> TRANSFORM_PROPERTIES = new HashSet<>();
-    static {
-        TRANSFORM_PROPERTIES.add(Constants.Name.OPACITY);
-        TRANSFORM_PROPERTIES.add(Constants.Name.BACKGROUND_COLOR);
-        TRANSFORM_PROPERTIES.add(Constants.Name.TRANSFORM);
-    }
-
-    private List<String> properties;
-    private Interpolator  interpolator;
-    private long  duration;
-    private long delay;
-    private WXComponent mWXComponent;
-    private Handler handler;
-    private ValueAnimator layoutValueAnimator;
-    private Map<String, Object> layoutPendingUpdates;
-    private ObjectAnimator transformAnimator;
-    private Map<String, Object> transformPendingUpdates;
-    private Runnable transitionEndEvent;
-    private Map<String, Object> targetStyles;
-    private Runnable animationRunnable;
-
-    private Runnable transformAnimationRunnable;
-    private volatile AtomicInteger lockToken = new AtomicInteger(0);
-
-
-    public WXTransition() {
-        this.properties = new ArrayList<>(4);
-        this.handler = new Handler();
-        this.layoutPendingUpdates = new ArrayMap<>();
-        this.transformPendingUpdates = new ArrayMap<>();
-        this.targetStyles = new ArrayMap<>();
-    }
-
-    /**
-     * create transition from map styles if style contains transitionProperty
-     * */
-    public static WXTransition fromMap(Map<String, Object> style, WXComponent component){
-        if(style.get(TRANSITION_PROPERTY) == null){
-            return  null;
-        }
-        String propertyString = WXUtils.getString(style.get(TRANSITION_PROPERTY), null);
-        if(propertyString == null){
-            return null;
-        }
-        WXTransition transition  = new WXTransition();
-        updateTransitionProperties(transition, propertyString);
-        if(transition.properties.isEmpty()){
-            return  null;
-        }
-        transition.duration = parseTimeMillis(style, TRANSITION_DURATION, 0);
-        transition.delay =  parseTimeMillis(style, TRANSITION_DELAY, 0);
-        transition.interpolator = createTimeInterpolator(WXUtils.getString(style.get(TRANSITION_TIMING_FUNCTION), null));
-        transition.mWXComponent = component;
-        return  transition;
-    }
-
-    /**
-     * check updates has transition property
-     * */
-    public boolean hasTransitionProperty(Map<String, Object> styles){
-        for(String property : properties){
-            if(styles.containsKey(property)){
-                return  true;
-            }
-        }
-        return false;
-    }
-
-    public void updateTranstionParams(Map<String, Object> updates){
-        if(updates.containsKey(TRANSITION_DELAY)){
-            mWXComponent.getStyles().put(TRANSITION_DELAY, updates.remove(TRANSITION_DELAY));
-            this.delay = parseTimeMillis(mWXComponent.getStyles(), TRANSITION_DELAY, 0);
-        }
-
-        if(updates.containsKey(TRANSITION_TIMING_FUNCTION) && updates.get(TRANSITION_TIMING_FUNCTION) != null){
-            mWXComponent.getStyles().put(TRANSITION_TIMING_FUNCTION, updates.remove(TRANSITION_TIMING_FUNCTION));
-            this.interpolator = createTimeInterpolator(mWXComponent.getStyles().get(TRANSITION_TIMING_FUNCTION).toString());
-        }
-
-        if(updates.containsKey(TRANSITION_DURATION)){
-            mWXComponent.getStyles().put(TRANSITION_DURATION, updates.remove(TRANSITION_DURATION));
-            this.duration = parseTimeMillis(mWXComponent.getStyles(), TRANSITION_DURATION, 0);
-        }
-
-        if(updates.containsKey(TRANSITION_PROPERTY)){
-            mWXComponent.getStyles().put(TRANSITION_PROPERTY, updates.remove(TRANSITION_PROPERTY));
-            updateTransitionProperties(this, WXUtils.getString(mWXComponent.getStyles().get(TRANSITION_PROPERTY), null));
-        }
-    }
-
-    /**
-     * start transition animation, updates maybe split two different updates,
-     * because javascript will send multi update on same transition, we assume that updates in 8ms is one transition
-     * */
-    public void  startTransition(Map<String, Object> updates){
-        synchronized (lockToken){
-            final View taregtView = getTargetView();
-            if(taregtView == null){
-                return;
-            }
-            final int token = lockToken.incrementAndGet();
-            for(String property : properties){
-                if(updates.containsKey(property)){
-                    Object targetValue = updates.remove(property);
-                    if(LAYOUT_PROPERTIES.contains(property)) {
-                        layoutPendingUpdates.put(property, targetValue);
-                    }else if(TRANSFORM_PROPERTIES.contains(property)){
-                        transformPendingUpdates.put(property, targetValue);
-                    }
-                }
-            }
-
-            int delay = WXUtils.getNumberInt(mWXComponent.getAttrs().get("actionDelay"), 16);
-            if(delay > duration){
-                delay = (int) duration;
-            }
-            if(animationRunnable != null) {
-                handler.removeCallbacks(animationRunnable);
-            }
-            animationRunnable = new Runnable() {
-                @Override
-                public void run() {
-                    if(token == lockToken.get()) {
-                        doTransitionAnimation(token);
-                    }
-                    animationRunnable = null;
-                }
-            };
-            if(delay > 0){
-                handler.postDelayed(animationRunnable, delay);
-            }else{
-                animationRunnable.run();
-            }
-        }
-    }
-
-    /**
-     * doTransitionAnimation include transform and layout animation.
-     * 1. put pre transition updates from target style to dom style
-     * 2. do transform animation and layout animation
-     * */
-    private void  doTransitionAnimation(final  int token){
-        final View taregtView = getTargetView();
-        if(taregtView == null){
-            return;
-        }
-        if(targetStyles.size() > 0){
-            for(String property : properties){
-                if(!(LAYOUT_PROPERTIES.contains(property) || TRANSFORM_PROPERTIES.contains(property))){
-                    continue;
-                }
-                if(layoutPendingUpdates.containsKey(property)){
-                    continue;
-                }
-                if(transformPendingUpdates.containsKey(property)){
-                    continue;
-                }
-                synchronized (targetStyles){
-                    if(targetStyles.containsKey(property)){
-                        //reset pre transition style
-                        Object targetValue = targetStyles.remove(property);
-                        mWXComponent.getStyles().put(property, targetValue);
-//                        domObject.getStyles().put(property, targetValue);
-//                        WXComponent component = getComponent();
-//                        if(component != null && component.getDomObject() != null){
-//                            component.getDomObject().getStyles().put(property, targetValue);
-//                        }
-                    }
-                }
-            }
-        }
-
-
-
-        if(transitionEndEvent != null){
-            taregtView.removeCallbacks(transitionEndEvent);
-        }
-        if(transitionEndEvent == null && duration > Float.MIN_NORMAL){
-            transitionEndEvent = new Runnable(){
-                @Override
-                public void run() {
-                    transitionEndEvent = null;
-                    if(duration < Float.MIN_NORMAL){
-                        return;
-                    }
-                    if(mWXComponent != null && mWXComponent.getEvents().contains(Constants.Event.ON_TRANSITION_END)){
-                        mWXComponent.fireEvent(Constants.Event.ON_TRANSITION_END);
-                    }
-                }
-            };
-        }
-        if(transformAnimationRunnable != null) {
-            taregtView.removeCallbacks(transformAnimationRunnable);
-        }
-        transformAnimationRunnable = new Runnable() {
-            @Override
-            public void run() {
-                synchronized (lockToken) {
-                    if(token == lockToken.get()) {
-                        doPendingTransformAnimation(token);
-                    }
-                }
-            }
-        };
-        taregtView.post(transformAnimationRunnable);
-        doPendingLayoutAnimation();
-    }
-
-
-    /**
-     *  transform, opacity, backgroundcolor which not effect layout use android system animation in main thread.
-     * */
-    private void doPendingTransformAnimation(int token) {
-        if(transformAnimator != null){
-            transformAnimator.cancel();
-            transformAnimator = null;
-        }
-        if(transformPendingUpdates.size() == 0){
-            return;
-        }
-        final View taregtView = getTargetView();
-        if(taregtView == null){
-            return;
-        }
-        List<PropertyValuesHolder> holders = new ArrayList<>(8);
-        String transform  = WXUtils.getString(transformPendingUpdates.remove(Constants.Name.TRANSFORM), null);
-        if(!TextUtils.isEmpty(transform)){
-            Map<Property<View,Float>, Float>  properties = TransformParser.parseTransForm(mWXComponent.getInstanceId(), transform, (int)mWXComponent.getLayoutWidth(), (int)mWXComponent.getLayoutHeight(), mWXComponent.getViewPortWidth());
-            PropertyValuesHolder[]  transformHolders = TransformParser.toHolders(properties);
-            for(PropertyValuesHolder holder : transformHolders){
-                holders.add(holder);
-            }
-            synchronized (targetStyles) {
-                targetStyles.put(Constants.Name.TRANSFORM, transform);
-            }
-        }
-
-        for(String property : properties){
-            if(!TRANSFORM_PROPERTIES.contains(property)){
-                continue;
-            }
-            if(!transformPendingUpdates.containsKey(property)){
-                continue;
-            }
-            Object value = transformPendingUpdates.remove(property);
-            synchronized (targetStyles) {
-                targetStyles.put(property, value);
-            }
-            switch (property){
-                case Constants.Name.OPACITY:{
-                    holders.add(PropertyValuesHolder.ofFloat(View.ALPHA, taregtView.getAlpha(), WXUtils.getFloat(value, 1.0f)));
-                    taregtView.setLayerType(View.LAYER_TYPE_SOFTWARE, null); //hardware or none has bug on some platform
-                }
-                break;
-                case Constants.Name.BACKGROUND_COLOR:{
-                    int fromColor = WXResourceUtils.getColor(WXUtils.getString(mWXComponent.getStyles().getBackgroundColor(), null), 0);
-                    int toColor = WXResourceUtils.getColor(WXUtils.getString(value, null), 0);
-                    if(WXViewUtils.getBorderDrawable(taregtView) != null){
-                        fromColor = WXViewUtils.getBorderDrawable(taregtView).getColor();
-                    }else if (taregtView.getBackground() instanceof ColorDrawable) {
-                        fromColor = ((ColorDrawable) taregtView.getBackground()).getColor();
-                    }
-                    holders.add(PropertyValuesHolder.ofObject(new BackgroundColorProperty(), new ArgbEvaluator(), fromColor,toColor));
-                }
-                break;
-                default:break;
-            }
-        }
-
-        if(token == lockToken.get()) {
-            transformPendingUpdates.clear();
-        }
-        transformAnimator =  ObjectAnimator.ofPropertyValuesHolder(taregtView, holders.toArray(new PropertyValuesHolder[holders.size()]));
-        transformAnimator.setDuration((long) duration);
-        if((long) delay > 0) {
-            transformAnimator.setStartDelay((long) delay);
-        }
-        if(interpolator != null) {
-            transformAnimator.setInterpolator(interpolator);
-        }
-        transformAnimator.addListener(new AnimatorListenerAdapter() {
-            boolean  hasCancel = false;
-            @Override
-            public void onAnimationCancel(Animator animation) {
-                super.onAnimationCancel(animation);
-                hasCancel = true;
-            }
-
-            @Override
-            public void onAnimationEnd(Animator animation) {
-                if(hasCancel){
-                    return;
-                }
-                super.onAnimationEnd(animation);
-                WXTransition.this.onTransitionAnimationEnd();
-            }
-        });
-        transformAnimator.start();
-    }
-
-
-    public void doPendingLayoutAnimation(){
-        if(layoutValueAnimator != null){
-            layoutValueAnimator.cancel();
-            layoutValueAnimator = null;
-        }
-        if(layoutPendingUpdates.size() == 0){
-            return;
-        }
-        PropertyValuesHolder[] holders = new PropertyValuesHolder[layoutPendingUpdates.size()];
-        int index = 0;
-        for(String property : properties){
-            if(!LAYOUT_PROPERTIES.contains(property)){
-                continue;
-            }
-            if(layoutPendingUpdates.containsKey(property)){
-                Object targetValue = layoutPendingUpdates.remove(property);
-                synchronized (targetStyles) {
-                    targetStyles.put(property, targetValue);
-                }
-                holders[index] = createLayoutPropertyValueHolder(property, targetValue);
-                index++;
-            }
-        }
-        layoutPendingUpdates.clear();
-        doLayoutPropertyValuesHolderAnimation(holders);
-    }
-
-
-    private PropertyValuesHolder createLayoutPropertyValueHolder(String property, Object value){
-        PropertyValuesHolder holder = null;
-        switch (property){
-            case Constants.Name.WIDTH:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.WIDTH, mWXComponent.getLayoutWidth(),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloat(value, 0.0f), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.HEIGHT:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.HEIGHT, mWXComponent.getLayoutHeight(),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloat(value, 0.0f), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.MARGIN_TOP:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.MARGIN_TOP,  mWXComponent.getMargin().get(CSSShorthand.EDGE.TOP),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.MARGIN_LEFT:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.MARGIN_LEFT,  mWXComponent.getMargin().get(CSSShorthand.EDGE.LEFT),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.MARGIN_RIGHT:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.MARGIN_RIGHT,  mWXComponent.getMargin().get(CSSShorthand.EDGE.RIGHT),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.MARGIN_BOTTOM:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.MARGIN_BOTTOM,  mWXComponent.getMargin().get(CSSShorthand.EDGE.BOTTOM),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.LEFT:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.LEFT,  mWXComponent.getLayoutPosition().getLeft(),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.RIGHT:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.RIGHT,  mWXComponent.getLayoutPosition().getRight(),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.BOTTOM:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.BOTTOM,  mWXComponent.getLayoutPosition().getBottom(),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.TOP:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.TOP,  mWXComponent.getLayoutPosition().getTop(),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.PADDING_TOP:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.PADDING_TOP,  mWXComponent.getPadding().get(CSSShorthand.EDGE.TOP),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.PADDING_BOTTOM:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.PADDING_BOTTOM,  mWXComponent.getPadding().get(CSSShorthand.EDGE.BOTTOM),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.PADDING_LEFT:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.PADDING_LEFT,  mWXComponent.getPadding().get(CSSShorthand.EDGE.LEFT),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            case Constants.Name.PADDING_RIGHT:{
-                holder = PropertyValuesHolder.ofFloat(Constants.Name.PADDING_RIGHT,  mWXComponent.getPadding().get(CSSShorthand.EDGE.RIGHT),
-                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
-            }
-            break;
-            default:
-                break;
-        }
-        if(holder == null){
-            holder  = PropertyValuesHolder.ofFloat(property, 1, 1);
-        }
-        return  holder;
-    }
-
-    private void doLayoutPropertyValuesHolderAnimation(PropertyValuesHolder[] holders){
-        layoutValueAnimator = ValueAnimator.ofPropertyValuesHolder(holders);
-        layoutValueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
-            @Override
-            public void onAnimationUpdate(final ValueAnimator animation) {
-                PropertyValuesHolder holders[] = animation.getValues();
-                for(PropertyValuesHolder holder : holders){
-
-                    final String property =  holder.getPropertyName();
-                    asynchronouslyUpdateLayout(mWXComponent, property, (Float) animation.getAnimatedValue(property));
-                }
-//                WXBridgeManager.getInstance().calculateLayoutPostToJSThread(mWXComponent.getInstanceId(), mWXComponent.getRef(), false);
-            }
-        });
-        layoutValueAnimator.addListener(new AnimatorListenerAdapter() {
-
-            boolean  hasCancel = false;
-            @Override
-            public void onAnimationCancel(Animator animation) {
-                super.onAnimationCancel(animation);
-                hasCancel = true;
-            }
-
-            @Override
-            public void onAnimationEnd(Animator animation) {
-                if(hasCancel){
-                    return;
-                }
-                super.onAnimationEnd(animation);
-                WXTransition.this.onTransitionAnimationEnd();
-            }
-        });
-        if(interpolator != null) {
-            layoutValueAnimator.setInterpolator(interpolator);
-        }
-        layoutValueAnimator.setStartDelay((long) (delay));
-        layoutValueAnimator.setDuration((long) (duration));
-        layoutValueAnimator.start();
-    }
-
-    @SuppressWarnings("unused")
-    public static void asynchronouslyUpdateLayout(WXComponent component, final String propertyName, final float propertyValue) {
-        if(component == null) {
-            return;
-        }
-        final String ref = component.getRef();
-        final String instanceId = component.getInstanceId();
-        if(TextUtils.isEmpty(ref) || TextUtils.isEmpty(instanceId)) {
-            return;
-        }
-
-        WXSDKManager.getInstance().getWXBridgeManager().post(new Runnable() {
-            @Override
-            public void run() {
-                switch (propertyName){
-                    case Constants.Name.WIDTH:{
-                        WXBridgeManager.getInstance().setStyleWidth(instanceId, ref, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.HEIGHT:{
-                        WXBridgeManager.getInstance().setStyleHeight(instanceId, ref, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.MARGIN_TOP:{
-                        WXBridgeManager.getInstance().setMargin(instanceId, ref, CSSShorthand.EDGE.TOP, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.MARGIN_LEFT:{
-                        WXBridgeManager.getInstance().setMargin(instanceId, ref, CSSShorthand.EDGE.LEFT, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.MARGIN_RIGHT:{
-                        WXBridgeManager.getInstance().setMargin(instanceId, ref, CSSShorthand.EDGE.RIGHT, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.MARGIN_BOTTOM:{
-                        WXBridgeManager.getInstance().setMargin(instanceId, ref, CSSShorthand.EDGE.BOTTOM, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.LEFT:{
-                        WXBridgeManager.getInstance().setPosition(instanceId, ref, CSSShorthand.EDGE.LEFT, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.RIGHT:{
-                        WXBridgeManager.getInstance().setPosition(instanceId, ref, CSSShorthand.EDGE.RIGHT, (propertyValue));
-                    }
-                    break;
-                    case Constants.Name.BOTTOM:{
-                        WXBridgeManager.getInstance().setPosition(instanceId, ref, CSSShorthand.EDGE.BOTTOM, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.TOP:{
-                        WXBridgeManager.getInstance().setPosition(instanceId, ref, CSSShorthand.EDGE.TOP, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.PADDING_TOP:{
-                        WXBridgeManager.getInstance().setPadding(instanceId, ref, CSSShorthand.EDGE.TOP, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.PADDING_BOTTOM:{
-                        WXBridgeManager.getInstance().setPadding(instanceId, ref, CSSShorthand.EDGE.BOTTOM, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.PADDING_LEFT:{
-                        WXBridgeManager.getInstance().setPadding(instanceId, ref, CSSShorthand.EDGE.LEFT, propertyValue);
-                    }
-                    break;
-                    case Constants.Name.PADDING_RIGHT:{
-                        WXBridgeManager.getInstance().setPadding(instanceId, ref, CSSShorthand.EDGE.RIGHT, propertyValue);
-                    }
-                    break;
-                    default:
-                        break;
-                }
-            }
-        });
-    }
-
-    private synchronized void onTransitionAnimationEnd(){
-        if(duration > 0){
-            if(transitionEndEvent != null){
-                View view = getTargetView();
-                if(view != null &&  transitionEndEvent != null){
-                    view.post(transitionEndEvent);
-                }
-                transitionEndEvent = null;
-            }
-        }
-        synchronized (targetStyles){
-            if(targetStyles.size() > 0){
-                for(String property : properties) {
-                    if(targetStyles.containsKey(property)){
-                        Object targetValue = targetStyles.remove(property);
-                        mWXComponent.getStyles().put(property, targetValue);
-                    }
-                }
-                targetStyles.clear();
-            }
-        }
-    }
-
-    private View getTargetView(){
-        return null != mWXComponent ? mWXComponent.getHostView() : null;
-    }
-
-
-    /**
-     * get time millis
-     * */
-    private static long parseTimeMillis(Map<String, Object> style, String key, long defaultValue){
-        String  duration = WXUtils.getString(style.get(key), null);
-        if(duration != null){
-            duration = duration.replaceAll("ms", "");
-        }
-        if(duration != null){
-            if(WXEnvironment.isApkDebugable()){
-                if(duration.contains("px")){
-                    WXLogUtils.w("Transition Duration Unit Only Support ms, " + duration + " is not ms Unit");
-                }
-            }
-            duration = duration.replaceAll("px", "");
-        }
-        if(TextUtils.isEmpty(duration)){
-            return  defaultValue;
-        }
-        try{
-            return (long)Float.parseFloat(duration);
-        }catch (NumberFormatException e){
-            return  defaultValue;
-        }
-    }
-
-    /**
-     * create interpolcator same with web
-     * http://www.w3school.com.cn/cssref/pr_transition-timing-function.asp
-     * */
-    private static Interpolator createTimeInterpolator(String interpolator) {
-        if (!TextUtils.isEmpty(interpolator)) {
-            switch (interpolator) {
-                case EASE_IN:
-                    return PathInterpolatorCompat.create(0.42f,0f, 1f,1f);
-                case EASE_OUT:
-                    return PathInterpolatorCompat.create(0f,0f, 0.58f,1f);
-                case EASE_IN_OUT:
-                    return PathInterpolatorCompat.create(0.42f,0f, 0.58f,1f);
-                case EASE:
-                    return PathInterpolatorCompat.create(0.25f,0.1f, 0.25f,1f);
-                case LINEAR:
-                    return PathInterpolatorCompat.create(0.0f,0f, 1f,1f);
-                default:
-                    try {
-                        //Parse cubic-bezier
-                        SingleFunctionParser<Float> parser = new SingleFunctionParser<>(
-                                interpolator,
-                                new SingleFunctionParser.FlatMapper<Float>() {
-                                    @Override
-                                    public Float map(String raw) {
-                                        return Float.parseFloat(raw);
-                                    }
-                                });
-                        List<Float> params = parser.parse(CUBIC_BEZIER);
-                        if (params != null && params.size() == 4) {
-                            return PathInterpolatorCompat.create(
-                                    params.get(0), params.get(1), params.get(2), params.get(3));
-                        }
-                    } catch (RuntimeException e) {
-                        if(WXEnvironment.isApkDebugable()) {
-                            WXLogUtils.e("WXTransition", e);
-                        }
-                    }
-            }
-        }
-        return PathInterpolatorCompat.create(0.25f,0.1f, 0.25f,1f);
-    }
-
-    private static  void  updateTransitionProperties(WXTransition transition, String transtionProperty){
-        if(transtionProperty == null){
-            return;
-        }
-        transition.properties.clear();
-        String[] propertiesArray = PROPERTY_SPLIT_PATTERN.split(transtionProperty);
-        for(String property : propertiesArray){
-            String trim = property.trim();
-            if(TextUtils.isEmpty(trim)){
-                continue;
-            }
-            if(!(LAYOUT_PROPERTIES.contains(trim) || TRANSFORM_PROPERTIES.contains(trim))){
-                if(WXEnvironment.isApkDebugable()){
-                    WXLogUtils.e("WXTransition Property Not Supported" + trim + " in " + transtionProperty);
-                }
-                continue;
-            }
-            transition.properties.add(trim);
-        }
-    }
-
-    public List<String> getProperties() {
-        return properties;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/el/parse/ArrayStack.java b/android/sdk/src/main/java/com/taobao/weex/el/parse/ArrayStack.java
deleted file mode 100644
index 0feb85e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/el/parse/ArrayStack.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.el.parse;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * stack for parse and execute code
- * Created by jianbai.gbj on 2017/9/1.
- */
-public class ArrayStack<T> {
-
-    private ArrayList<T> stack;
-
-    public ArrayStack() {
-        this.stack = new ArrayList<T>(4);
-    }
-
-    public int size() {
-        return stack.size();
-    }
-
-    public T pop() {
-        return stack.remove(stack.size()-1);
-    }
-
-    public void push(T token) {
-        stack.add(token);
-    }
-
-
-    public T peek() {
-        return stack.get(stack.size()-1);
-    }
-
-    public T get(int i) {
-        return stack.get(i);
-    }
-
-    public T remove(int i) {
-        return stack.remove(i);
-    }
-
-    public void add(int i, T t) {
-        stack.add(i, t);
-    }
-
-    public boolean isEmpty() {
-        return   stack.isEmpty();
-    }
-
-    public List<T> getList(){
-        return stack;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/el/parse/Block.java b/android/sdk/src/main/java/com/taobao/weex/el/parse/Block.java
deleted file mode 100644
index 6c3e29a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/el/parse/Block.java
+++ /dev/null
@@ -1,71 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.el.parse;
-
-import com.alibaba.fastjson.JSONArray;
-
-import java.util.List;
-
-/**
- * block, has more than one tokens, but only first will be execute.
- * Created by jianbai.gbj on 2017/8/28.
- */
-class Block extends Token {
-    private List<Token> tokens;
-    public Block(List<Token> tokens,  int type) {
-        super("", type);
-        this.tokens = tokens;
-    }
-
-    @Override
-    public Object execute(Object context){
-        if(getType() == TYPE_ARRAY){
-            if(tokens == null || tokens.size() == 0){
-                return  new JSONArray(4);
-            }
-            JSONArray arrayList = new JSONArray(tokens.size());
-            for(int i=0; i<tokens.size(); i++){
-                Token token = tokens.get(i);
-                if(token == null){
-                    arrayList.add(null);
-                }else{
-                    arrayList.add(token.execute(context));
-                }
-            }
-            return arrayList;
-        }
-        if(tokens == null || tokens.size() == 0){
-            return  null;
-        }
-        Token token = tokens.get(0);
-        return token.execute(context);
-    }
-
-    @Override
-    public String toString() {
-        if(getType() == TYPE_ARRAY){
-            return "" + tokens + "";
-        }else {
-            if(tokens != null && tokens.size() == 1){
-                return "{" + tokens.get(0) + '}';
-            }
-            return "{" + tokens + '}';
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/el/parse/Operator.java b/android/sdk/src/main/java/com/taobao/weex/el/parse/Operator.java
deleted file mode 100644
index d597be8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/el/parse/Operator.java
+++ /dev/null
@@ -1,106 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.el.parse;
-
-
-/**
- * Created by jianbai.gbj on 2017/8/28.
- * one operator, two operator, and three operator
- */
-class Operator extends Token {
-    public Token self;
-    public Token first;
-    public Token second;
-
-    public Operator(String operator, int type) {
-        super(operator, type);
-    }
-
-
-    @Override
-    public Object execute(Object context){
-        String op = getToken();
-        switch (op){
-            case  Operators.DOT_STR:
-            case  Operators.ARRAY_START_STR:{
-                return  Operators.dot(first, second, context);
-            }
-            case  Operators.EQUAL:
-            case  Operators.EQUAL2:{
-                return Operators.isEquals(first, second, context);
-            }
-            case  Operators.NOT_EQUAL:
-            case  Operators.NOT_EQUAL2:{
-                return !Operators.isEquals(first, second, context);
-            }
-            case  Operators.CONDITION_IF_STRING:{
-                return Operators.condition(self, first, second, context);
-            }
-            case  Operators.AND_NOT:{
-                return  !Operators.tokenTrue(self, context);
-            }
-            case  Operators.AND:{
-                return  Operators.tokenTrue(first, context) && Operators.tokenTrue(second, context);
-            }
-            case  Operators.OR:{
-                return  Operators.tokenTrue(first, context) || Operators.tokenTrue(second, context);
-            }
-            case  Operators.G:{
-                return  Operators.tokenNumber(first, context) > Operators.tokenNumber(second, context);
-            }
-            case  Operators.GE:{
-                return  Operators.tokenNumber(first, context) >= Operators.tokenNumber(second, context);
-            }
-            case  Operators.L:{
-                return  Operators.tokenNumber(first, context) < Operators.tokenNumber(second, context);
-            }
-            case  Operators.LE:{
-                return  Operators.tokenNumber(first, context) <= Operators.tokenNumber(second, context);
-            }
-            case  Operators.PLUS:{
-                return  Operators.plus(first, second, context);
-            }
-            case  Operators.SUB:{
-                return  Operators.sub(first, second, context);
-            }
-            case  Operators.MUL:{
-                return  Operators.mul(first, second, context);
-            }
-            case  Operators.DIV:{
-                return  Operators.div(first, second, context);
-            }
-            case  Operators.MOD:{
-                return  Operators.mod(first, second, context);
-            }
-            default:
-                throw new IllegalArgumentException(op + " operator is not supported");
-        }
-    }
-
-    @Override
-    public String toString() {
-        if(Operators.AND_NOT.equals(getToken())){
-            return "{!" +  self + "}";
-        }
-        if(self == null){
-            return "{" + first +  getToken() + second + "}";
-        }
-        return "{" + self + getToken() + first + ":" + second + "}";
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/el/parse/Operators.java b/android/sdk/src/main/java/com/taobao/weex/el/parse/Operators.java
deleted file mode 100644
index d0bcb7e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/el/parse/Operators.java
+++ /dev/null
@@ -1,502 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.el.parse;
-
-import java.lang.reflect.Array;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Stack;
-
-/**
- * Created by furture on 2017/8/28.
- */
-public class Operators {
-
-
-    public static Object dot(Token left, Token right, Object context){
-        if(left == null || right == null){
-            return null;
-        }
-        Object leftValue = left.execute(context);
-        if(leftValue == null){
-            return null;
-        }
-        Object value =  null;
-        if(right.getType() != Token.TYPE_IDENTIFIER){
-            Object identifter = right.execute(context);
-            if(identifter instanceof Double){
-                identifter = ((Double) identifter).intValue();
-            }
-            String key = identifter == null ? "" : identifter.toString().trim();
-            value = Operators.el(leftValue, key);
-        }else{
-            value = right.execute(leftValue);
-        }
-        if(value != null){
-            return value;
-        }
-        return  specialKey(leftValue, right.getToken());
-    }
-
-    /**
-     * get key's value on object
-     * */
-    public static  Object el(Object context, String key){
-        if(context == null){
-            return  null;
-        }
-        // TODO
-//        if(context instanceof CellRenderContext){
-//            if(WXEnvironment.isApkDebugable()){
-//                throw new IllegalArgumentException("rong context CellRenderContext, you should pass it's stack");
-//            }
-//            context = ((CellRenderContext) context).stack;
-//        }
-        if(context instanceof ArrayStack){
-            ArrayStack stack = (ArrayStack) context;
-            for(int index=stack.size()-1; index >= 0; index--){
-                Object value = stack.get(index);
-                if(value instanceof  Map){
-                    Map map = (Map) value;
-                    if(map.containsKey(key)){
-                        return map.get(key);
-                    }
-                }
-            }
-        }
-        if(context instanceof Stack){
-            Stack stack = (Stack) context;
-            for(int index=stack.size()-1; index >= 0; index--){
-                Object value = stack.get(index);
-                if(value instanceof  Map){
-                    Map map = (Map) value;
-                    if(map.containsKey(key)){
-                        return map.get(key);
-                    }
-                }
-            }
-        }
-
-        if(context instanceof  Map){
-            return ((Map) context).get(key);
-        }
-
-        if(context instanceof List){
-            List list = (List) context;
-            try{
-                return list.get(Integer.parseInt(key));
-            }catch (Exception e){}
-        }
-        if(context.getClass().isArray()){
-            try{
-                return Array.get(context, Integer.parseInt(key));
-            }catch (Exception e){}
-        }
-        return  null;
-    }
-
-    public static  Object specialKey(Object leftValue, String key){
-        if("length".equals(key)){
-            if(leftValue instanceof  CharSequence){
-                return ((CharSequence) leftValue).length();
-            }
-            if(leftValue instanceof  Map){
-                return  ((Map) leftValue).size();
-            }
-            if(leftValue instanceof  Map){
-                return  ((Map) leftValue).size();
-            }
-            if(leftValue instanceof  List){
-                return  ((List) leftValue).size();
-            }
-            if(leftValue.getClass().isArray()){
-                return Array.getLength(leftValue);
-            }
-        }
-        return null;
-    }
-
-    public static Object plus(Token left, Token right, Object context){
-        Object leftValue = null;
-        Object rightValue = null;
-        if(left != null){
-            leftValue = left.execute(context);
-        }
-        if(right  != null){
-            rightValue = right.execute(context);
-        }
-        if(leftValue instanceof  CharSequence || rightValue instanceof  CharSequence){
-            if(leftValue == null){
-                return  rightValue;
-            }
-            return leftValue.toString() + (rightValue == null ? "" : rightValue.toString());
-        }
-        if(leftValue instanceof  Number || rightValue instanceof Number){
-            return getNumber(leftValue) + getNumber(rightValue);
-        }
-        if(leftValue == null && rightValue == null){
-            return  null;
-        }
-        if(leftValue == null){
-            return  rightValue.toString();
-        }
-        return leftValue.toString() + (rightValue == null ? "" : rightValue.toString());
-    }
-
-
-    public static Object sub(Token left, Token right, Object context){
-        Object leftValue = null;
-        Object rightValue = null;
-        if(left != null){
-            leftValue = left.execute(context);
-        }
-        if(right  != null){
-            rightValue = right.execute(context);
-        }
-        return getNumber(leftValue) - getNumber(rightValue);
-    }
-
-    public static Object div(Token left, Token right, Object context){
-        Object leftValue = null;
-        Object rightValue = null;
-        if(left != null){
-            leftValue = left.execute(context);
-        }
-        if(right  != null){
-            rightValue = right.execute(context);
-        }
-        return getNumber(leftValue)/getNumber(rightValue);
-    }
-
-    public static Object mul(Token left, Token right, Object context){
-        Object leftValue = null;
-        Object rightValue = null;
-        if(left != null){
-            leftValue = left.execute(context);
-        }
-        if(right  != null){
-            rightValue = right.execute(context);
-        }
-        return getNumber(leftValue)*getNumber(rightValue);
-    }
-
-    public static Object mod(Token left, Token right, Object context){
-        Object leftValue = null;
-        Object rightValue = null;
-        if(left != null){
-            leftValue = left.execute(context);
-        }
-        if(right  != null){
-            rightValue = right.execute(context);
-        }
-        return (getNumber(leftValue))%(getNumber(rightValue));
-    }
-
-    /**
-     * condition expression
-     * */
-    public static Object condition(Token selfs, Token first, Token second, Object context){
-        boolean value = false;
-        if(selfs != null){
-            value = isTrue(selfs.execute(context));
-        }
-        if(value){
-            if(first != null){
-                return  first.execute(context);
-            }
-        }else{
-            if(second != null){
-                return  second.execute(context);
-            }
-        }
-        return null;
-    }
-
-
-    /**
-     * is token value is true
-     * */
-    public static boolean tokenTrue(Token selfs, Object context) {
-        if(selfs == null){
-            return false;
-        }
-        Object value = selfs.execute(context);
-        return  isTrue(value);
-    }
-
-    /**
-     * get token number
-     * */
-    public static double tokenNumber(Token self,  Object context) {
-        if(self == null){
-            return  0;
-        }
-        Object value = self.execute(context);
-        return  getNumber(value);
-    }
-
-
-
-    /**
-     * isEquls operation
-     * */
-    public static boolean isEquals(Token left, Token right, Object context){
-        if(left == null && right == null){
-            return  true;
-        }
-        Object leftValue =  null;
-        if(left != null){
-            leftValue  = left.execute(context);
-        }
-        Object rightValue = null;
-        if(right != null) {
-            rightValue = right.execute(context);
-        }
-        if(leftValue == null){
-            if(rightValue == null){
-                return  true;
-            }
-            if(rightValue instanceof  CharSequence){
-                if(isEmpty(rightValue.toString())){
-                    return  true;
-                }
-            }
-            return  false;
-        }
-        if(rightValue == null){
-            if(isEmpty(leftValue.toString())){
-                return  true;
-            }
-            return  false;
-        }
-        if(leftValue instanceof  Number){
-            if(rightValue instanceof  Number){
-                return  ((Number) leftValue).doubleValue() == ((Number) rightValue).doubleValue();
-            }
-            return ((Number) leftValue).doubleValue() == getNumber(rightValue);
-        }
-        if(rightValue instanceof  Number){
-            return getNumber(leftValue) == ((Number) rightValue).doubleValue();
-        }
-        if(leftValue instanceof CharSequence
-                ||  rightValue instanceof CharSequence){
-            return  leftValue.toString().trim().equals(rightValue.toString().trim());
-        }
-        return  leftValue.equals(rightValue);
-    }
-
-
-    /**
-     * check whether value is true
-     * */
-    public static boolean isTrue(Object value){
-        if(value == null){
-            return  false;
-        }
-        if(value instanceof  Number){
-            return ((Number) value).doubleValue() != 0;
-        }
-        String bool = value.toString().trim();
-        if("false".equals(bool)
-                || "undefined".equals(bool)
-                || "null".equals(bool)){
-            return  false;
-        }
-        if(isEmpty(bool)){
-            return  false;
-        }
-        return  true;
-    }
-
-    /**
-     * check String value is empty
-     * */
-    public static boolean isEmpty(String value){
-        if (value == null){
-            return  true;
-        }
-        for(int i=0; i<value.length(); i++){
-            if(value.charAt(i) != ' '){
-                return  false;
-            }
-        }
-        return true;
-    }
-
-
-    /**
-     * get number
-     * */
-    public static double getNumber(Object value){
-        if(value == null){
-            return  0;
-        }
-        if(value instanceof  Number){
-            return  ((Number) value).doubleValue();
-        }
-        try{
-            return Double.parseDouble(value.toString());
-        }catch (Exception e){return  0;}
-    }
-
-    public static boolean isOpEnd(String op){
-        return isOpEnd(op.charAt(0));
-    }
-    /**
-     * op end, has none operation, should not enter operator stack.
-     * */
-    public static boolean isOpEnd(char op){
-        if(op == BRACKET_END
-                || op == ARRAY_END
-                || op == SPACE
-                || op == ARRAY_SEPRATOR){
-            return true;
-        }
-        return  false;
-    }
-
-    /**
-     * is not
-     * */
-    public static boolean isDot(String opStr){
-        char op = opStr.charAt(0);
-        return  op == DOT || op == ARRAY_START;
-    }
-
-
-
-
-    public static final char BRACKET_END = ')';
-    public static final String BRACKET_END_STR = ")";
-    public static final char BRACKET_START = '(';
-    public static final String BRACKET_START_STR = "(";
-    public static final char QUOTE = '"';
-    public static final char SINGLE_QUOTE = '\'';
-    public static final char DOT = '.';
-    public static final String DOT_STR = ".";
-    public static final char ARRAY_START = '[';
-    public static final String ARRAY_START_STR = "[";
-    public static final char ARRAY_SEPRATOR = ',';
-    public static final String ARRAY_SEPRATOR_STR = ",";
-    public static final char ARRAY_END = ']';
-    public static final String ARRAY_END_STR = "]";
-    public static final String SPACE_STR = " ";
-    public static final char SPACE = ' ';
-    public static final char BLOCK_START = '{';
-    public static final String BLOCK_START_STR = "{";
-    public static final char BLOCK_END = '}';
-    public static final String BLOCK_END_STR = "}";
-    public static final char DOLLAR = '$';
-    public static final String DOLLAR_STR = "$";
-
-    /**
-     * condition
-     * */
-    public static final char  CONDITION_IF = '?';
-    public static final String  CONDITION_IF_STRING = "?";
-    public static final char  CONDITION_IF_MIDDLE = ':';
-
-
-
-    /**
-     * match
-     * */
-    public static final String PLUS ="+";
-    public static final String SUB = "-";
-    public static final String MUL = "*";
-    public static final String DIV = "/";
-    public static final String MOD = "%";
-
-
-
-    public static final String AND  = "&&";
-    public static final String OR  = "||";
-    /**
-     * and operator
-     * */
-    public static final String EQUAL = "===";
-    public static final String EQUAL2 = "==";
-    public static final String NOT_EQUAL = "!==";
-    public static final String NOT_EQUAL2 = "!=";
-    public static final String AND_NOT = "!";
-
-
-    public static final String G = ">";
-    public static final String GE = ">=";
-    public static final String LE = "<=";
-    public static final String L = "<";
-
-
-
-
-
-    /**
-     * https://github.com/jquery/esprima/blob/master/src/parser.ts
-     * */
-    public static Map<String, Integer> OPERATORS_PRIORITY = new HashMap<>();
-    static {
-        OPERATORS_PRIORITY.put(BLOCK_END_STR, 0);
-        OPERATORS_PRIORITY.put(BRACKET_END_STR, 0);
-        OPERATORS_PRIORITY.put(SPACE_STR, 0);
-        OPERATORS_PRIORITY.put(ARRAY_SEPRATOR_STR, 0);
-        OPERATORS_PRIORITY.put(ARRAY_END_STR, 0);
-
-
-        OPERATORS_PRIORITY.put(OR, 1);
-        OPERATORS_PRIORITY.put(AND, 1);
-
-        OPERATORS_PRIORITY.put(EQUAL, 2);
-        OPERATORS_PRIORITY.put(EQUAL2, 2);
-        OPERATORS_PRIORITY.put(NOT_EQUAL, 2);
-        OPERATORS_PRIORITY.put(NOT_EQUAL2, 2);
-
-        OPERATORS_PRIORITY.put(G, 7);
-        OPERATORS_PRIORITY.put(GE, 7);
-        OPERATORS_PRIORITY.put(L, 7);
-        OPERATORS_PRIORITY.put(LE, 8);
-
-        OPERATORS_PRIORITY.put(PLUS, 9);
-        OPERATORS_PRIORITY.put(SUB, 9);
-        OPERATORS_PRIORITY.put(MUL, 10);
-        OPERATORS_PRIORITY.put(DIV, 10);
-        OPERATORS_PRIORITY.put(MOD, 10);
-        OPERATORS_PRIORITY.put(AND_NOT, 11);
-
-        OPERATORS_PRIORITY.put(DOT_STR, 15);
-        
-        OPERATORS_PRIORITY.put(ARRAY_START_STR, 16);
-
-
-        OPERATORS_PRIORITY.put(BRACKET_START_STR, 17);
-        OPERATORS_PRIORITY.put(BLOCK_START_STR, 17);
-
-
-    }
-
-
-    public static final Map<String,Object> KEYWORDS = new HashMap<>();
-    static {
-        KEYWORDS.put("null", null);
-        KEYWORDS.put("true", Boolean.TRUE);
-        KEYWORDS.put("false", Boolean.FALSE);
-        KEYWORDS.put("undefined", null);
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/el/parse/Parser.java b/android/sdk/src/main/java/com/taobao/weex/el/parse/Parser.java
deleted file mode 100644
index 6609e3f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/el/parse/Parser.java
+++ /dev/null
@@ -1,486 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.el.parse;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.ArrayList;
-import java.util.List;
-
-
-/**
- * Created by furture on 2017/8/28.
- * simple expression parse, less ast node and save memory
- */
-public class Parser {
-
-    private String code;
-    private int position;
-    private ArrayStack<Token> stacks;
-    private ArrayStack<Symbol> operators;
-
-    public Parser(String code){
-        this.code = code;
-        this.position = 0;
-        this.stacks = new ArrayStack<>();
-        this.operators = new ArrayStack<>();
-    }
-
-
-    public final Token parse(){
-        while (hasNextToken()){
-            scanNextToken();
-        }
-        while (!operators.isEmpty()){
-            Symbol op = operators.pop();
-            doOperator(op);
-        }
-        if(stacks.size() == 1){
-            return  stacks.pop();
-        }
-        Block block = new Block(stacks.getList(), Token.TYPE_BLOCK);
-        return block;
-    }
-
-
-    /**
-     * parse code to ast block.
-     * */
-    public static Token parse(String code){
-        try{
-            Parser parser = new Parser(code);
-            return parser.parse();
-        }catch (Exception e){
-            if(WXEnvironment.isApkDebugable()){
-                WXLogUtils.e("code " + code, e);
-            }
-            return new Block(null, Token.TYPE_BLOCK);
-        }
-    }
-
-
-    final char scanNextToken(){
-        char ch = nextToken();
-        if(ch == Operators.DOLLAR){
-            position++;
-            return ch;
-        }else if(Character.isJavaIdentifierStart(ch)){
-            scanIdentifier();
-        }else if (ch == Operators.BRACKET_START || ch == Operators.BLOCK_START) {
-            scanBracket();
-        }else if (ch == Operators.ARRAY_START) {
-            scanArray();
-        }else if (ch ==  Operators.QUOTE || ch == Operators.SINGLE_QUOTE) {
-            scanString();
-        }else if((ch == Operators.DOT && Character.isDigit(code.charAt(position + 1)))
-                || Character.isDigit(ch)){ //number .00 .00e6
-            scanNumber();
-        }else if(ch ==  Operators.CONDITION_IF){
-            scanIf();
-        }else if(ch ==  Operators.CONDITION_IF_MIDDLE
-                || ch ==  Operators.BRACKET_END
-                || ch == Operators.BLOCK_END
-                || ch == Operators.SPACE
-                || ch == Operators.ARRAY_END){
-            position++;
-            return ch;
-        }else{
-            scanOperator();
-        }
-        return ch;
-    }
-
-
-    final void  scanArray(){
-        int stackSize = stacks.size();
-        int opSize = operators.size();
-        int type = Token.TYPE_IDENTIFIER;
-        if(position - 1 < 0 || !Character.isJavaIdentifierPart(code.charAt(position - 1))){
-            type = Token.TYPE_ARRAY;
-        }
-        operators.push(new Symbol(Operators.ARRAY_START_STR, stacks.size()));
-        position++;
-        while (hasNextToken()){
-            char token = scanNextToken();
-            if(token == Operators.ARRAY_END){
-                break;
-            }
-        }
-
-        if(stacks.size() <= stackSize){ // empty bracket, none need, save memory
-            while (operators.size() > opSize){
-                operators.pop();
-            }
-            return;
-        }
-
-        while (operators.size() > opSize){
-            Symbol op = operators.pop();
-            if(stacks.size() > stackSize){
-                doOperator(op);
-            }
-        }
-        List<Token> tokens = new ArrayList<>(4);
-        for(int i=stackSize; i<stacks.size(); i++){
-            tokens.add(stacks.get(i));
-        }
-        while (stacks.size() > stackSize){
-            stacks.pop();
-        }
-        if(type == Token.TYPE_ARRAY || stacks.size() == 0){
-            Block block = new Block(tokens, Token.TYPE_ARRAY);
-            stacks.push(block);
-            return;
-        }
-
-        Token identifer = stacks.pop();
-        Token second = null;
-        if(tokens.size() == 1){
-            second = tokens.get(0);
-        }else{
-            second = new Block(tokens, Token.TYPE_BLOCK);
-        }
-        Operator operator = new Operator(Operators.DOT_STR, type);
-        operator.first = identifer;
-        operator.second = second;
-        stacks.push(operator);
-    }
-
-    void  scanBracket(){
-        int stackSize = stacks.size();
-        int opSize = operators.size();
-        if(code.charAt(position) == Operators.BLOCK_START){
-            operators.push(new Symbol(Operators.BLOCK_START_STR, stacks.size()));
-            position++;
-            while (hasNextToken()){
-                if(scanNextToken() == Operators.BLOCK_END){
-                    break;
-                }
-            }
-        }else{
-            operators.push(new Symbol(Operators.BRACKET_START_STR, stacks.size()));
-            position++;
-            while (hasNextToken()){
-                if(scanNextToken() == Operators.BRACKET_END){
-                    break;
-                }
-            }
-        }
-        if(stacks.size() <= stackSize){ // empty bracket, none need, save memory
-            while (operators.size() > opSize){
-                operators.pop();
-            }
-            return;
-        }
-        while (operators.size() > opSize){
-            Symbol op = operators.pop();
-            if(stacks.size() > stackSize){
-                doOperator(op);
-            }
-        }
-        List<Token> tokens = new ArrayList<>(4);
-        for(int i=stackSize; i<stacks.size(); i++){
-            tokens.add(stacks.get(i));
-        }
-        while (stacks.size() > stackSize){
-            stacks.pop();
-        }
-        if(tokens.size() == 1){
-            stacks.push(tokens.get(0));
-        }else{
-            Block block = new Block(tokens, Token.TYPE_BLOCK);
-            stacks.push(block);
-        }
-    }
-
-    /**
-     * 1  === (1 + 3) &&  1
-     * scan operator
-     * */
-    void scanOperator(){
-        int start = position;
-        int length = Math.min(position + 3, code.length());
-        String operator = code.substring(position, length);
-        if(operator.length() >= 3){
-            if(!Operators.OPERATORS_PRIORITY.containsKey(operator)){
-                operator = operator.substring(0, 2);
-            }
-        }
-        if(operator.length() >= 2){
-            if(!Operators.OPERATORS_PRIORITY.containsKey(operator)){
-                operator = operator.substring(0, 1);
-            }
-        }
-        if(!Operators.OPERATORS_PRIORITY.containsKey(operator)){
-            //just skip illegal character
-            int illegalChar = Math.min(start + 1, code.length());
-            WXLogUtils.e("weex", new IllegalArgumentException(code.substring(0, illegalChar) + " illegal code operator" + operator));
-            position += operator.length();
-            return;
-        }
-        if((!operators.isEmpty() && operators.peek() != null)){
-            String preOp = operators.peek().op;
-            if(Operators.OPERATORS_PRIORITY.get(preOp) >= Operators.OPERATORS_PRIORITY.get(operator)){
-                Symbol op = operators.pop();
-                doOperator(op);
-            }
-        }
-        if(!Operators.isOpEnd(operator)){
-            operators.push(new Symbol(operator, stacks.size()));
-        }
-        position += operator.length();
-    }
-
-
-
-    void doOperator(Symbol symbol){
-        String op = symbol.op;
-        if(Operators.BRACKET_START_STR.equals(symbol.op)
-                || Operators.BLOCK_START_STR.equals(symbol.op)
-                || Operators.ARRAY_START_STR.equals(symbol.op)
-                || Operators.DOLLAR_STR.equals(symbol.op)){
-            return;
-        }
-        if(Operators.BLOCK_START_STR.equals(symbol.op)){
-            return;
-        }
-        int second = symbol.pos;
-        int first  = Math.max(symbol.pos - 1, 0);
-        if(!operators.isEmpty()){
-            first = Math.max(first, operators.peek().pos);
-        }
-
-        Operator operator = new Operator(op, Token.TYPE_OPERATOR);
-        if(Operators.AND_NOT.equals(op)){
-            if(stacks.size() > second) {
-                Token token = stacks.remove(second);
-                operator.self = token;
-                stacks.add(second, operator);
-                return;
-            }
-            return; //invalid
-        }
-        if(stacks.size() > second) {
-            operator.second = stacks.remove(second);
-        }else{
-            return;
-        }
-        if(stacks.size() > first) {
-            operator.first = stacks.remove(first);
-        }else{
-            if(operator.second == null){
-                return;
-            }
-        }
-        stacks.add(first, operator);
-    }
-
-    /**
-     * condition if
-     * */
-    void scanIf(){
-        Operator operator = new Operator(Operators.CONDITION_IF_STRING, Token.TYPE_OPERATOR);
-        int selfIndex = 0;
-        doStackOperators(0);
-        if(operators.size() > 0){
-            selfIndex = Math.max(operators.peek().pos, selfIndex);
-        }
-        if(stacks.size() > selfIndex){
-            operator.self = stacks.pop();
-        }
-
-        int stackSize = stacks.size();
-        int leftOperatorSize = operators.size();
-        position++;
-        while (hasNextToken()){
-            if(scanNextToken() == Operators.CONDITION_IF_MIDDLE){
-                break;
-            }
-        }
-        while (operators.size() > leftOperatorSize){
-            Symbol symbol = operators.pop();
-            doOperator(symbol);
-        }
-
-        while (stacks.size() > stackSize){
-            operator.first = stacks.pop();
-        }
-        int rightOperatorsSize = operators.size();
-        while (hasNextToken()){
-            scanNextToken();
-            if(hasNextToken()){
-                scanNextToken();
-            }
-            if(operators.size() <= rightOperatorsSize){
-                break;
-            }
-        }
-        doStackOperators(rightOperatorsSize);
-        while (stacks.size() > stackSize){
-            operator.second = stacks.pop();
-        }
-        stacks.push(operator);
-    }
-
-    private final void doStackOperators(int operatorSize){
-        while (operators.size() > operatorSize){
-            Symbol symbol = operators.pop();
-            doOperator(symbol);
-        }
-    }
-
-    /**
-     * 1+e6
-     * .00
-     * .00e6
-     * 100
-     * 199e5
-     * */
-    final void scanNumber(){
-        boolean isInt = true;
-        int start = position;
-        if(code.charAt(position) == 'e' || code.charAt(position) == '.'){
-            isInt = false;
-        }
-        position++;
-        while (hasNext()){
-            char ch = code.charAt(position);
-            if(Character.isDigit(ch)
-                    || ch == '.'
-                    || ch =='e'){
-                if(ch == 'e'
-                        || ch == '.'){
-                    isInt = false;
-                }
-                position++;
-            }else{
-                break;
-            }
-        }
-        String number = code.substring(start, position);
-        if(".".equals(number)){
-            return;
-        }
-        Token stack = null;
-        if(isInt){
-            stack = new Token(number, Token.TYPE_INT);
-        }else{
-            stack = new Token(number, Token.TYPE_DOUBLE);
-        }
-        stacks.push(stack);
-    }
-
-
-    final void  scanString(){
-        int start = position;
-        ArrayStack operator = new ArrayStack();
-        char quote = code.charAt(start);
-        operator.push(quote);
-        StringBuilder builder = new StringBuilder();
-        for(position= start + 1; position<code.length(); position++){
-            char ch = code.charAt(position);
-            if(ch == quote){
-                if(code.charAt(position -1) != '\\'){
-                    operator.pop();
-                    if(operator.size() == 0){
-                       position++;
-                       break;
-                    }
-                }else{
-                    builder.deleteCharAt(builder.length()-1);
-                    builder.append(ch);
-                }
-            }else{
-                builder.append(ch);
-            }
-        }
-        String string =  builder.toString();
-        Token token = new Token(string, Token.TYPE_STRING);
-        stacks.push(token);
-    }
-
-
-
-    /**
-     * scan el expression.
-     * item.ddd
-     * ${item.dd}
-     * $item.dd
-     * */
-    final void scanIdentifier(){
-        int start = position;
-        position++;
-        while (hasNext()){
-            char ch = code.charAt(position);
-            if(Character.isJavaIdentifierPart(ch)){
-               position++;
-            }else{
-                break;
-            }
-            //2.true
-        }
-        String el = code.substring(start, position);
-        if(el.startsWith(Operators.DOLLAR_STR)){
-            if(el.length() == Operators.DOLLAR_STR.length()){
-                return;
-            }
-            el = el.substring(Operators.DOLLAR_STR.length());
-        }
-        int type = Token.TYPE_IDENTIFIER;
-        if(Operators.KEYWORDS.containsKey(el)){
-            if(!(!operators.isEmpty() && Operators.isDot(operators.peek().op))){
-                type = Token.TYPE_KEYWORD;
-            }
-        }
-        Token token = new Token(el, type);
-        stacks.push(token);
-    }
-
-
-    final boolean hasNext(){
-        return position < code.length();
-    }
-
-
-
-    final boolean hasNextToken(){
-        while (hasNext()){
-            char ch = code.charAt(position);
-            if(ch == ' '){
-                position++;
-                continue;
-            }
-            return  true;
-        }
-        return false;
-    }
-
-    final char nextToken(){
-        char ch = code.charAt(position);
-        while (ch == ' '){
-            position ++;
-            if(code.length() <= position){
-                break;
-            }
-            ch = code.charAt(position);
-        }
-        return ch;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/el/parse/Symbol.java b/android/sdk/src/main/java/com/taobao/weex/el/parse/Symbol.java
deleted file mode 100644
index e42aa78..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/el/parse/Symbol.java
+++ /dev/null
@@ -1,38 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.el.parse;
-
-/**
- * Created by furture on 2017/8/29.
- */
-
-public class Symbol {
-    public final String op;
-    public final int pos;
-    public Symbol(String op, int pos) {
-        this.op = op;
-        this.pos = pos;
-    }
-
-    /**
-    @Override
-    public String toString() {
-        return op;
-    }*/
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/el/parse/Token.java b/android/sdk/src/main/java/com/taobao/weex/el/parse/Token.java
deleted file mode 100644
index 44f9135..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/el/parse/Token.java
+++ /dev/null
@@ -1,89 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.el.parse;
-
-/**
- * Created by furture on 2017/8/28.
- */
-public class Token {
-
-    /**
-     * token's type
-     * */
-    public static final int TYPE_IDENTIFIER = 0;
-    public static final int TYPE_INT = 1;
-    public static final int TYPE_DOUBLE = 2;
-    public static final int TYPE_STRING = 3;
-    public static final int TYPE_KEYWORD = 4;
-    public static final int TYPE_OPERATOR = 5;
-    public static final int TYPE_BLOCK = 6;
-
-    public static final int TYPE_ARRAY = 7;
-
-
-
-    private String token;
-    private int type;
-
-    public Token(String token, int type){
-        this.token = token;
-        this.type = type;
-    }
-
-
-    /**
-     * stack should use array stack.
-     * execute token in context, and return value.
-     * */
-    public Object execute(Object context){
-        if(type == TYPE_IDENTIFIER){
-            return Operators.el(context, token);
-        }else if(type == TYPE_STRING){
-            return  token;
-        }else if(type == TYPE_INT){
-            try{
-                return  Integer.parseInt(token);
-            }catch (Exception e){
-                return 0;
-            }
-        }else if(type == TYPE_DOUBLE){
-            try{
-                return  Double.parseDouble(token);
-            }catch (Exception e){
-                return 0;
-            }
-        }else if(type == TYPE_KEYWORD){
-            return  Operators.KEYWORDS.get(token);
-        }
-        throw new IllegalArgumentException("unhandled token type " + type);
-    }
-
-    @Override
-    public String toString() {
-        return "{" + token + "," + type + '}';
-    }
-
-    public String getToken() {
-        return token;
-    }
-
-    public int getType() {
-        return type;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/font/FontAdapter.java b/android/sdk/src/main/java/com/taobao/weex/font/FontAdapter.java
deleted file mode 100644
index 4556a39..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/font/FontAdapter.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.font;
-
-import java.util.List;
-import java.util.concurrent.CopyOnWriteArrayList;
-
-public class FontAdapter {
-
-
-    private List<FontListener> mFontListener;
-
-    public FontAdapter(){
-        mFontListener = new CopyOnWriteArrayList<>();
-    }
-
-    public void addFontListener(FontListener fontListener){
-        mFontListener.add(fontListener);
-    }
-
-    public void removeFontListener(FontListener fontListener){
-        mFontListener.remove(fontListener);
-    }
-
-    public void onAddFontRule(String pageId, String fontFamily, String fontUrl){
-        synchronized (this){
-            for(FontListener fontListener : mFontListener){
-                fontListener.onAddFontRule(pageId, fontFamily, fontUrl);
-            }
-        }
-    }
-
-    public void onFontLoad(String fontFaimly, String fontUrl, String filePath){
-        synchronized (this) {
-            for (FontListener fontListener : mFontListener) {
-                fontListener.onFontLoad(fontFaimly, fontUrl, filePath);
-            }
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/font/FontListener.java b/android/sdk/src/main/java/com/taobao/weex/font/FontListener.java
deleted file mode 100644
index e6d70a5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/font/FontListener.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.font;
-
-public interface FontListener {
-
-    public void onAddFontRule(String pageId, String fontFamily, String fontUrl);
-
-    public void onFontLoad(String fontFamily, String fontUrl, String filePath);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/http/Options.java b/android/sdk/src/main/java/com/taobao/weex/http/Options.java
deleted file mode 100644
index effb241..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/http/Options.java
+++ /dev/null
@@ -1,138 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.http;
-
-import java.util.HashMap;
-import java.util.Map;
-import com.taobao.weex.common.*;
-
-/**
- * Created by sospartan on 5/19/16.
- */
-class Options {
-  private String method;
-  private String url;
-  private Map<String, String> headers;
-  private String body;
-  private Type type = Type.text;
-  private int timeout = WXRequest.DEFAULT_TIMEOUT_MS;
-
-  private Options(String method,
-                  String url,
-                  Map<String, String> headers,
-                  String body,
-                  Type type,
-                  int timeout) {
-    this.method = method;
-    this.url = url;
-    this.headers = headers;
-    this.body = body;
-    this.type = type;
-    if (timeout == 0) {
-      timeout = WXRequest.DEFAULT_TIMEOUT_MS;
-    }
-    this.timeout = timeout;
-  }
-
-  public String getMethod() {
-    return method;
-  }
-
-  public String getUrl() {
-    return url;
-  }
-
-  public Map<String, String> getHeaders() {
-    return headers;
-  }
-
-  public String getBody() {
-    return body;
-  }
-
-  public Type getType() {
-    return type;
-  }
-
-  public int getTimeout() { return timeout; }
-
-  public enum Type {
-    json, text,jsonp
-  }
-
-  public static class Builder {
-    private String method;
-    private String url;
-    private Map<String, String> headers = new HashMap<>();
-    private String body;
-    private Type type;
-    private int timeout;
-
-    public Builder setMethod(String method) {
-      this.method = method;
-      return this;
-    }
-
-    public Builder setUrl(String url) {
-      this.url = url;
-      return this;
-    }
-
-    public Builder putHeader(String key,String value){
-      this.headers.put(key,value);
-      return this;
-    }
-
-    public Builder setBody(String body) {
-      this.body = body;
-      return this;
-    }
-
-    /**
-     * default text
-     * json = jsonp
-     * @param type
-     * @return
-       */
-    public Builder setType(String type) {
-      if(Type.json.name().equals(type)){
-        this.type = Type.json;
-      }else if(Type.jsonp.name().equals(type)){
-        this.type = Type.jsonp;
-      }else{
-        this.type = Type.text;
-      }
-      return this;
-    }
-
-    public Builder setType(Type type) {
-      this.type = type;
-      return this;
-    }
-
-    public Builder setTimeout(int timeout) {
-      this.timeout = timeout;
-      return this;
-    }
-
-    public Options createOptions() {
-      return new Options(method, url, headers, body, type, timeout);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/http/Status.java b/android/sdk/src/main/java/com/taobao/weex/http/Status.java
deleted file mode 100644
index 429f53f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/http/Status.java
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.http;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by sospartan on 5/26/16.
- */
-public class Status {
-  public static final String UNKNOWN_STATUS = "unknown status";
-  public static final String ERR_INVALID_REQUEST = "ERR_INVALID_REQUEST";
-  public static final String ERR_CONNECT_FAILED = "ERR_CONNECT_FAILED";
-
-  private static Map<String,String> statusMap = new HashMap<>();
-
-  static {
-    statusMap.put("100","Continue");
-    statusMap.put("101","Switching Protocol");
-    statusMap.put("200","OK");
-    statusMap.put("201","Created");
-    statusMap.put("202","Accepted");
-    statusMap.put("203","Non-Authoritative Information");
-    statusMap.put("204","No Content");
-    statusMap.put("205","Reset Content");
-    statusMap.put("206","Partial Content");
-    statusMap.put("300","Multiple Choice");
-    statusMap.put("301","Moved Permanently");
-    statusMap.put("302","Found");
-    statusMap.put("303","See Other");
-    statusMap.put("304","Not Modified");
-    statusMap.put("305","Use Proxy");
-    statusMap.put("306","unused");
-    statusMap.put("307","Temporary Redirect");
-    statusMap.put("308","Permanent Redirect");
-    statusMap.put("400","Bad Request");
-    statusMap.put("401","Unauthorized");
-    statusMap.put("402","Payment Required");
-    statusMap.put("403","Forbidden");
-    statusMap.put("404","Not Found");
-    statusMap.put("405","Method Not Allowed");
-    statusMap.put("406","Not Acceptable");
-    statusMap.put("407","Proxy Authentication Required");
-    statusMap.put("408","Request Timeout");
-    statusMap.put("409","Conflict");
-    statusMap.put("410","Gone");
-    statusMap.put("411","Length Required");
-    statusMap.put("412","Precondition Failed");
-    statusMap.put("413","Payload Too Large");
-    statusMap.put("414","URI Too Long");
-    statusMap.put("415","Unsupported Media Type");
-    statusMap.put("416","Requested Range Not Satisfiable");
-    statusMap.put("417","Expectation Failed");
-    statusMap.put("418","I'm a teapot");
-    statusMap.put("421","Misdirected Request");
-    statusMap.put("426","Upgrade Required");
-    statusMap.put("428","Precondition Required");
-    statusMap.put("429","Too Many Requests");
-    statusMap.put("431","Request Header Fields Too Large");
-    statusMap.put("500","Internal Server Error");
-    statusMap.put("501","Not Implemented");
-    statusMap.put("502","Bad Gateway");
-    statusMap.put("503","Service Unavailable");
-    statusMap.put("504","Gateway Timeout");
-    statusMap.put("505","HTTP Version Not Supported");
-    statusMap.put("506","Variant Also Negotiates");
-    statusMap.put("507","Variant Also Negotiates");
-    statusMap.put("511","Network Authentication Required");
-  }
-
-  public static String getStatusText(String code){
-    if(!statusMap.containsKey(code))
-      return UNKNOWN_STATUS;
-    return statusMap.get(code);
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/http/WXHttpUtil.java b/android/sdk/src/main/java/com/taobao/weex/http/WXHttpUtil.java
deleted file mode 100644
index 4f58841..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/http/WXHttpUtil.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.http;
-
-import android.content.Context;
-import android.text.TextUtils;
-
-import com.taobao.weex.common.WXConfig;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.Map;
-
-/**
- * Created by lixinke on 16/4/6.
- */
-public class WXHttpUtil {
-
-  private static String sDefaultUA = null;
-
-  public static final String KEY_USER_AGENT = "user-agent";
-
-  public static String assembleUserAgent(Context ctx,Map<String, String> config) {
-    if (TextUtils.isEmpty(sDefaultUA)) {
-      StringBuilder builder = new StringBuilder();
-      builder.append(config.get(WXConfig.sysModel))
-          .append("(Android/")
-          .append(config.get(WXConfig.sysVersion))
-          .append(")")
-          .append(" ")
-
-          .append(TextUtils.isEmpty(config.get(WXConfig.appGroup)) ? "" : config.get(WXConfig.appGroup))
-          .append("(")
-          .append(TextUtils.isEmpty(config.get(WXConfig.appName)) ? "" : config.get(WXConfig.appName))
-          .append("/")
-          .append(config.get(WXConfig.appVersion))
-          .append(")")
-          .append(" ")
-
-          .append("Weex/")
-          .append(config.get(WXConfig.weexVersion))
-          .append(" ")
-
-          .append(TextUtils.isEmpty(config.get(WXConfig.externalUserAgent)) ? "" : config.get(WXConfig.externalUserAgent))
-          .append(TextUtils.isEmpty(config.get(WXConfig.externalUserAgent)) ? "" : " ")
-
-          .append(WXViewUtils.getScreenWidth(ctx) + "x" + WXViewUtils.getScreenHeight(ctx));
-      sDefaultUA = builder.toString();
-    }
-    return sDefaultUA;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/http/WXStreamModule.java b/android/sdk/src/main/java/com/taobao/weex/http/WXStreamModule.java
deleted file mode 100644
index 3e8e9e5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/http/WXStreamModule.java
+++ /dev/null
@@ -1,382 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.http;
-
-import static com.taobao.weex.http.WXHttpUtil.KEY_USER_AGENT;
-
-import android.net.Uri;
-import android.text.TextUtils;
-
-import com.alibaba.fastjson.JSONException;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.common.WXRequest;
-import com.taobao.weex.common.WXResponse;
-import com.taobao.weex.performance.WXStateRecord;
-import com.taobao.weex.utils.WXLogUtils;
-import java.io.UnsupportedEncodingException;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Locale;
-import java.util.Map;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-
-public class WXStreamModule extends WXModule {
-
-  public static final String STATUS_TEXT = "statusText";
-  public static final String STATUS = "status";
-  final IWXHttpAdapter mAdapter;
-  static final Pattern CHARSET_PATTERN = Pattern.compile("charset=([a-z0-9-]+)");
-
-  public WXStreamModule(){
-    this(null);
-  }
-  public WXStreamModule(IWXHttpAdapter adapter){
-    mAdapter = adapter;
-  }
-
-  /**
-   * send HTTP request
-   *
-   * @param params   {method:POST/GET/PUT/DELETE/HEAD/PATCH,url:http://xxx,header:{key:value},
-   *                 body:{key:value}}
-   * @param callback formate：handler(err, response)
-   */
-  @Deprecated
-  @JSMethod(uiThread = false)
-  public void sendHttp(JSONObject paramsObj, final String callback) {
-
-    String method = paramsObj.getString("method");
-    String url = paramsObj.getString("url");
-    JSONObject headers = paramsObj.getJSONObject("header");
-    String body = paramsObj.getString("body");
-    int timeout = paramsObj.getIntValue("timeout");
-
-    if (method != null) method = method.toUpperCase(Locale.ROOT);
-    Options.Builder builder = new Options.Builder()
-            .setMethod(!"GET".equals(method)
-                    &&!"POST".equals(method)
-                    &&!"PUT".equals(method)
-                    &&!"DELETE".equals(method)
-                    &&!"HEAD".equals(method)
-                    &&!"PATCH".equals(method)?"GET":method)
-            .setUrl(url)
-            .setBody(body)
-            .setTimeout(timeout);
-
-    extractHeaders(headers,builder);
-    sendRequest(builder.createOptions(), new ResponseCallback() {
-      @Override
-      public void onResponse(WXResponse response, Map<String, String> headers) {
-        if(callback != null && mWXSDKInstance != null)
-          WXBridgeManager.getInstance().callback(mWXSDKInstance.getInstanceId(), callback,
-                  (response == null || response.originalData == null) ? "{}" :
-                          readAsString(response.originalData,
-                                  headers!=null?getHeader(headers,"Content-Type"):""
-                          ));
-      }
-    }, null, mWXSDKInstance.getInstanceId(), mWXSDKInstance.getBundleUrl());
-  }
-
-  /**
-   *
-   * @param optionsStr request options include:
-   *  method: GET 、POST、PUT、DELETE、HEAD、PATCH
-   *  headers：object，request header
-   *  url:
-   *  body: "Any body that you want to add to your request"
-   *  type: json、text、jsonp（json）
-   * @param callback finished callback,response object:
-   *  status：status code
-   *  ok：boolean is success，http status200～299
-   *  statusText： statusText
-   *  data:  option type is json，data is object，not data is string
-   *  headers: headers
-   *
-   * @param progressCallback in progress callback,for download progress and request state,response object:
-   *  readyState: number connection status 1 OPENED 2 HEADERS_RECEIVED 3 LOADING
-   *  status：status code
-   *  length：headers Content-Length
-   *  statusText：statusText
-   *  headers: headers
-   */
-  @JSMethod(uiThread = false)
-  public void fetch(JSONObject optionsObj , final JSCallback callback, JSCallback progressCallback){
-    fetch(optionsObj, callback, progressCallback, mWXSDKInstance.getInstanceId(), mWXSDKInstance.getBundleUrl());
-  }
-
-  public void fetch(JSONObject optionsObj , final JSCallback callback, JSCallback progressCallback, final String instanceId, String bundleURL){
-    boolean invaildOption = optionsObj==null || optionsObj.getString("url")==null;
-    if(invaildOption){
-      if(callback != null) {
-        Map<String, Object> resp = new HashMap<>();
-        resp.put("ok", false);
-        resp.put(STATUS_TEXT, Status.ERR_INVALID_REQUEST);
-        callback.invoke(resp);
-      }
-      return;
-    }
-    String method = optionsObj.getString("method");
-    String url = optionsObj.getString("url");
-    JSONObject headers = optionsObj.getJSONObject("headers");
-    String body = optionsObj.getString("body");
-    String type = optionsObj.getString("type");
-    int timeout = optionsObj.getIntValue("timeout");
-
-    WXSDKInstance wxsdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (wxsdkInstance != null) {
-      if (wxsdkInstance.getStreamNetworkHandler() != null) {
-        String localUrl = wxsdkInstance.getStreamNetworkHandler().fetchLocal(url);
-        if (!TextUtils.isEmpty(localUrl)) {
-          url = localUrl;
-        }
-      }
-    }
-
-    if (method != null) method = method.toUpperCase(Locale.ROOT);
-    Options.Builder builder = new Options.Builder()
-        .setMethod(!"GET".equals(method)
-            &&!"POST".equals(method)
-            &&!"PUT".equals(method)
-            &&!"DELETE".equals(method)
-            &&!"HEAD".equals(method)
-            &&!"PATCH".equals(method)?"GET":method)
-        .setUrl(url)
-        .setBody(body)
-        .setType(type)
-        .setTimeout(timeout);
-
-    extractHeaders(headers,builder);
-    final Options options = builder.createOptions();
-    sendRequest(options, new ResponseCallback() {
-      @Override
-      public void onResponse(WXResponse response, Map<String, String> headers) {
-        if(callback != null) {
-          Map<String, Object> resp = new HashMap<>();
-          if(response == null|| "-1".equals(response.statusCode)){
-            resp.put(STATUS,-1);
-            resp.put(STATUS_TEXT,Status.ERR_CONNECT_FAILED);
-          }else {
-            int code = Integer.parseInt(response.statusCode);
-            resp.put(STATUS, code);
-            resp.put("ok", (code >= 200 && code <= 299));
-            if (response.originalData == null) {
-              resp.put("data", null);
-            } else {
-              String respData = readAsString(response.originalData,
-                  headers != null ? getHeader(headers, "Content-Type") : ""
-              );
-              try {
-                resp.put("data", parseData(respData, options.getType()));
-              } catch (JSONException exception) {
-                WXLogUtils.e("", exception);
-                resp.put("ok", false);
-                resp.put("data","{'err':'Data parse failed!'}");
-              }
-            }
-            resp.put(STATUS_TEXT, Status.getStatusText(response.statusCode));
-          }
-          resp.put("headers", headers);
-          WXStateRecord.getInstance().recordAction(instanceId,"stream response code:"+(null!= response?response.statusCode:"null"));
-          callback.invoke(resp);
-        }
-      }
-    }, progressCallback, instanceId, bundleURL);
-  }
-
-  Object parseData(String data, Options.Type type) throws JSONException{
-    if( type == Options.Type.json){
-      return JSONObject.parse(data);
-    }else if( type == Options.Type.jsonp){
-      if(data == null || data.isEmpty()) {
-        return new JSONObject();
-      }
-      int b = data.indexOf("(")+1;
-      int e = data.lastIndexOf(")");
-      if(b ==0 || b >= e || e <= 0){
-        return new JSONObject();
-      }
-
-      data = data.substring(b,e);
-      return JSONObject.parse(data);
-    }else {
-      return data;
-    }
-  }
-
-  static String getHeader(Map<String,String> headers,String key){
-    if(headers == null||key == null){
-      return null;
-    }
-    if(headers.containsKey(key)){
-      return headers.get(key);
-    }else{
-      return headers.get(key.toLowerCase(Locale.ROOT));
-    }
-  }
-
-
-
-  static String readAsString(byte[] data,String cType){
-    String charset = "utf-8";
-    if(cType != null){
-      Matcher matcher = CHARSET_PATTERN.matcher(cType.toLowerCase(Locale.ROOT));
-      if(matcher.find()){
-        charset = matcher.group(1);
-      }
-    }
-    try {
-      return new String(data,charset);
-    } catch (UnsupportedEncodingException e) {
-      WXLogUtils.e("", e);
-      return new String(data);
-    }
-  }
-
-
-  private void extractHeaders(JSONObject headers, Options.Builder builder){
-    //set user-agent
-    String UA = WXHttpUtil.assembleUserAgent(WXEnvironment.getApplication(),WXEnvironment.getConfig());
-    if(headers != null){
-      for (String key : headers.keySet()) {
-        if (key.equals(KEY_USER_AGENT)) {
-          UA = headers.getString(key);
-          continue;
-        }
-        builder.putHeader(key, headers.getString(key));
-      }
-    }
-    builder.putHeader(KEY_USER_AGENT,UA);
-  }
-
-
-  private void sendRequest(Options options,ResponseCallback callback,JSCallback progressCallback,String instanceId, String bundleURL){
-    WXRequest wxRequest = new WXRequest();
-    wxRequest.method = options.getMethod();
-    wxRequest.url = WXSDKManager.getInstance().getURIAdapter().rewrite(bundleURL, URIAdapter.REQUEST,Uri.parse(options.getUrl())).toString();
-    wxRequest.body = options.getBody();
-    wxRequest.timeoutMs = options.getTimeout();
-    wxRequest.instanceId = instanceId;
-
-    if(options.getHeaders()!=null) {
-      if (wxRequest.paramMap == null) {
-        wxRequest.paramMap = options.getHeaders();
-      } else {
-        wxRequest.paramMap.putAll(options.getHeaders());
-      }
-    }
-
-    IWXHttpAdapter adapter = ( mAdapter==null) ? WXSDKManager.getInstance().getIWXHttpAdapter() : mAdapter;
-    if (adapter != null) {
-      adapter.sendRequest(wxRequest, new StreamHttpListener(callback,progressCallback));
-    }else{
-      WXLogUtils.e("WXStreamModule","No HttpAdapter found,request failed.");
-    }
-  }
-
-  private interface ResponseCallback{
-    void onResponse(WXResponse response, Map<String, String> headers);
-  }
-
-  private static class StreamHttpListener implements IWXHttpAdapter.OnHttpListener {
-    private ResponseCallback mCallback;
-    private JSCallback mProgressCallback;
-    private Map<String,Object> mResponse = new HashMap<>();
-    private Map<String,String> mRespHeaders;
-
-    private StreamHttpListener(ResponseCallback callback,JSCallback progressCallback) {
-      mCallback = callback;
-      mProgressCallback = progressCallback;
-    }
-
-
-    @Override
-    public void onHttpStart() {
-      if(mProgressCallback !=null) {
-        mResponse.put("readyState",1);//readyState: number 1 OPENED 2 HEADERS_RECEIVED 3 LOADING
-        mResponse.put("length",0);
-        mProgressCallback.invokeAndKeepAlive(new HashMap<>(mResponse));
-      }
-    }
-
-    @Override
-    public void onHttpUploadProgress(int uploadProgress) {
-
-    }
-
-    @Override
-    public void onHeadersReceived(int statusCode,Map<String,List<String>> headers) {
-      mResponse.put("readyState", 2);
-      mResponse.put("status", statusCode);
-
-      Map<String, String> simpleHeaders = new HashMap<>();
-      if (headers != null) {
-        Iterator<Map.Entry<String, List<String>>> it = headers.entrySet().iterator();
-        while (it.hasNext()) {
-          Map.Entry<String, List<String>> entry = it.next();
-          if (entry.getValue().size() == 0) {
-            continue;
-          } else if (entry.getValue().size() == 1)
-            simpleHeaders.put(entry.getKey() == null ? "_" : entry.getKey(), entry.getValue().get(0));
-          else {
-            simpleHeaders.put(entry.getKey() == null ? "_" : entry.getKey(), entry.getValue().toString());
-          }
-        }
-      }
-
-      mResponse.put("headers", simpleHeaders);
-      mRespHeaders = simpleHeaders;
-      if (mProgressCallback != null) {
-        mProgressCallback.invokeAndKeepAlive(new HashMap<>(mResponse));
-      }
-    }
-
-    @Override
-    public void onHttpResponseProgress(int loadedLength) {
-      mResponse.put("length",loadedLength);
-      if(mProgressCallback!=null){
-        mProgressCallback.invokeAndKeepAlive(new HashMap<>(mResponse));
-      }
-
-    }
-
-    @Override
-    public void onHttpFinish(final WXResponse response) {
-      //compatible with old sendhttp
-      if(mCallback!=null){
-        mCallback.onResponse(response, mRespHeaders);
-      }
-
-      if(WXEnvironment.isApkDebugable()){
-        WXLogUtils.d("WXStreamModule",response!=null && response.originalData!=null?new String(response.originalData):"response data is NUll!");
-      }
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/instance/InstanceOnFireEventInterceptor.java b/android/sdk/src/main/java/com/taobao/weex/instance/InstanceOnFireEventInterceptor.java
deleted file mode 100644
index 3b142f7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/instance/InstanceOnFireEventInterceptor.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.instance;
-
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.ui.WXRenderManager;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Created by furture on 2018/8/23.
- */
-
-public abstract  class InstanceOnFireEventInterceptor {
-
-    private List<String> listenEvents;
-
-    public InstanceOnFireEventInterceptor() {
-        this.listenEvents = new ArrayList<>();
-    }
-
-    public void addInterceptEvent(String event){
-        if(!listenEvents.contains(event)){
-            this.listenEvents.add(event);
-        }
-    }
-
-    public List<String> getListenEvents() {
-        return listenEvents;
-    }
-
-    public void onInterceptFireEvent(String instanceId, String elementRef, String type, Map<String, Object> params, Map<String, Object> domChanges){
-        if(params == null){
-            return;
-        }
-        if(this.listenEvents.contains(type)){
-            onFireEvent(instanceId, elementRef, type, params, domChanges);
-        }
-    }
-
-    public  abstract void onFireEvent(String instanceId, String elementRef,String type, Map<String, Object> params, Map<String, Object> domChanges);
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/jsEngine/CallBackCode.java b/android/sdk/src/main/java/com/taobao/weex/jsEngine/CallBackCode.java
deleted file mode 100644
index 8456852..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/jsEngine/CallBackCode.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.jsEngine;
-
-public class CallBackCode {
-
-    public static final CallBackCode ERROR_JSENGINE_CRASHED = new CallBackCode(-1, "js engine Crashed");
-    public static final CallBackCode JSENGINE_INIT_FINISH = new CallBackCode(1, "js Engine init finished");
-    public int code;
-    public String msg;
-
-    private CallBackCode(int code, String msg) {
-        this.code = code;
-        this.msg = msg;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/jsEngine/EnvCallback.java b/android/sdk/src/main/java/com/taobao/weex/jsEngine/EnvCallback.java
deleted file mode 100644
index eb56df2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/jsEngine/EnvCallback.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.jsEngine;
-
-public interface EnvCallback {
-    void error(CallBackCode code);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSBiz.java b/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSBiz.java
deleted file mode 100644
index cd3f155..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSBiz.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.jsEngine;
-
-public class JSBiz {
-    private String bizName;
-    private String bizId;
-
-    public JSBiz(String id, String name) {
-        this.bizId = id;
-        this.bizName = name;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSContext.java b/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSContext.java
deleted file mode 100644
index 365946e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSContext.java
+++ /dev/null
@@ -1,122 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.jsEngine;
-
-import com.taobao.weex.base.CalledByNative;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.io.Serializable;
-import java.util.concurrent.ConcurrentHashMap;
-
-import static com.taobao.weex.jsEngine.JSEngine.mCreatedJSContext;
-
-public class JSContext implements Serializable {
-    private ConcurrentHashMap<String, JSFunction> funcMap = new ConcurrentHashMap<>();
-    //JSEnginePtrContainer
-    private long mNativeContextPtr = 0;
-
-    private JSException mExceptionTransfer = null;
-
-    protected JSContext() {
-        WXBridgeManager.getInstance().post(new Runnable() {
-            @Override
-            public void run() {
-                mNativeContextPtr = nativeCreateContext();
-                mCreatedJSContext.put(mNativeContextPtr, JSContext.this);
-            }
-        });
-    }
-
-    public void registerException(JSException e) {
-        mExceptionTransfer = e;
-    }
-
-    public void destroy() {
-        mCreatedJSContext.remove(mNativeContextPtr);
-        mExceptionTransfer = null;
-        WXBridgeManager.getInstance().post(new Runnable() {
-            @Override
-            public void run() {
-                if (mNativeContextPtr != 0) {
-                    long tmp = mNativeContextPtr;
-                    mNativeContextPtr = 0;
-                    nativeDestroyContext(tmp);
-                }
-            }
-        });
-    }
-
-    public void bindFunction(final String name, final JSFunction function) {
-        WXBridgeManager.getInstance().post(new Runnable() {
-            @Override
-            public void run() {
-                funcMap.put(name, function);
-                nativeBindFunc(mNativeContextPtr, name);
-            }
-        });
-    }
-
-    public void unBindFunction(final String name) {
-        WXBridgeManager.getInstance().post(new Runnable() {
-            @Override
-            public void run() {
-                funcMap.remove(name);
-                nativeUnBindFunc(mNativeContextPtr, name);
-            }
-        });
-    }
-
-    public void Eval(final String script) {
-        WXBridgeManager.getInstance().post(new Runnable() {
-            @Override
-            public void run() {
-                nativeExecJS(mNativeContextPtr, script);
-            }
-        });
-    }
-
-
-    @CalledByNative
-    public String Invoke(String name, String args) {
-        JSFunction jsFunction = funcMap.get(name);
-        if (jsFunction != null) {
-            WXLogUtils.d("jsEngine invoke " + name + " arg:" + args);
-            return jsFunction.invoke(args);
-        }
-        return "";
-    }
-
-    @CalledByNative
-    public void Exception(String exception) {
-        if (exception != null && mExceptionTransfer != null) {
-            this.mExceptionTransfer.exception(exception);
-        }
-    }
-
-    private native long nativeCreateContext();
-
-    private native void nativeDestroyContext(long ctxPtr);
-
-    private native void nativeBindFunc(long ctxPtr, String name);
-
-    private native void nativeUnBindFunc(long ctxPtr, String name);
-
-    private native void nativeExecJS(long ctxPtr, String script);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSEngine.java b/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSEngine.java
deleted file mode 100644
index b6d68c8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSEngine.java
+++ /dev/null
@@ -1,99 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.jsEngine;
-
-import android.support.annotation.Nullable;
-import android.util.Log;
-
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.io.Serializable;
-import java.util.HashMap;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-
-import static com.taobao.weex.jsEngine.CallBackCode.ERROR_JSENGINE_CRASHED;
-import static com.taobao.weex.jsEngine.CallBackCode.JSENGINE_INIT_FINISH;
-
-public class JSEngine implements Serializable {
-    private static JSEngine mJsEngine = null;
-
-    public static final ConcurrentHashMap<Long, JSContext> mCreatedJSContext = new ConcurrentHashMap<>();
-
-    private static final ConcurrentHashMap<JSBiz, EnvCallback> mEnvCallbacks = new ConcurrentHashMap<>();
-
-    private JSEngine() {
-    }
-
-    public static JSEngine getInstance() {
-        if (mJsEngine == null) {
-            synchronized (JSEngine.class) {
-                if (mJsEngine == null) {
-                    mJsEngine = new JSEngine();
-                }
-            }
-        }
-        return mJsEngine;
-    }
-
-    public void registerEnvCallback(JSBiz biz, EnvCallback e) {
-        if (biz == null || e == null) {
-            return;
-        }
-        mEnvCallbacks.put(biz, e);
-    }
-
-    public void unRegisterEnvCallback(JSBiz biz) {
-        if (biz == null) {
-            return;
-        }
-        mEnvCallbacks.remove(biz);
-    }
-
-
-    @Nullable
-    public JSContext createJSContext() {
-        if (!WXSDKEngine.isInitialized()) {
-            WXLogUtils.e("Create JSContext Failed because of weex has not been initialized");
-            return null;
-        }
-        return new JSContext();
-    }
-
-    public void engineInitFinished() {
-        for (Map.Entry<JSBiz, EnvCallback> next : mEnvCallbacks.entrySet()) {
-            next.getValue().error(JSENGINE_INIT_FINISH);
-        }
-    }
-
-    public void engineCrashed() {
-        for (Map.Entry<JSBiz, EnvCallback> next : mEnvCallbacks.entrySet()) {
-            next.getValue().error(ERROR_JSENGINE_CRASHED);
-        }
-
-        HashMap<Long, JSContext> map = new HashMap<>(mCreatedJSContext);
-        mCreatedJSContext.clear();
-        for (Map.Entry<Long, JSContext> next : map.entrySet()) {
-            JSContext value = next.getValue();
-            value.destroy();
-        }
-        map.clear();
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSException.java b/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSException.java
deleted file mode 100644
index 67082e0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSException.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.jsEngine;
-
-public interface JSException {
-    void exception(String exception);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSFunction.java b/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSFunction.java
deleted file mode 100644
index 7a74327..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/jsEngine/JSFunction.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.jsEngine;
-
-public interface JSFunction {
-    String invoke(String args);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/layout/ContentBoxMeasurement.java b/android/sdk/src/main/java/com/taobao/weex/layout/ContentBoxMeasurement.java
deleted file mode 100644
index d25a845..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/layout/ContentBoxMeasurement.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.layout;
-
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import com.taobao.weex.base.CalledByNative;
-import com.taobao.weex.common.Destroyable;
-import com.taobao.weex.ui.component.WXComponent;
-
-import java.io.Serializable;
-import java.lang.ref.WeakReference;
-
-public abstract class ContentBoxMeasurement implements Serializable,Destroyable {
-
-  @Nullable
-  protected WXComponent mComponent;
-
-  protected float mMeasureWidth;
-
-  protected float mMeasureHeight;
-
-  public ContentBoxMeasurement() {
-    mComponent = null;
-  }
-
-  public ContentBoxMeasurement(@NonNull WXComponent component) {
-    this.mComponent = component;
-  }
-
-  /** uiThread = false **/
-  @CalledByNative
-  public final void measure(float width, float height, int widthMeasureMode, int heightMeasureMode) {
-    measureInternal(width, height, widthMeasureMode, heightMeasureMode);
-  }
-
-  /** uiThread = false **/
-  public abstract void measureInternal(float width, float height, int widthMeasureMode, int heightMeasureMode);
-
-  /** uiThread = false **/
-  @CalledByNative
-  public abstract void layoutBefore();
-
-  /** uiThread = false **/
-  @CalledByNative
-  public abstract void layoutAfter(float computedWidth, float computedHeight);
-
-  @CalledByNative
-  public float getWidth() {
-    return mMeasureWidth;
-  }
-
-  @CalledByNative
-  public float getHeight() {
-    return mMeasureHeight;
-  }
-
-  @Override
-  public void destroy() {
-    mComponent = null;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/layout/MeasureMode.java b/android/sdk/src/main/java/com/taobao/weex/layout/MeasureMode.java
deleted file mode 100644
index fd25f50..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/layout/MeasureMode.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.layout;
-
-import java.io.Serializable;
-
-public class MeasureMode implements Serializable {
-
-  public static int EXACTLY = 1;
-
-  public static int UNSPECIFIED = 0;
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/layout/MeasureSize.java b/android/sdk/src/main/java/com/taobao/weex/layout/MeasureSize.java
deleted file mode 100644
index ad671bf..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/layout/MeasureSize.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.layout;
-
-import java.io.Serializable;
-
-public class MeasureSize implements Serializable{
-  private float width;
-  private float height;
-
-  public float getWidth() {
-    return width;
-  }
-
-  public void setWidth(float width) {
-    this.width = width;
-  }
-
-  public float getHeight() {
-    return height;
-  }
-
-  public void setHeight(float height) {
-    this.height = height;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/layout/measurefunc/TextContentBoxMeasurement.java b/android/sdk/src/main/java/com/taobao/weex/layout/measurefunc/TextContentBoxMeasurement.java
deleted file mode 100755
index 3a22532..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/layout/measurefunc/TextContentBoxMeasurement.java
+++ /dev/null
@@ -1,500 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.layout.measurefunc;
-
-import android.graphics.Canvas;
-import android.os.Build;
-import android.os.Looper;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.text.Editable;
-import android.text.Layout;
-import android.text.Spannable;
-import android.text.SpannableString;
-import android.text.SpannableStringBuilder;
-import android.text.Spanned;
-import android.text.SpannedString;
-import android.text.StaticLayout;
-import android.text.TextPaint;
-import android.text.TextUtils;
-import android.text.style.AbsoluteSizeSpan;
-import android.text.style.AlignmentSpan;
-import android.text.style.ForegroundColorSpan;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.support.annotation.WorkerThread;
-
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.TextDecorationSpan;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.dom.WXCustomStyleSpan;
-import com.taobao.weex.dom.WXLineHeightSpan;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.layout.ContentBoxMeasurement;
-import com.taobao.weex.layout.MeasureMode;
-import com.taobao.weex.layout.MeasureSize;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXText;
-import com.taobao.weex.ui.component.WXTextDecoration;
-import com.taobao.weex.utils.WXDomUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXResourceUtils;
-
-import java.lang.ref.WeakReference;
-import java.util.Collections;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicReference;
-
-import static com.taobao.weex.dom.WXStyle.UNSET;
-import static com.taobao.weex.utils.WXUtils.isUndefined;
-
-/**
- * Created by miomin on 2018/3/9.
- */
-
-public class TextContentBoxMeasurement extends ContentBoxMeasurement {
-
-  private static final Canvas DUMMY_CANVAS = new Canvas();
-
-  public TextContentBoxMeasurement(WXComponent component) {
-    super(component);
-  }
-
-  class SetSpanOperation {
-
-    protected final int start, end, flag;
-    protected final Object what;
-
-    SetSpanOperation(int start, int end, Object what) {
-      this(start, end, what, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
-    }
-
-    SetSpanOperation(int start, int end, Object what, int flag) {
-      this.start = start;
-      this.end = end;
-      this.what = what;
-      this.flag = flag;
-    }
-
-    public void execute(Spannable sb) {
-      sb.setSpan(what, start, end, flag);
-    }
-  }
-
-  private static final String ELLIPSIS = "\u2026";
-  private boolean mIsColorSet = false;
-  private boolean hasBeenMeasured = false;
-  private int mColor;
-  private int mFontStyle = UNSET;
-  private int mFontWeight = UNSET;
-  private int mNumberOfLines = UNSET;
-  private int mFontSize = UNSET;
-  private int mLineHeight = UNSET;
-  private float previousWidth = Float.NaN;
-  private String mFontFamily = null;
-  private String mText = null;
-  private TextUtils.TruncateAt textOverflow;
-  private Layout.Alignment mAlignment;
-  private WXTextDecoration mTextDecoration = WXTextDecoration.NONE;
-  private TextPaint mTextPaint;
-  private @Nullable
-  Spanned spanned;
-  private @Nullable
-  Layout layout;
-  private AtomicReference<Layout> atomicReference = new AtomicReference<>();
-
-  /**
-   * uiThread = false
-   **/
-  @Override
-  public void layoutBefore() {
-    mTextPaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG);
-    hasBeenMeasured = false;
-    updateStyleAndText();
-    spanned = createSpanned(mText);
-  }
-
-  /**
-   * uiThread = false
-   **/
-  @Override
-  public void measureInternal(float width, float height, int widthMeasureMode, int heightMeasureMode) {
-    float measureWidth = width, measureHeight = height;
-    hasBeenMeasured = true;
-    float textWidth = getTextWidth(mTextPaint, width, widthMeasureMode == MeasureMode.EXACTLY);
-
-    if (textWidth > 0 && spanned != null) {
-      layout = createLayout(textWidth,null);
-      previousWidth = layout.getWidth();
-      if (Float.isNaN(width)) {
-        measureWidth = layout.getWidth();
-      } else {
-        measureWidth = Math.min(layout.getWidth(), measureWidth);
-      }
-
-      if (Float.isNaN(height)) {
-        measureHeight = layout.getHeight();
-      }
-    } else {
-      if (widthMeasureMode == MeasureMode.UNSPECIFIED) {
-        measureWidth = 0;
-      }
-      if (heightMeasureMode == MeasureMode.UNSPECIFIED) {
-        measureHeight = 0;
-      }
-    }
-    mMeasureWidth = measureWidth;
-    mMeasureHeight = measureHeight;
-  }
-
-  /**
-   * uiThread = false
-   **/
-  @Override
-  public void layoutAfter(float computedWidth, float computedHeight) {
-    if(mComponent!=null) {
-      if (hasBeenMeasured) {
-        if (layout != null &&
-            WXDomUtils
-                .getContentWidth(mComponent.getPadding(), mComponent.getBorder(), computedWidth)
-                != previousWidth) {
-          recalculateLayout(computedWidth);
-        }
-      } else {
-        updateStyleAndText();
-        recalculateLayout(computedWidth);
-      }
-      hasBeenMeasured = false;
-      if (layout != null && !layout.equals(atomicReference.get()) &&
-          Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
-        if (Thread.currentThread() != Looper.getMainLooper().getThread()) {
-          warmUpTextLayoutCache(layout);
-        }
-      }
-      swap();
-      WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(new Runnable() {
-        @Override
-        public void run() {
-          if(mComponent!=null) {
-            mComponent.updateExtra(atomicReference.get());
-          }
-        }
-      }, mComponent.getInstanceId());
-    }
-  }
-
-  private void updateStyleAndText() {
-    updateStyleImp(mComponent.getStyles());
-    mText = WXAttr.getValue(mComponent.getAttrs());
-  }
-
-  /**
-   * Force relayout the text, the text must layout before invoke this method.
-   *
-   * Internal method, do not invoke unless you what what you are doing
-   * @param isRTL
-   */
-  @RestrictTo(Scope.LIBRARY)
-  @WorkerThread
-  public void forceRelayout(){
-    //Generate Spans
-    layoutBefore();
-
-    //Measure
-    measure(previousWidth, Float.NaN, MeasureMode.EXACTLY, MeasureMode.UNSPECIFIED);
-
-    //Swap text layout to UI Thread
-    layoutAfter(previousWidth, Float.NaN);
-  }
-
-  /**
-   * Record the property according to the given style
-   *
-   * @param style the give style.
-   */
-  private void updateStyleImp(Map<String, Object> style) {
-    if (style != null) {
-      if (style.containsKey(Constants.Name.LINES)) {
-        int lines = WXStyle.getLines(style);
-        mNumberOfLines = lines > 0 ? lines : UNSET;
-      }
-      if (style.containsKey(Constants.Name.FONT_SIZE)) {
-        mFontSize = WXStyle.getFontSize(style, mComponent.getViewPortWidth());
-      }
-      if (style.containsKey(Constants.Name.FONT_WEIGHT)) {
-        mFontWeight = WXStyle.getFontWeight(style);
-      }
-      if (style.containsKey(Constants.Name.FONT_STYLE)) {
-        mFontStyle = WXStyle.getFontStyle(style);
-      }
-      if (style.containsKey(Constants.Name.COLOR)) {
-        mColor = WXResourceUtils.getColor(WXStyle.getTextColor(style));
-        mIsColorSet = mColor != Integer.MIN_VALUE;
-      }
-      if (style.containsKey(Constants.Name.TEXT_DECORATION)) {
-        mTextDecoration = WXStyle.getTextDecoration(style);
-      }
-      if (style.containsKey(Constants.Name.FONT_FAMILY)) {
-        mFontFamily = WXStyle.getFontFamily(style);
-      }
-      mAlignment = WXStyle.getTextAlignment(style, mComponent.isLayoutRTL());
-      textOverflow = WXStyle.getTextOverflow(style);
-      int lineHeight = WXStyle.getLineHeight(style, mComponent.getViewPortWidth());
-      if (lineHeight != UNSET) {
-        mLineHeight = lineHeight;
-      }
-    }
-  }
-
-  /**
-   * Update {@link #spanned} according to the give charSequence and styles
-   *
-   * @param text the give raw text.
-   * @return an Spanned contains text and spans
-   */
-  protected
-  @NonNull
-  Spanned createSpanned(String text) {
-    if (!TextUtils.isEmpty(text)) {
-      SpannableString spannable = new SpannableString(text);
-      updateSpannable(spannable, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
-      return spannable;
-    }
-    return new SpannableString("");
-  }
-
-  protected void updateSpannable(Spannable spannable, int spanFlag) {
-    int end = spannable.length();
-    if (mFontSize == UNSET) {
-      mTextPaint.setTextSize(WXText.sDEFAULT_SIZE);
-    }
-    else{
-      mTextPaint.setTextSize(mFontSize);
-    }
-
-    if (mLineHeight != UNSET) {
-      setSpan(spannable, new WXLineHeightSpan(mLineHeight), 0, end, spanFlag);
-    }
-
-    setSpan(spannable, new AlignmentSpan.Standard(mAlignment), 0, end, spanFlag);
-
-    if (mFontStyle != UNSET || mFontWeight != UNSET || mFontFamily != null) {
-      setSpan(spannable, new WXCustomStyleSpan(mFontStyle, mFontWeight, mFontFamily), 0, end, spanFlag);
-    }
-
-    if (mIsColorSet) {
-      mTextPaint.setColor(mColor);
-    }
-
-    if (mTextDecoration == WXTextDecoration.UNDERLINE || mTextDecoration == WXTextDecoration.LINETHROUGH) {
-      setSpan(spannable, new TextDecorationSpan(mTextDecoration), 0, end, spanFlag);
-    }
-  }
-
-  private void setSpan(Spannable spannable, Object what, int start, int end, int spanFlag){
-    spannable.setSpan(what, start, end, spanFlag);
-  }
-
-  /**
-   * Get text width according to constrain of outerWidth with and forceToDesired
-   *
-   * @param textPaint      paint used to measure text
-   * @param outerWidth     the width that css-layout desired.
-   * @param forceToDesired if set true, the return value will be outerWidth, no matter what the width
-   *                       of text is.
-   * @return if forceToDesired is false, it will be the minimum value of the width of text and
-   * outerWidth in case of outerWidth is defined, in other case, it will be outer width.
-   */
-  private float getTextWidth(TextPaint textPaint, float outerWidth, boolean forceToDesired) {
-    if (mText == null) {
-      if (forceToDesired) {
-        return outerWidth;
-      }
-      return 0;
-    }
-    else {
-      float textWidth;
-      if (forceToDesired) {
-        textWidth = outerWidth;
-      } else {
-        float desiredWidth = Layout.getDesiredWidth(spanned, textPaint);
-        if (isUndefined(outerWidth) || desiredWidth < outerWidth) {
-          textWidth = desiredWidth;
-        } else {
-          textWidth = outerWidth;
-        }
-      }
-      return textWidth;
-    }
-  }
-
-  /**
-   * Update layout according to {@link #mText} and span
-   *
-   * @param width          the specified width.
-   * @param forceWidth     If true, force the text width to the specified width, otherwise, text width
-   *                       may equals to or be smaller than the specified width.
-   * @param previousLayout the result of previous layout, could be null.
-   */
-  private
-  @NonNull
-  Layout createLayout(final float textWidth, @Nullable Layout previousLayout) {
-    Layout layout;
-    if (previousWidth != textWidth || previousLayout == null) {
-      layout = new StaticLayout(spanned, mTextPaint, (int) Math.ceil(textWidth),
-              Layout.Alignment.ALIGN_NORMAL, 1, 0, false);
-    } else {
-      layout = previousLayout;
-    }
-    if (mNumberOfLines != UNSET && mNumberOfLines > 0 && mNumberOfLines < layout.getLineCount()) {
-      int lastLineStart, lastLineEnd;
-      lastLineStart = layout.getLineStart(mNumberOfLines - 1);
-      lastLineEnd = layout.getLineEnd(mNumberOfLines - 1);
-      if (lastLineStart < lastLineEnd) {
-        SpannableStringBuilder builder = null;
-        if (lastLineStart > 0) {
-          builder = new SpannableStringBuilder(spanned.subSequence(0, lastLineStart));
-        } else {
-          builder = new SpannableStringBuilder();
-        }
-        Editable lastLine = new SpannableStringBuilder(spanned.subSequence(lastLineStart, lastLineEnd));
-        builder.append(truncate(lastLine, mTextPaint, (int) Math.ceil(textWidth), textOverflow));
-        adjustSpansRange(spanned, builder);
-        spanned = builder;
-        return new StaticLayout(spanned, mTextPaint, (int) Math.ceil(textWidth),
-                Layout.Alignment.ALIGN_NORMAL, 1, 0, false);
-      }
-    }
-    return layout;
-  }
-
-  /**
-   * Truncate the source span to the specified lines.
-   * Caller of this method must ensure that the lines of text is <strong>greater than desired lines and need truncate</strong>.
-   * Otherwise, unexpected behavior may happen.
-   *
-   * @param source     The source span.
-   * @param paint      the textPaint
-   * @param desired    specified lines.
-   * @param truncateAt truncate method, null value means clipping overflow text directly, non-null value means using ellipsis strategy to clip
-   * @return The spans after clipped.
-   */
-  private
-  @NonNull
-  Spanned truncate(@Nullable Editable source, @NonNull TextPaint paint,
-                   int desired, @Nullable TextUtils.TruncateAt truncateAt) {
-    Spanned ret = new SpannedString("");
-    if (!TextUtils.isEmpty(source) && source.length() > 0) {
-      if (truncateAt != null) {
-        source.append(ELLIPSIS);
-        Object[] spans = source.getSpans(0, source.length(), Object.class);
-        for (Object span : spans) {
-          int start = source.getSpanStart(span);
-          int end = source.getSpanEnd(span);
-          if (start == 0 && end == source.length() - 1) {
-            source.removeSpan(span);
-            source.setSpan(span, 0, source.length(), source.getSpanFlags(span));
-          }
-        }
-      }
-
-      StaticLayout layout;
-      int startOffset;
-
-      while (source.length() > 1) {
-        startOffset = source.length() - 1;
-        if (truncateAt != null) {
-          startOffset -= 1;
-        }
-        source.delete(startOffset, startOffset + 1);
-        layout = new StaticLayout(source, paint, desired, Layout.Alignment.ALIGN_NORMAL, 1, 0, false);
-        if (layout.getLineCount() <= 1) {
-          ret = source;
-          break;
-        }
-      }
-    }
-    return ret;
-  }
-
-  /**
-   * Adjust span range after truncate due to the wrong span range during span copy and slicing.
-   *
-   * @param beforeTruncate The span before truncate
-   * @param afterTruncate  The span after truncate
-   */
-  private void adjustSpansRange(@NonNull Spanned beforeTruncate, @NonNull Spannable afterTruncate) {
-    Object[] spans = beforeTruncate.getSpans(0, beforeTruncate.length(), Object.class);
-    for (Object span : spans) {
-      int start = beforeTruncate.getSpanStart(span);
-      int end = beforeTruncate.getSpanEnd(span);
-      if (start == 0 && end == beforeTruncate.length()) {
-        afterTruncate.removeSpan(span);
-        afterTruncate.setSpan(span, 0, afterTruncate.length(), beforeTruncate.getSpanFlags(span));
-      }
-    }
-  }
-
-  private void recalculateLayout(float computedWidth) {
-    float contentWidth = WXDomUtils.getContentWidth(mComponent.getPadding(), mComponent.getBorder(), computedWidth);
-    if (contentWidth > 0) {
-      spanned = createSpanned(mText);
-      if (spanned != null) {
-        layout = createLayout(contentWidth, layout);
-        previousWidth = layout.getWidth();
-      } else {
-        previousWidth = 0;
-      }
-    }
-  }
-
-  /**
-   * As warming up TextLayoutCache done in the DOM thread may manipulate UI operation,
-   * there may be some exception, in which case the exception is ignored. After all,
-   * this is just a warm up operation.
-   *
-   * @return false for warm up failure, otherwise returns true.
-   */
-  private boolean warmUpTextLayoutCache(Layout layout) {
-    boolean result;
-    try {
-      layout.draw(DUMMY_CANVAS);
-      result = true;
-    } catch (Exception e) {
-      WXLogUtils.eTag("TextWarmUp", e);
-      result = false;
-    }
-    return result;
-  }
-
-  /**
-   * Move the reference of current layout to the {@link AtomicReference} for further use,
-   * then clear current layout.
-   */
-  private void swap() {
-    if (layout != null) {
-      atomicReference.set(layout);
-      layout = null;
-    }
-    hasBeenMeasured = false;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/performance/IApmGenerator.java b/android/sdk/src/main/java/com/taobao/weex/performance/IApmGenerator.java
deleted file mode 100644
index face350..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/performance/IApmGenerator.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/**
- * 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
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.performance;
-
-public interface IApmGenerator {
-    /**
-     * @param type apm type
-     * @return impl
-     */
-    IWXApmMonitorAdapter generateApmInstance(String type);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/performance/IWXAnalyzer.java b/android/sdk/src/main/java/com/taobao/weex/performance/IWXAnalyzer.java
deleted file mode 100644
index cbd170c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/performance/IWXAnalyzer.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/**
- * 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
- * http://www.apache.org/licenses/LICENSE-2.0
- * 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.
- */
-package com.taobao.weex.performance;
-
-
-/**
- * @author zhongcang
- * @date 2018/2/28
- */
-
-public interface IWXAnalyzer {
-
-  /**
-   *
-   * @param group   dataGroup
-   * @param module  dataModule in group
-   * @param type    dataType
-   * @param data   data (json)
-   */
-  void transfer(String group, String module, String type, String data);
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/performance/IWXApmMonitorAdapter.java b/android/sdk/src/main/java/com/taobao/weex/performance/IWXApmMonitorAdapter.java
deleted file mode 100644
index 1fe198e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/performance/IWXApmMonitorAdapter.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/**
- * 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
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.performance;
-
-public interface IWXApmMonitorAdapter {
-
-    /**
-     * start record
-     *
-     * @param instanceId instanceId
-     */
-    void onStart(String instanceId);
-
-    /**
-     * end record
-     */
-    void onEnd();
-
-    /**
-     * record event
-     */
-    void onEvent(String name, Object value);
-
-    /**
-     * record stage
-     */
-    void onStage(String name, long timestamp);
-
-    /**
-     * record property
-     */
-    void addProperty(String key, Object value);
-
-    /**
-     * record statistic
-     */
-    void addStats(String key, double value);
-
-    /**
-     * record subProcedure stage
-     */
-
-    void onSubProcedureStage(String procedureName, String stageName);
-
-    /**
-     * record SubProcedure event
-     */
-
-    void onSubProcedureEvent(String procedureName, String eventName);
-
-    /**
-     * record subProcedure stats
-     */
-    void setSubProcedureStats(String procedureName, String name, double value);
-
-    /**
-     * record subProcedure properties
-     */
-    void setSubProcedureProperties(String procedureName, String name, Object value);
-
-    void onAppear();
-
-    void onDisappear();
-
-    String parseReportUrl(String originUrl);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/performance/WXAnalyzerDataTransfer.java b/android/sdk/src/main/java/com/taobao/weex/performance/WXAnalyzerDataTransfer.java
deleted file mode 100644
index 194046c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/performance/WXAnalyzerDataTransfer.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/**
- * 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
- * http://www.apache.org/licenses/LICENSE-2.0
- * 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.
- */
-package com.taobao.weex.performance;
-
-import java.util.Iterator;
-import java.util.List;
-
-import android.util.Log;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.bridge.WXJSObject;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXJSExceptionInfo;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.WXUtils;
-import org.json.JSONObject;
-
-/**
- * @author zhongcang
- * @date 2018/2/28
- */
-
-public class WXAnalyzerDataTransfer {
-
-  private static final String GROUP = "WXAnalyzer";
-  private static final String MODULE_ERROR = "WXError";
-  private static final String MODULE_WX_APM = "wxapm";
-  public static boolean isOpenPerformance = false;
-  public static final String INTERACTION_TAG = "wxInteractionAnalyzer";
-  private static boolean sOpenInteractionLog;
-
-
-  public static void transferPerformance(String instanceId,String type,String key,Object value)
-  {
-      if (!isOpenPerformance){
-          return;
-      }
-      if (sOpenInteractionLog && "stage".equals(type)){
-          Log.d(INTERACTION_TAG, "[client][stage]"+instanceId+","+key+","+value);
-      }
-      List<IWXAnalyzer> transferList = WXSDKManager.getInstance().getWXAnalyzerList();
-      if (null == transferList || transferList.size() == 0) {
-          return;
-      }
-
-      WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
-      if (null == instance){
-          return;
-      }
-
-      String data;
-      try {
-        data = new JSONObject().put(key,value).toString();
-      }catch (Exception e){
-        e.printStackTrace();
-        return;
-      }
-
-      Iterator<IWXAnalyzer> itr = transferList.iterator();
-      while (itr.hasNext()){
-          IWXAnalyzer item = itr.next();
-          item.transfer(MODULE_WX_APM, instance.getInstanceId(), type, data);
-      }
-  }
-
-  public static void transferInteractionInfo(WXComponent targetComponent){
-    if (!isOpenPerformance){
-      return;
-    }
-
-    List<IWXAnalyzer> transferList = WXSDKManager.getInstance().getWXAnalyzerList();
-    if (null == transferList || transferList.size() == 0) {
-      return;
-    }
-    long renderOriginDiffTime = WXUtils.getFixUnixTime() - targetComponent.getInstance().getWXPerformance().renderUnixTimeOrigin;
-    String data;
-    try{
-      data = new JSONObject()
-          .put("renderOriginDiffTime",renderOriginDiffTime)
-          .put("type",targetComponent.getComponentType())
-          .put("ref",targetComponent.getRef())
-          .put("style",targetComponent.getStyles())
-          .put("attrs",targetComponent.getAttrs())
-          .toString();
-    }catch (Exception e){
-      e.printStackTrace();
-      return;
-    }
-    for (IWXAnalyzer transfer : transferList) {
-      transfer.transfer(MODULE_WX_APM, targetComponent.getInstanceId(), "wxinteraction", data);
-    }
-  }
-
-
-  public static void transferError(WXJSExceptionInfo exceptionInfo, String instanceId) {
-    if (!WXEnvironment.isApkDebugable()) {
-      return;
-    }
-    List<IWXAnalyzer> transferList = WXSDKManager.getInstance().getWXAnalyzerList();
-    if (null == transferList || transferList.size() == 0) {
-      return;
-    }
-
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (null == instance) {
-      return;
-    }
-    WXErrorCode errorCode = exceptionInfo.getErrCode();
-    String data = "";
-    try {
-      data = new JSONObject()
-              .put("instanceId", instanceId)
-              .put("url", instance.getBundleUrl())
-              .put("errorCode", errorCode.getErrorCode())
-              .put("errorMsg", errorCode.getErrorMsg())
-              .put("errorGroup", errorCode.getErrorGroup())
-              .toString();
-    } catch (Exception e) {
-      e.printStackTrace();
-    }
-    for (IWXAnalyzer transfer : transferList) {
-      transfer.transfer(GROUP, MODULE_ERROR, errorCode.getErrorType().toString(), data);
-    }
-  }
-
-  public static void switchInteractionLog(final boolean isOpen){
-      if ( sOpenInteractionLog == isOpen || !WXEnvironment.JsFrameworkInit){
-          return;
-      }
-      sOpenInteractionLog = isOpen;
-      //for jsfm && jsengin
-      //TODO wait for JSFramework
-//      WXBridgeManager.getInstance().post(new Runnable() {
-//          @Override
-//          public void run() {
-//              WXJSObject[] args = {new WXJSObject(isOpen?1:0)};
-//              WXBridgeManager.getInstance().invokeExecJS(
-//                  "",
-//                  null,
-//                  "switchInteractionLog",
-//                  args,
-//                  false);
-//          }
-//      });
-      //for weex_core
-      WXBridgeManager.getInstance().registerCoreEnv("switchInteractionLog",String.valueOf(isOpen));
-  }
-
-  public static boolean isInteractionLogOpen(){
-     return sOpenInteractionLog;
-  }
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/performance/WXInstanceApm.java b/android/sdk/src/main/java/com/taobao/weex/performance/WXInstanceApm.java
deleted file mode 100644
index 4f99696..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/performance/WXInstanceApm.java
+++ /dev/null
@@ -1,683 +0,0 @@
-/**
- * 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
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.performance;
-
-import java.util.HashMap;
-import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-import java.util.concurrent.CopyOnWriteArraySet;
-
-import android.graphics.Rect;
-import android.os.Handler;
-import android.os.Looper;
-import android.text.TextUtils;
-import android.util.Log;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXPerformance;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-
-public class WXInstanceApm {
-
-    public static final String WEEX_PAGE_TOPIC = "weex_page";
-
-    /************** properties *****************/
-    public static final String KEY_PROPERTIES_ERROR_CODE = "wxErrorCode";
-    //public static final String KEY_PAGE_PROPERTIES_LAUNCH_ID = "wxLaunchId";
-    public static final String KEY_PAGE_PROPERTIES_BIZ_ID = "wxBizID";
-    public static final String KEY_PAGE_PROPERTIES_BUBDLE_URL = "wxBundleUrl";
-    public static final String KEY_PAGE_PROPERTIES_JSLIB_VERSION = "wxJSLibVersion";
-    public static final String KEY_PAGE_PROPERTIES_WEEX_VERSION = "wxSDKVersion";
-    public static final String KEY_PAGE_PROPERTIES_REQUEST_TYPE = "wxRequestType";
-    public static final String KEY_PAGE_PROPERTIES_CACHE_TYPE = "wxCacheType";
-    public static final String KEY_PAGE_PROPERTIES_CACHE_INFO = "wxZCacheInfo";
-    public static final String KEY_PAGE_PROPERTIES_JS_FM_INI = "wxJsFrameworkInit";
-    public static final String KEY_PAGE_PROPERTIES_CONTAINER_NAME = "wxContainerName";
-    public static final String KEY_PAGE_PROPERTIES_INSTANCE_TYPE = "wxInstanceType";
-    public static final String KEY_PAGE_PROPERTIES_PARENT_PAGE = "wxParentPage";
-    public static final String KEY_PAGE_PROPERTIES_BUNDLE_TYPE = "wxBundleType";
-    public static final String KEY_PAGE_PROPERTIES_RENDER_TYPE = "wxRenderType";
-    public static final String KEY_PAGE_PROPERTIES_UIKIT_TYPE = "wxUIKitType";
-
-    /************** stages *****************/
-    public static final String KEY_PAGE_STAGES_CONTAINER_READY = "wxContainerReady";
-    public static final String KEY_PAGE_STAGES_DOWN_BUNDLE_START = "wxStartDownLoadBundle";
-    public static final String KEY_PAGE_STAGES_DOWN_BUNDLE_END = "wxEndDownLoadBundle";
-    public static final String KEY_PAGE_STAGES_RENDER_ORGIGIN = "wxRenderTimeOrigin";
-    public static final String KEY_PAGE_STAGES_LOAD_BUNDLE_START = "wxStartLoadBundle";
-    public static final String KEY_PAGE_STAGES_LOAD_BUNDLE_END = "wxEndLoadBundle";
-    public static final String KEY_PAGE_STAGES_FIRST_INTERACTION_VIEW = "wxFirstInteractionView";
-    public static final String KEY_PAGE_STAGES_CREATE_FINISH= "wxJSBundleCreateFinish";
-    public static final String KEY_PAGE_STAGES_FSRENDER = "wxFsRender";
-    public static final String KEY_PAGE_STAGES_NEW_FSRENDER = "wxNewFsRender";
-    public static final String KEY_PAGE_STAGES_END_EXCUTE_BUNDLE = "wxEndExecuteBundle";
-    public static final String KEY_PAGE_STAGES_INTERACTION = "wxInteraction";
-    public static final String KEY_PAGE_STAGES_DESTROY = "wxDestroy";
-
-    //Custom preprocessing start, called when activity created or other time. Called by other activity
-    public static final String KEY_PAGE_STAGES_CUSTOM_PREPROCESS_START = "wxCustomPreprocessStart";
-    //Custom preprocessing end, called when you'are able to start weex render. Called by other activity
-    public static final String KEY_PAGE_STAGES_CUSTOM_PREPROCESS_END = "wxCustomPreprocessEnd";
-
-    /************** stats *****************/
-    public static final String KEY_PAGE_STATS_BUNDLE_SIZE = "wxBundleSize";
-    public static final String KEY_PAGE_STATS_FS_CALL_JS_TIME = "wxFSCallJsTotalTime";
-    public static final String KEY_PAGE_STATS_FS_CALL_JS_NUM = "wxFSCallJsTotalNum";
-    public static final String KEY_PAGE_STATS_FS_TIMER_NUM = "wxFSTimerCount";
-    public static final String KEY_PAGE_STATS_FS_CALL_NATIVE_TIME = "wxFSCallNativeTotalTime";
-    public static final String KEY_PAGE_STATS_FS_CALL_NATIVE_NUM = "wxFSCallNativeTotalNum";
-    public static final String KEY_PAGE_STATS_FS_CALL_EVENT_NUM = "wxFSCallEventTotalNum";
-    public static final String KEY_PAGE_STATS_FS_REQUEST_NUM = "wxFSRequestNum";
-    public static final String KEY_PAGE_STATS_CELL_EXCEED_NUM = "wxCellExceedNum";
-    public static final String KEY_PAGE_STATS_MAX_DEEP_VIEW = "wxMaxDeepViewLayer";
-    public static final String KEY_PAGE_STATS_MAX_DEEP_DOM = "wxMaxDeepVDomLayer";
-    public static final String KEY_PAGE_STATS_MAX_COMPONENT_NUM = "wxMaxComponentCount";
-    public static final String KEY_PAGE_STATS_WRONG_IMG_SIZE_COUNT = "wxWrongImgSizeCount";
-    public static final String KEY_PAGE_STATS_EMBED_COUNT = "wxEmbedCount";
-    public static final String KEY_PAGE_STATS_LARGE_IMG_COUNT = "wxLargeImgMaxCount";
-    public static final String KEY_PAGE_STATS_BODY_RATIO = "wxBodyRatio";
-    public static final String KEY_PAGE_STATS_SCROLLER_NUM = "wxScrollerCount";
-    public static final String KEY_PAGE_STATS_CELL_DATA_UN_RECYCLE_NUM = "wxCellDataUnRecycleCount";
-    public static final String KEY_PAGE_STATS_CELL_UN_RE_USE_NUM = "wxCellUnReUseCount";
-    public static final String KEY_PAGE_STATS_IMG_UN_RECYCLE_NUM = "wxImgUnRecycleCount";
-
-    public static final String KEY_PAGE_STATS_I_SCREEN_VIEW_COUNT = "wxInteractionScreenViewCount";
-    public static final String KEY_PAGE_STATS_I_ALL_VIEW_COUNT = "wxInteractionAllViewCount";
-    public static final String KEY_PAGE_STATS_I_COMPONENT_CREATE_COUNT = "wxInteractionComponentCreateCount";
-    public static final String KEY_PAGE_ANIM_BACK_NUM = "wxAnimationInBackCount";
-    public static final String KEY_PAGE_TIMER_BACK_NUM = "wxTimerInBackCount";
-    public static final String KEY_PAGE_STATS_ACTUAL_DOWNLOAD_TIME = "wxActualNetworkTime";
-
-    public static final String KEY_PAGE_STATS_IMG_LOAD_NUM = "wxImgLoadCount";
-    public static final String KEY_PAGE_STATS_IMG_LOAD_SUCCESS_NUM = "wxImgLoadSuccessCount";
-    public static final String KEY_PAGE_STATS_IMG_LOAD_FAIL_NUM = "wxImgLoadFailCount";
-    public static final String KEY_PAGE_STATS_NET_NUM = "wxNetworkRequestCount";
-    public static final String KEY_PAGE_STATS_NET_SUCCESS_NUM = "wxNetworkRequestSuccessCount";
-    public static final String KEY_PAGE_STATS_NET_FAIL_NUM = "wxNetworkRequestFailCount";
-    public static final String KEY_PAGE_STATS_JSLIB_INIT_TIME = "wxJSLibInitTime";
-    public static final String KEY_PAGE_STATS_VIEW_CREATE_COST = "wxViewCost";
-    public static final String KEY_PAGE_STATS_COMPONENT_CREATE_COST = "wxComponentCost";
-    public static final String KEY_PAGE_STATS_EXECUTE_JS_CALLBACK_COST = "wxExecJsCallBack";
-    public static final String KEY_PAGE_STATS_LAYOUT_TIME = "wxLayoutTime";
-
-
-    /************** value *****************/
-    public static final String VALUE_ERROR_CODE_DEFAULT = "0";
-    public static final String VALUE_BUNDLE_LOAD_LENGTH = "wxLoadedLength";
-
-    private String mInstanceId;
-    private IWXApmMonitorAdapter apmInstance;
-    private Map<String, Double> recordStatsMap;
-    public final Map<String, Long> stageMap;
-    private Map<String,Object> mPropertiesMap;
-    private boolean isFSEnd;
-    private boolean mHasInit = false;
-    private boolean mEnd = false;
-    private boolean hasRecordFistInteractionView =false;
-    public final Map<String,Object> extInfo;
-    public boolean forceStopRecordInteraction = false;
-    public Rect instanceRect;
-    public String reportPageName;
-    public boolean hasReportLayerOverDraw = false;
-    public boolean hasAddView;
-    private Handler mUIHandler;
-
-    public Set<String> exceptionRecord = new CopyOnWriteArraySet<String>();
-
-    private double interactionLayoutTime;
-    public long componentCreateTime;
-    private long interactionComponentCreateTime;
-    public long viewCreateTime;
-    private long interactionViewCreateTime;
-    //next version
-    private long wxExecJsCallBackTime;
-    private long interactionJsCallBackTime;
-
-
-    private boolean mHasRecordDetailData = false;
-
-    /**
-     * send performance value to js
-     **/
-    private boolean hasSendInteractionToJS = false;
-    public volatile boolean isReady = true;
-
-    public WXInstanceApm(String instanceId) {
-        mInstanceId = instanceId;
-        extInfo = new ConcurrentHashMap<>();
-        stageMap = new ConcurrentHashMap<>();
-        mUIHandler = new Handler(Looper.getMainLooper());
-        recordStatsMap = new ConcurrentHashMap<>();
-        mPropertiesMap = new ConcurrentHashMap<>();
-        IApmGenerator generator = WXSDKManager.getInstance().getApmGenerater();
-        if (null != generator) {
-            apmInstance = generator.generateApmInstance(WEEX_PAGE_TOPIC);
-        }
-    }
-
-    public void onInstanceReady(boolean isPreDownLoad){
-        this.isReady = true;
-        if (isPreDownLoad){
-            onStage(KEY_PAGE_STAGES_DOWN_BUNDLE_START);
-        }
-        doInit();
-        for (Map.Entry<String,Long> stage:stageMap.entrySet()){
-            sendStageInfo(stage.getKey(),stage.getValue());
-        }
-        for (Map.Entry<String,Double> stats:recordStatsMap.entrySet()){
-           sendStats(stats.getKey(),stats.getValue());
-        }
-        for (Map.Entry<String,Object> p:mPropertiesMap.entrySet()){
-           sendProperty(p.getKey(),p.getValue());
-        }
-    }
-
-    /**
-     * record event
-     */
-    public void onEvent(String name, Object value) {
-        if (null == apmInstance) {
-            return;
-        }
-        apmInstance.onEvent(name, value);
-    }
-
-    /**
-     * record stage
-     */
-    public void onStage(String name) {
-        long time =  WXUtils.getFixUnixTime();
-        onStageWithTime(name,time);
-    }
-
-    /**
-     *
-     * @param name stage
-     * @param time unixTime ,plz use WXUtils.getFixUnixTime
-     */
-    public void onStageWithTime(String name,long time){
-        if (mEnd){
-            return;
-        }
-        if (null == name){
-            return;
-        }
-        stageMap.put(name,time);
-        if (isReady){
-            sendStageInfo(name,time);
-        }
-    }
-
-    private void sendStageInfo(String name,long time){
-        if(WXAnalyzerDataTransfer.isOpenPerformance){
-            WXAnalyzerDataTransfer.transferPerformance(mInstanceId,"stage",name,time);
-        }
-
-        if (KEY_PAGE_STAGES_RENDER_ORGIGIN.equalsIgnoreCase(name)){
-            mUIHandler.postDelayed(jsPerformanceCallBack,8000);
-        }
-
-        if (null == apmInstance) {
-            return;
-        }
-
-        apmInstance.onStage(name, time);
-    }
-
-    private Runnable jsPerformanceCallBack = new Runnable() {
-        @Override
-        public void run() {
-            sendPerformanceToJS();
-        }
-    };
-
-    /**
-     * record property
-     */
-    public void addProperty(String key, Object value) {
-        if (mEnd){
-            return;
-        }
-        if (null == key || null == value){
-            return;
-        }
-        mPropertiesMap.put(key,value);
-        if (isReady){
-            sendProperty(key,value);
-        }
-    }
-
-    private void sendProperty(String key,Object value){
-        if(WXAnalyzerDataTransfer.isOpenPerformance){
-            WXAnalyzerDataTransfer.transferPerformance(mInstanceId,"properties",key,value);
-        }
-
-        if (null == apmInstance) {
-            return;
-        }
-        apmInstance.addProperty(key, value);
-    }
-
-    /**
-     * record statistic
-     */
-    public void addStats(String key, double value) {
-        if (mEnd){
-            return;
-        }
-        if (null == key){
-            return;
-        }
-        recordStatsMap.put(key,value);
-        if (isReady){
-            sendStats(key,value);
-        }
-    }
-
-    private void sendStats(String key,double value){
-        if(WXAnalyzerDataTransfer.isOpenPerformance){
-            WXAnalyzerDataTransfer.transferPerformance(mInstanceId,"stats",key,value);
-        }
-
-        if (null == apmInstance) {
-            return;
-        }
-        apmInstance.addStats(key, value);
-    }
-
-
-    public boolean hasInit(){
-        return mHasInit;
-    }
-
-    /**
-     * start record
-     */
-    public void doInit() {
-        if (!isReady){
-            return;
-        }
-        if (mHasInit){
-            return;
-        }
-        mHasInit = true;
-        if (null == apmInstance) {
-            return;
-        }
-        apmInstance.onStart(mInstanceId);
-        WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(mInstanceId);
-        String url = null == instance ? "unKnowUrl" : instance.getBundleUrl();
-        addProperty(KEY_PAGE_PROPERTIES_BUBDLE_URL, url);
-        addProperty(KEY_PROPERTIES_ERROR_CODE, VALUE_ERROR_CODE_DEFAULT);
-        addProperty(KEY_PAGE_PROPERTIES_JSLIB_VERSION, WXEnvironment.JS_LIB_SDK_VERSION);
-        addProperty(KEY_PAGE_PROPERTIES_WEEX_VERSION, WXEnvironment.WXSDK_VERSION);
-        addProperty(KEY_PAGE_PROPERTIES_WEEX_VERSION, WXEnvironment.WXSDK_VERSION);
-        addStats("wxReInitCount",WXBridgeManager.reInitCount);
-        if (null != instance){
-            addProperty(KEY_PAGE_PROPERTIES_UIKIT_TYPE, instance.getRenderType());
-        }
-
-        addProperty("wxUseRuntimeApi",WXEnvironment.sUseRunTimeApi);
-        if (instance != null && (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER
-                || instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY)) {
-            addProperty(KEY_PAGE_PROPERTIES_RENDER_TYPE, WXEnvironment.EAGLE);
-        }
-        if (null != instance) {
-            for (Map.Entry<String, String> entry : instance.getContainerInfo().entrySet()) {
-                addProperty(entry.getKey(), entry.getValue());
-            }
-        }
-    }
-
-    public void setPageName(String pageName) {
-        if (TextUtils.isEmpty(pageName)) {
-            WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(mInstanceId);
-            if (null != instance) {
-                pageName = instance.getContainerInfo().get(KEY_PAGE_PROPERTIES_CONTAINER_NAME);
-            }
-        }
-        reportPageName = null == apmInstance?pageName:apmInstance.parseReportUrl(pageName);
-        reportPageName = TextUtils.isEmpty(reportPageName) ? "emptyPageName" : reportPageName;
-        addProperty(KEY_PAGE_PROPERTIES_BIZ_ID, reportPageName);
-    }
-
-    public void onAppear(){
-        if (null == apmInstance) {
-            return;
-        }
-        apmInstance.onAppear();
-    }
-
-    public void onDisAppear(){
-        if (null == apmInstance) {
-            return;
-        }
-        apmInstance.onDisappear();
-    }
-
-    /**
-     * end record
-     */
-    public void onEnd() {
-        if (null == apmInstance || mEnd) {
-            return;
-        }
-        new Handler(Looper.getMainLooper()).removeCallbacks(delayCollectDataTask);
-        recordPerformanceDetailData();
-        exceptionRecord.clear();
-        mUIHandler.removeCallbacks(jsPerformanceCallBack);
-        onStage(KEY_PAGE_STAGES_DESTROY);
-        if (mHasInit && null != apmInstance){
-            apmInstance.onEnd();
-        }
-        mEnd = true;
-        if (WXEnvironment.isApkDebugable()){
-            printLog();
-        }
-    }
-
-    public void doDelayCollectData(){
-        new Handler(Looper.getMainLooper()).postDelayed(delayCollectDataTask,8000);
-    }
-
-    private Runnable delayCollectDataTask = new Runnable() {
-        @Override
-        public void run() {
-            recordPerformanceDetailData();
-        }
-    };
-
-
-    private void printLog(){
-        Long startDownLoad = stageMap.get(KEY_PAGE_STAGES_DOWN_BUNDLE_START);
-        Long endDownLoad = stageMap.get(KEY_PAGE_STAGES_DOWN_BUNDLE_END);
-        Long interaction = stageMap.get(KEY_PAGE_STAGES_INTERACTION);
-        Long containerReady = stageMap.get(KEY_PAGE_STAGES_CONTAINER_READY);
-        if (null != endDownLoad && null != startDownLoad){
-            WXLogUtils.d("test->", "downLoadTime: "+ (endDownLoad - startDownLoad));
-        }
-        if (null != endDownLoad && null != interaction){
-            WXLogUtils.d("test->", "renderTime: "+ (interaction - endDownLoad));
-        }
-        if (null != containerReady && null !=interaction){
-            WXLogUtils.d("test->", "showTime: "+ (interaction - containerReady));
-        }
-
-    }
-
-    public void arriveNewFsRenderTime(){
-        if (null == apmInstance){
-            return;
-        }
-        onStage(WXInstanceApm.KEY_PAGE_STAGES_NEW_FSRENDER);
-    }
-
-    public void arriveFSRenderTime() {
-        if (null == apmInstance){
-            return;
-        }
-        isFSEnd = true;
-        onStage(WXInstanceApm.KEY_PAGE_STAGES_FSRENDER);
-    }
-
-    public void arriveInteraction(WXComponent targetComponent) {
-        if (null == apmInstance || null == targetComponent || targetComponent.getInstance() == null) {
-            return;
-        }
-
-        if (WXAnalyzerDataTransfer.isOpenPerformance){
-            WXAnalyzerDataTransfer.transferInteractionInfo(targetComponent);
-        }
-
-
-        if (null == apmInstance){
-            return;
-        }
-
-        WXPerformance performanceRecord = targetComponent.getInstance().getWXPerformance();
-        if (null == performanceRecord){
-            return;
-        }
-
-        long curTime = WXUtils.getFixUnixTime();
-
-        if (WXAnalyzerDataTransfer.isInteractionLogOpen()){
-            Log.d(WXAnalyzerDataTransfer.INTERACTION_TAG, "[client][wxinteraction]"
-                + targetComponent.getInstance().getInstanceId()
-                +","+targetComponent.getComponentType()
-                +","+targetComponent.getRef()
-                +","+targetComponent.getStyles()
-                +","+targetComponent.getAttrs()
-            );
-        }
-
-        if (!hasRecordFistInteractionView){
-            onStage(KEY_PAGE_STAGES_FIRST_INTERACTION_VIEW);
-            hasRecordFistInteractionView = true;
-        }
-        if (forceStopRecordInteraction){
-            return;
-        }
-        long now = WXUtils.getFixUnixTime();
-        if (now - preUpdateTime > 50){
-            //for performance, reduce jni calls
-            WXBridgeManager.getInstance().onInteractionTimeUpdate(mInstanceId);
-            preUpdateTime = now;
-        }
-
-        interactionComponentCreateTime = componentCreateTime;
-        interactionViewCreateTime = viewCreateTime;
-        Double layoutTime = recordStatsMap.get("wxLayoutTime");
-        interactionLayoutTime = layoutTime ==null? 0:layoutTime;
-
-        performanceRecord.interactionTime = curTime - performanceRecord.renderUnixTimeOrigin;
-        performanceRecord.interactionRealUnixTime = System.currentTimeMillis();
-        onStageWithTime(KEY_PAGE_STAGES_INTERACTION,curTime);
-
-        updateDiffStats(KEY_PAGE_STATS_I_SCREEN_VIEW_COUNT, 1);
-        updateMaxStats(KEY_PAGE_STATS_I_ALL_VIEW_COUNT, performanceRecord.localInteractionViewAddCount);
-        WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
-        if (null != instance) {
-            updateMaxStats(KEY_PAGE_STATS_I_COMPONENT_CREATE_COUNT, instance.getWXPerformance().componentCount);
-        }
-    }
-
-    private long preUpdateTime = 0;
-
-    public void updateFSDiffStats(String name, double diffValue) {
-        if (null == apmInstance || isFSEnd) {
-            return;
-        }
-        updateDiffStats(name, diffValue);
-    }
-
-    public void recordPerformanceDetailData(){
-        if (mHasRecordDetailData){
-            return;
-        }
-        mHasRecordDetailData = true;
-        addStats(KEY_PAGE_STATS_VIEW_CREATE_COST,interactionViewCreateTime);
-        addStats(KEY_PAGE_STATS_COMPONENT_CREATE_COST,interactionComponentCreateTime);
-        addStats(KEY_PAGE_STATS_EXECUTE_JS_CALLBACK_COST,interactionJsCallBackTime);
-        addStats(KEY_PAGE_STATS_LAYOUT_TIME,interactionLayoutTime);
-    }
-
-    public void updateDiffStats(String name, double diffValue) {
-        if (null == apmInstance) {
-            return;
-        }
-        Double preVal = recordStatsMap.containsKey(name) ? recordStatsMap.get(name) : 0;
-        //fix by use ConcurrentHashMap,but not sure,so report if error still happen
-        if (null == preVal){
-            WXExceptionUtils.commitCriticalExceptionRT(
-                "",
-                WXErrorCode.WX_ERR_HASH_MAP_TMP,
-                "updateDiffStats",
-                "key : "+name,
-                null
-            );
-            return;
-        }
-
-        double currentValue = preVal + diffValue;
-        addStats(name, currentValue);
-    }
-
-    public void updateMaxStats(String name, double currentVal) {
-        if (null == apmInstance) {
-            return;
-        }
-        Double maxValue = recordStatsMap.containsKey(name) ? recordStatsMap.get(name) : 0;
-        //fix by use ConcurrentHashMap,but not sure,so report if error still happen
-        if (null == maxValue){
-            WXExceptionUtils.commitCriticalExceptionRT(
-                "",
-                WXErrorCode.WX_ERR_HASH_MAP_TMP,
-                "updateMaxStats",
-                "key : "+name,
-                null
-            );
-            return;
-        }
-        if (maxValue < currentVal) {
-            maxValue = currentVal;
-            addStats(name, maxValue);
-        }
-    }
-
-    public void updateRecordInfo(Map<String, Object> extParams) {
-        if (null == apmInstance || null == extParams) {
-            return;
-        }
-
-        addPropeyFromExtParms(KEY_PAGE_PROPERTIES_REQUEST_TYPE, KEY_PAGE_PROPERTIES_REQUEST_TYPE, extParams);
-        addPropeyFromExtParms("cacheType", KEY_PAGE_PROPERTIES_CACHE_TYPE, extParams);
-        addPropeyFromExtParms("zCacheInfo", KEY_PAGE_PROPERTIES_CACHE_INFO, extParams);
-
-        addStats(KEY_PAGE_STATS_JSLIB_INIT_TIME, WXEnvironment.sJSLibInitTime);
-        addProperty(KEY_PAGE_PROPERTIES_JS_FM_INI, WXEnvironment.JsFrameworkInit);
-
-        Object wxNetLibDownBundleTime = extParams.get("actualNetworkTime");
-        if (wxNetLibDownBundleTime instanceof Long) {
-            updateDiffStats(KEY_PAGE_STATS_ACTUAL_DOWNLOAD_TIME, ((Long)wxNetLibDownBundleTime).doubleValue());
-        }
-    }
-
-    private void addPropeyFromExtParms(String fromKey, String toKey, Map<String, Object> extParams) {
-        Object value = extParams.get(fromKey);
-        if (value instanceof String) {
-            addProperty(toKey, value);
-        }
-    }
-
-    /************** called by IWXHttpAdapter implementer *****************/
-
-    public void actionNetRequest() {
-        if (!isFSEnd) {
-            updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_REQUEST_NUM, 1);
-        }
-        updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_NET_NUM, 1);
-    }
-
-    public void actionNetResult(boolean succeed, String errorCode) {
-        if (succeed) {
-            updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_NET_SUCCESS_NUM, 1);
-        } else {
-            updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_NET_FAIL_NUM, 1);
-        }
-    }
-
-    /************** called by IWXImgLoaderAdapter implementer *****************/
-
-    public void actionLoadImg() {
-        updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_IMG_LOAD_NUM, 1);
-    }
-
-    public void actionLoadImgResult(boolean succeed, String errorCode) {
-        if (succeed) {
-            updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_IMG_LOAD_SUCCESS_NUM, 1);
-        } else {
-            updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_IMG_LOAD_FAIL_NUM, 1);
-        }
-    }
-
-    public void sendPerformanceToJS() {
-        if (hasSendInteractionToJS) {
-            return;
-        }
-        hasSendInteractionToJS = true;
-        WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(mInstanceId);
-        if (null == instance) {
-            return;
-        }
-
-        Map<String,String> sendProperties = new HashMap<>(2);
-        sendProperties.put(KEY_PAGE_PROPERTIES_BIZ_ID,reportPageName);
-        sendProperties.put(KEY_PAGE_PROPERTIES_BUBDLE_URL,instance.getBundleUrl());
-
-        Map<String,Long> sendStage = new HashMap<>(1);
-        sendStage.put(KEY_PAGE_STAGES_INTERACTION,instance.getWXPerformance().interactionRealUnixTime);
-
-        Map<String, Object> data = new HashMap<>(2);
-        data.put("stage",sendStage);
-        data.put("properties",sendProperties);
-
-        instance.fireGlobalEventCallback("wx_apm", data);
-    }
-
-
-    public String toPerfString() {
-        Long start = stageMap.get(KEY_PAGE_STAGES_RENDER_ORGIGIN);
-        Long end = stageMap.get(KEY_PAGE_STAGES_INTERACTION);
-        Long wxNewFsRender = stageMap.get(KEY_PAGE_STAGES_NEW_FSRENDER);
-        StringBuilder builder = new StringBuilder();
-        if(start != null && end != null){
-            builder.append("interactiveTime " + (end - start) + "ms");
-        }
-        if(wxNewFsRender != null){
-            builder.append(" wxNewFsRender " + (wxNewFsRender) + "ms");
-        }
-        return builder.toString();
-   }
-
-   public void updateNativePerformanceData(Map<String,String> nativePerformanceData){
-        if (null == nativePerformanceData){
-            return;
-        }
-        for (Map.Entry<String,String> entry : nativePerformanceData.entrySet()){
-            double value = -1;
-            try {
-                value = Double.valueOf(entry.getValue());
-            }catch (Exception e){
-                e.printStackTrace();
-            }
-            if (value != -1){
-                recordStatsMap.put(entry.getKey(),value);
-            }
-        }
-   }
- }
diff --git a/android/sdk/src/main/java/com/taobao/weex/performance/WXStateRecord.java b/android/sdk/src/main/java/com/taobao/weex/performance/WXStateRecord.java
deleted file mode 100644
index 0711af2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/performance/WXStateRecord.java
+++ /dev/null
@@ -1,211 +0,0 @@
-/**
- * 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
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-
-package com.taobao.weex.performance;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.ConcurrentLinkedQueue;
-
-import android.support.annotation.NonNull;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.ui.IFComponentHolder;
-import com.taobao.weex.utils.WXUtils;
-
-/**
- * @author zhongcang
- * @date 2019/6/19
- */
-public class WXStateRecord {
-
-    private RecordList<Info> mExceptionHistory;
-    private RecordList<Info> mActionHistory;
-    private RecordList<Info> mJsfmInitHistory;
-    private RecordList<Info> mJscCrashHistory;
-    private RecordList<Info> mJscReloadHistory;
-    private RecordList<Info> mJsThradWatchHistory;
-    private RecordList<Info> mIPCExceptionHistory;
-
-    private static class SingleTonHolder {
-        private static final WXStateRecord S_INSTANCE = new WXStateRecord();
-    }
-
-    public static WXStateRecord getInstance() {
-        return SingleTonHolder.S_INSTANCE;
-    }
-
-    private WXStateRecord() {
-        mExceptionHistory = new RecordList<>(10);
-        mActionHistory = new RecordList<>(20);
-        mJsfmInitHistory = new RecordList<>(10);
-        mJscCrashHistory = new RecordList<>(10);
-        mJscReloadHistory = new RecordList<>(10);
-        mJsThradWatchHistory = new RecordList<>(20);
-        mIPCExceptionHistory = new RecordList<>(20);
-    }
-
-    /**
-     * check history exception (may be cause ws)
-     */
-    public void recordException(String instanceId, String exception) {
-        String shortException = exception.length() > 200 ?exception.substring(0,200) : exception;
-        recordCommon(mExceptionHistory,new Info(WXUtils.getFixUnixTime(), instanceId, shortException));
-    }
-
-    /**
-     * check history action (may be occupy cpu by preInstance or some task)
-     */
-    public void recordAction(String instanceId, String action) {
-        recordCommon(mActionHistory,new Info(WXUtils.getFixUnixTime(), instanceId, action));
-    }
-
-    public void recordIPCException (String instanceId,String exception){
-        String shortException = exception.length() > 200 ?exception.substring(0,200) : exception;
-        recordCommon(mIPCExceptionHistory,new Info(WXUtils.getFixUnixTime(), instanceId, shortException));
-    }
-
-    /**
-     * check onJSFMInit time,and we know when jsfm is init sucess in reloadJsEngine case
-     */
-    public void onJSFMInit() {
-        recoreJsfmInitHistory("setJsfmVersion");
-    }
-
-    public void recoreJsfmInitHistory(String msg){
-        recordCommon(mJsfmInitHistory,new Info(WXUtils.getFixUnixTime(), "JSFM", msg));
-    }
-
-    public void recordJsThreadWatch(String msg){
-        recordCommon(mJsThradWatchHistory,new Info(WXUtils.getFixUnixTime(), "jsWatch", msg));
-    }
-
-    /**
-     * check onJSEngineReload time,and we know how many times reload and each reload time
-     */
-    public void onJSEngineReload(String instanceId) {
-        recordCommon(mJscReloadHistory,new Info(WXUtils.getFixUnixTime(), instanceId, "onJSEngineReload"));
-    }
-
-    /**
-     * check jsc crash time,and we know how many times jscCrash and each crash time
-     */
-    public void onJSCCrash(String instanceId) {
-        recordCommon(mJscCrashHistory,new Info(WXUtils.getFixUnixTime(), instanceId, "onJSCCrash"));
-    }
-
-    private void recordCommon(RecordList<Info> list ,Info info){
-        if (null == list || null == info){
-            return;
-        }
-        try {
-            list.add(info);
-            if (!list.isEmpty() && list.size()>list.maxSize){
-                list.poll();
-            }
-        }catch (Throwable e){
-            e.getStackTrace();
-        }
-    }
-
-    public Map<String, String> getStateInfo() {
-        Map<String, String> stateInfo = new HashMap<>(5);
-        stateInfo.put("reInitCount", String.valueOf(WXBridgeManager.reInitCount));
-
-        int size = mExceptionHistory.size()+mActionHistory.size()+mJsfmInitHistory.size()
-            +mJscCrashHistory.size()+mJscReloadHistory.size()+mJsThradWatchHistory.size();
-
-        List<Info> reportTimeLineInfo = new ArrayList<>(size);
-        reportTimeLineInfo.addAll(mExceptionHistory);
-        reportTimeLineInfo.addAll(mActionHistory);
-        reportTimeLineInfo.addAll(mJsfmInitHistory);
-        reportTimeLineInfo.addAll(mJscCrashHistory);
-        reportTimeLineInfo.addAll(mJscReloadHistory);
-        reportTimeLineInfo.addAll(mJsThradWatchHistory);
-        reportTimeLineInfo.addAll(mIPCExceptionHistory);
-        Collections.sort(reportTimeLineInfo);
-        stateInfo.put("stateInfoList",reportTimeLineInfo.toString());
-
-        IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
-        if (null != adapter && "true".equalsIgnoreCase(adapter.getConfig("wxapm","dumpIpcPageInfo","true"))){
-            stateInfo.put("pageQueueInfo",WXBridgeManager.getInstance().dumpIpcPageInfo());
-        }
-        return stateInfo;
-    }
-
-    private static class RecordList<E> extends ConcurrentLinkedQueue<E> {
-        private int maxSize;
-
-        public RecordList(int maxSize) {
-            super();
-            this.maxSize = maxSize;
-        }
-    }
-
-    private static class Info implements Comparable<Info>{
-        private long time;
-        private String instanceId;
-        private String msg;
-
-        public Info(long time, String instance, String msg) {
-            this.time = time;
-            this.instanceId = instance;
-            this.msg = msg;
-        }
-
-        @Override
-        public String toString() {
-            return new StringBuilder()
-                .append('[').append(instanceId).append(',').append(time).append(',').append(msg).append("]->")
-                .toString();
-        }
-
-        @Override
-        public int compareTo(@NonNull Info next) {
-            if (this.time == next.time){
-                return 0;
-            }
-            return this.time > next.time? 1:-1;
-        }
-    }
-
-    public void startJSThreadWatchDog(){
-        WXBridgeManager.getInstance().post(jsThreadWatchTask);
-    }
-
-    private  long jsThreadTime =-1;
-
-    private Runnable jsThreadWatchTask = new Runnable() {
-        @Override
-        public void run() {
-            if (jsThreadTime == -1){
-                jsThreadTime = WXUtils.getFixUnixTime();
-            }
-            long diff = WXUtils.getFixUnixTime() - jsThreadTime;
-            recordJsThreadWatch("diff:"+diff);
-            jsThreadTime = WXUtils.getFixUnixTime();
-            WXBridgeManager.getInstance().postDelay(jsThreadWatchTask,500);
-        }
-    };
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/performance/WhiteScreenUtils.java b/android/sdk/src/main/java/com/taobao/weex/performance/WhiteScreenUtils.java
deleted file mode 100644
index 6e7543e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/performance/WhiteScreenUtils.java
+++ /dev/null
@@ -1,179 +0,0 @@
-/**
- * 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
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.performance;
-
-import android.text.TextUtils;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewParent;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.ui.IFComponentHolder;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.utils.WXViewUtils;
-import org.json.JSONObject;
-
-/**
- * @author zhongcang
- * @date 2019/5/30
- */
-public class WhiteScreenUtils {
-
-    public static boolean doWhiteScreenCheck() {
-        IWXConfigAdapter configAdapter = WXSDKManager.getInstance().getWxConfigAdapter();
-        if (null == configAdapter) {
-            return false;
-        }
-        double randomValue = Math.random() * 100;
-        double max = 100;
-        try {
-            String configValue = configAdapter.getConfig("wxapm", "new_ws_sampling", "100");
-            max = Double.valueOf(configValue);
-        } catch (Exception e) {
-            e.printStackTrace();
-        }
-        return randomValue < max;
-    }
-
-    public static boolean isWhiteScreen(WXSDKInstance instance) {
-        if (null == instance) {
-            return false;
-        }
-        View v = instance.getContainerView();
-        if (!(v instanceof ViewGroup)) {
-            return false;
-        }
-
-        if (!WXViewUtils.isViewVisible(v) || !checkParentVisible(v.getParent())){
-            return false;
-        }
-        if (isInWhiteList(instance)){
-            return false;
-        }
-        return !hasLeafViewOrSizeIgnore(v,3);
-    }
-
-    private static boolean isInWhiteList(WXSDKInstance instance){
-        IWXConfigAdapter configAdapter = WXSDKManager.getInstance().getWxConfigAdapter();
-        if (null == configAdapter){
-            return false;
-        }
-        String whiteList = configAdapter.getConfig("wxapm","ws_white_list",null);
-        if (TextUtils.isEmpty(whiteList)){
-            return false;
-        }
-        try {
-            String[] urlList = whiteList.split(";");
-            for (String whiteUrl : urlList){
-                if (instance.getBundleUrl() != null && instance.getBundleUrl().contains(whiteUrl)){
-                    return true;
-                }
-            }
-        }catch (Exception e){
-            e.printStackTrace();
-        }
-
-        return false;
-    }
-
-    private static boolean checkParentVisible(ViewParent parent){
-        //root view getParent is null
-        if (!(parent instanceof View)){
-            return true;
-        }
-        View vp = (View)parent;
-        boolean visible = vp.getVisibility() == View.VISIBLE && vp.getAlpha()>0;
-        if (!visible){
-            return false;
-        }
-        return checkParentVisible(vp.getParent());
-    }
-
-    private static boolean hasLeafViewOrSizeIgnore(View v,int checkDeep) {
-
-        if (!(v instanceof ViewGroup)) {
-            return true;
-        }
-
-        if (checkDeep > 0){
-            if ( v.getHeight() < 10 || v.getWidth() < 10) {
-                return true;
-            }
-            checkDeep--;
-        }
-
-        ViewGroup group = (ViewGroup)v;
-        for (int i = 0; i < group.getChildCount(); i++) {
-            View child = group.getChildAt(i);
-            boolean res = hasLeafViewOrSizeIgnore(child,checkDeep);
-            if (res) {
-                return true;
-            }
-        }
-        return false;
-    }
-
-    /**
-     * get instance viewTree && component tree msg
-     */
-    public static String takeViewTreeSnapShot(WXSDKInstance instance) {
-        if (null == instance) {
-            return "nullInstance";
-        }
-        View v = instance.getContainerView();
-        JSONObject root = geViewDetailTreeMsg(v);
-        if (null != root) {
-            return root.toString();
-        }
-        return "";
-    }
-
-    private static JSONObject geViewDetailTreeMsg(View view) {
-        if (null == view) {
-            return null;
-        }
-        JSONObject node = new JSONObject();
-        try {
-            node.put("width", view.getWidth());
-            node.put("height", view.getHeight());
-            int[] location = new int[2];
-            location[0] = -1;
-            location[1] = -1;
-            view.getLocationOnScreen(location);
-            node.put("x", location[0]);
-            node.put("y", location[1]);
-
-            if (view instanceof ViewGroup) {
-                node.put("type", view.getClass().getSimpleName());
-                ViewGroup group = (ViewGroup)view;
-                for (int i = 0; i < group.getChildCount(); i++) {
-                    node.put("child_"+i, geViewDetailTreeMsg(group.getChildAt(i)));
-                }
-            } else {
-                node.put("type", view.getClass().getSimpleName());
-            }
-
-        } catch (Exception e) {
-            e.printStackTrace();
-        }
-        return node;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/render/WXAbstractRenderContainer.java b/android/sdk/src/main/java/com/taobao/weex/render/WXAbstractRenderContainer.java
deleted file mode 100644
index ade7339..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/render/WXAbstractRenderContainer.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.render;
-
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-import android.widget.FrameLayout;
-import com.taobao.weex.WXSDKInstance;
-import java.lang.ref.WeakReference;
-
-public class WXAbstractRenderContainer extends FrameLayout {
-
-    protected  WeakReference<WXSDKInstance> mSDKInstance;
-    protected boolean mHasConsumeEvent = false;
-
-    public WXAbstractRenderContainer(@NonNull Context context) {
-        super(context);
-    }
-
-    public WXAbstractRenderContainer(@NonNull Context context, @Nullable AttributeSet attrs) {
-        super(context, attrs);
-    }
-
-    public WXAbstractRenderContainer(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
-        super(context, attrs, defStyleAttr);
-    }
-
-    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
-    public WXAbstractRenderContainer(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) {
-        super(context, attrs, defStyleAttr, defStyleRes);
-    }
-
-    public void setSDKInstance(WXSDKInstance instance) {
-        mSDKInstance = new WeakReference<>(instance);
-    }
-
-    @Override
-    protected void onSizeChanged(int w, int h, int oldw, int oldh) {
-        super.onSizeChanged(w, h, oldw, oldh);
-        WXSDKInstance instance;
-        if (mSDKInstance != null && (instance = mSDKInstance.get()) != null) {
-            //re-render instance
-            instance.setSize(w, h);
-        }
-    }
-
-
-    @Override
-    public boolean dispatchTouchEvent(MotionEvent ev) {
-        mHasConsumeEvent = true;
-        return super.dispatchTouchEvent(ev);
-    }
-
-    public boolean hasConsumeEvent(){
-        return mHasConsumeEvent;
-    }
-
-    public void createInstanceRenderView(String instanceId){
-
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/tracing/Stopwatch.java b/android/sdk/src/main/java/com/taobao/weex/tracing/Stopwatch.java
deleted file mode 100644
index 10b8be2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/tracing/Stopwatch.java
+++ /dev/null
@@ -1,132 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.tracing;
-
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.List;
-
-/**
- * Created by moxun on 2017/6/2.
- */
-
-public class Stopwatch {
-  private static final ThreadLocal<Stopwatch> sThreadLocal = new ThreadLocal<>();
-  private long startNanos;
-  private List<ProcessEvent> splits = new ArrayList<>();
-  private long startMillis;
-
-  private static void prepare() {
-    if (sThreadLocal.get() == null) {
-      sThreadLocal.set(new Stopwatch());
-    }
-  }
-
-  public static void tick() {
-    if (WXTracing.isAvailable()) {
-      try {
-        prepare();
-        if (sThreadLocal.get().startNanos != 0L) {
-          WXLogUtils.w("Stopwatch", "Stopwatch is not reset");
-        }
-        sThreadLocal.get().startNanos = System.nanoTime();
-        sThreadLocal.get().startMillis = System.currentTimeMillis();
-      } catch (Throwable t) {
-        t.printStackTrace();
-      }
-    }
-  }
-
-  public static void split(String fname) {
-    if (WXTracing.isAvailable()) {
-      try {
-        ProcessEvent event = new ProcessEvent();
-        long start = sThreadLocal.get().startMillis;
-        double millis = tackAndTick();
-        event.fname = fname;
-        event.duration = millis;
-        event.startMillis = start;
-        sThreadLocal.get().splits.add(event);
-      } catch (Throwable throwable) {
-        throwable.printStackTrace();
-      }
-    }
-  }
-
-  public static List<ProcessEvent> getProcessEvents() {
-    if (WXTracing.isAvailable()) {
-      tack();
-      List<ProcessEvent> existedEvents = sThreadLocal.get().splits;
-      sThreadLocal.get().splits = new ArrayList<>();
-      return existedEvents;
-    } else {
-      return Collections.emptyList();
-    }
-  }
-
-  public static double tack() {
-    if (WXTracing.isAvailable()) {
-      try {
-        long startNanos = sThreadLocal.get().startNanos;
-        if (startNanos == 0L) {
-          WXLogUtils.w("Stopwatch", "Should call Stopwatch.tick() before Stopwatch.tack() called");
-        }
-        long nanos = System.nanoTime() - startNanos;
-        sThreadLocal.get().startNanos = 0L;
-        return nanosToMillis(nanos);
-      } catch (Throwable throwable) {
-        throwable.printStackTrace();
-      }
-    }
-    return -1;
-  }
-
-  public static long lastTickStamp() {
-    if (WXTracing.isAvailable()) {
-      try {
-        return sThreadLocal.get().startMillis;
-      } catch (Throwable t) {
-        t.printStackTrace();
-      }
-    }
-    return -1;
-  }
-
-  public static double tackAndTick() {
-    double ms = tack();
-    tick();
-    return ms;
-  }
-
-  public static double nanosToMillis(long nanos) {
-    return nanos / 1000000.0;
-  }
-
-  public static double millisUntilNow(long startNanos) {
-    return nanosToMillis(System.nanoTime() - startNanos);
-  }
-
-  public static class ProcessEvent {
-    public String fname;
-    public double duration;
-    public long startMillis;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/tracing/WXTracing.java b/android/sdk/src/main/java/com/taobao/weex/tracing/WXTracing.java
deleted file mode 100644
index 0dc11ce..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/tracing/WXTracing.java
+++ /dev/null
@@ -1,129 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.tracing;
-
-import android.os.Looper;
-import android.util.SparseArray;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.ITracingAdapter;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.Map;
-import java.util.concurrent.atomic.AtomicInteger;
-
-/**
- * Created by moxun on 2017/6/6.
- */
-
-public class WXTracing {
-  private static final AtomicInteger sIdGenerator = new AtomicInteger(0);
-
-  public static int nextId() {
-    return sIdGenerator.getAndIncrement();
-  }
-
-  public static boolean isAvailable() {
-    return WXEnvironment.isApkDebugable();
-  }
-
-  public static synchronized void submit(TraceEvent event) {
-    ITracingAdapter tracingAdapter = WXSDKManager.getInstance().getTracingAdapter();
-    if (tracingAdapter != null) {
-      tracingAdapter.submitTracingEvent(event);
-    }
-  }
-
-  public static class TraceEvent {
-    public String fname;
-    public String tname;
-    public String ph;
-    public int traceId;
-    public long ts;
-    public String iid;
-    public String ref;
-    public String parentRef;
-    public String name;
-    public String classname;
-    public int parentId = -1;
-    public double duration;
-
-    /**
-     * Internal use
-     */
-    public SparseArray<TraceEvent> subEvents;
-    public String payload;
-    public double parseJsonTime;
-    public boolean isSegment;
-    public Map<String, Object> extParams;
-    public boolean firstScreenFinish;
-
-    private boolean submitted;
-
-    public TraceEvent() {
-      ts = System.currentTimeMillis();
-      traceId = nextId();
-      tname = currentThreadName();
-    }
-
-    public void submit() {
-      if (!submitted) {
-        submitted = true;
-        WXTracing.submit(this);
-      } else {
-        WXLogUtils.w("WXTracing", "Event " + traceId + " has been submitted.");
-      }
-    }
-  }
-
-  public static String currentThreadName() {
-    Thread thread = Thread.currentThread();
-    String name = thread.getName();
-
-    if ("WeexJSBridgeThread".equals(name)) {
-      return "JSThread";
-    } else if ("WeeXDomThread".equals(name)) {
-      return "DOMThread";
-    } else if (Looper.getMainLooper() == Looper.myLooper()) {
-      return "UIThread";
-    }
-
-    return name;
-  }
-
-  public static TraceEvent newEvent(String fname, String instanceId, int parentId) {
-    WXTracing.TraceEvent traceEvent = new TraceEvent();
-    traceEvent.fname = fname;
-    traceEvent.iid = instanceId;
-    traceEvent.traceId = WXTracing.nextId();
-    traceEvent.parentId = parentId;
-    return traceEvent;
-  }
-
-  public static class TraceInfo {
-    public int rootEventId;
-    public long domQueueTime;
-    public long uiQueueTime;
-    public long domThreadStart = -1;
-    public long domThreadNanos;
-    public long uiThreadStart = -1;
-    public long uiThreadNanos;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/ComponentCreator.java b/android/sdk/src/main/java/com/taobao/weex/ui/ComponentCreator.java
deleted file mode 100644
index c2e7f15..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/ComponentCreator.java
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Created by sospartan on 7/27/16.
- */
-public interface ComponentCreator {
-  WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/ExternalLoaderComponentHolder.java b/android/sdk/src/main/java/com/taobao/weex/ui/ExternalLoaderComponentHolder.java
deleted file mode 100644
index b33445c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/ExternalLoaderComponentHolder.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import android.util.Pair;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.Map;
-import java.util.Set;
-
-/**
- * Created by sospartan on 8/26/16.
- */
-public class ExternalLoaderComponentHolder implements IFComponentHolder {
-  public static final String TAG = "SimpleComponentHolder";
-  private Map<String, Invoker> mPropertyInvokers;
-  private Map<String, Invoker> mMethodInvokers;
-  private final IExternalComponentGetter mClzGetter;
-  private final String mType;
-  private Class mClass;
-
-
-  public ExternalLoaderComponentHolder(String type,IExternalComponentGetter clzGetter) {
-    this.mClzGetter = clzGetter;
-    mType = type;
-  }
-
-  @Override
-  public void loadIfNonLazy() {
-  }
-
-  private synchronized boolean generate(){
-    if(mClass==null){
-      return false;
-    }
-
-    Pair<Map<String, Invoker>, Map<String, Invoker>> methodPair = SimpleComponentHolder.getMethods(mClass);
-    mPropertyInvokers = methodPair.first;
-    mMethodInvokers = methodPair.second;
-    return true;
-  }
-
-  @Override
-  public synchronized WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-    if (mClass == null) {
-      mClass = mClzGetter.getExternalComponentClass(mType, instance);
-    }
-    ComponentCreator creator = new SimpleComponentHolder.ClazzComponentCreator(mClass);
-    WXComponent component = creator.createInstance(instance, parent, basicComponentData);
-
-    component.bindHolder(this);
-    return component;
-  }
-
-  @Override
-  public synchronized Invoker getPropertyInvoker(String name){
-    if (mPropertyInvokers == null && !generate()) {
-      return null;
-    }
-
-    return mPropertyInvokers.get(name);
-  }
-
-  @Override
-  public Invoker getMethodInvoker(String name) {
-    if(mMethodInvokers == null && !generate()){
-      return null;
-    }
-    return mMethodInvokers.get(name);
-  }
-
-  @Override
-  public synchronized String[] getMethods() {
-    if(mMethodInvokers == null && !generate()){
-      //generate failed
-      return new String[0];
-    }
-    Set<String> keys = mMethodInvokers.keySet();
-    return keys.toArray(new String[keys.size()]);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/IExternalComponentGetter.java b/android/sdk/src/main/java/com/taobao/weex/ui/IExternalComponentGetter.java
deleted file mode 100644
index 63aaf5c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/IExternalComponentGetter.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by zhengshihan on 16/8/25.
- */
-public interface IExternalComponentGetter {
-    Class<? extends WXComponent> getExternalComponentClass(String type, WXSDKInstance instance);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/IExternalModuleGetter.java b/android/sdk/src/main/java/com/taobao/weex/ui/IExternalModuleGetter.java
deleted file mode 100644
index 80f0257..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/IExternalModuleGetter.java
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import android.content.Context;
-
-import com.taobao.weex.common.WXModule;
-
-/**
- * Created by zhengshihan on 16/8/25.
- */
-public interface IExternalModuleGetter {
-    Class<? extends WXModule> getExternalModuleClass(String type, Context context);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/IFComponentHolder.java b/android/sdk/src/main/java/com/taobao/weex/ui/IFComponentHolder.java
deleted file mode 100644
index 45344d4..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/IFComponentHolder.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.bridge.JavascriptInvokable;
-
-/**
- * Created by sospartan on 6/23/16.
- */
-public interface IFComponentHolder extends ComponentCreator,JavascriptInvokable {
-
-    /** Prepare component if not a lazy load componnet.**/
-    void loadIfNonLazy();
-
-    Invoker getPropertyInvoker(String name);
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/RenderContextImpl.java b/android/sdk/src/main/java/com/taobao/weex/ui/RenderContextImpl.java
deleted file mode 100644
index 852becf..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/RenderContextImpl.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.dom.RenderContext;
-import com.taobao.weex.ui.component.WXComponent;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-
-/**
- * Class for rendering view. Method in this class should be run in main thread.
- * This class is also <strong>not</storng> thread safe.
- */
-class RenderContextImpl implements RenderContext {
-
-  private Map<String, WXComponent> mRegistry;
-  private WXSDKInstance mWXSDKInstance;
-
-  public RenderContextImpl(WXSDKInstance instance) {
-    mWXSDKInstance = instance;
-    mRegistry = new ConcurrentHashMap<>();
-  }
-
-  public void destroy() {
-    mWXSDKInstance = null;
-    try {
-      mRegistry.clear();
-    } catch (Throwable e) {
-      e.printStackTrace();
-    }
-  }
-
-  public WXSDKInstance getWXSDKInstance() {
-    return mWXSDKInstance;
-  }
-
-  @Override
-  public WXSDKInstance getInstance() {
-    return mWXSDKInstance;
-  }
-
-  @Override
-  public WXComponent getComponent(String ref) {
-    return mRegistry.get(ref);
-  }
-
-  public void registerComponent(String ref, WXComponent comp) {
-    mRegistry.put(ref, comp);
-  }
-
-  @Override
-  public WXComponent unregisterComponent(String ref) {
-    return mRegistry.remove(ref);
-  }
-
-  public int getComponentCount(){
-    return mRegistry.size();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/SimpleComponentHolder.java b/android/sdk/src/main/java/com/taobao/weex/ui/SimpleComponentHolder.java
deleted file mode 100644
index afd992a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/SimpleComponentHolder.java
+++ /dev/null
@@ -1,235 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import android.util.Pair;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.bridge.MethodInvoker;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXComponentProp;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.lang.annotation.Annotation;
-import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-import java.util.HashMap;
-import java.util.Map;
-import java.util.Set;
-
-import static com.taobao.weex.bridge.WXBridgeManager.METHOD_REGISTER_COMPONENTS;
-
-/**
- * Created by sospartan on 6/12/16.
- */
-public class SimpleComponentHolder implements IFComponentHolder{
-  public static final String TAG = "SimpleComponentHolder";
-  private final Class<? extends WXComponent> mClz;
-  private Map<String, Invoker> mPropertyInvokers;
-  private Map<String, Invoker> mMethodInvokers;
-  private ComponentCreator mCreator;
-
-  public static class ClazzComponentCreator implements ComponentCreator{
-
-    private Constructor<? extends WXComponent> mConstructor;
-    private final Class<? extends WXComponent> mCompClz;
-
-    public ClazzComponentCreator(Class<? extends WXComponent> c){
-      mCompClz = c;
-    }
-
-    private void loadConstructor() {
-      Class<? extends WXComponent> c = mCompClz;
-      Constructor<? extends WXComponent> constructor;
-      try {
-        constructor = c.getConstructor(WXSDKInstance.class, WXVContainer.class, BasicComponentData.class);
-      } catch (NoSuchMethodException e) {
-        WXLogUtils.d("ClazzComponentCreator", "Use deprecated component constructor");
-        try {
-          //compatible deprecated constructor with 4 args
-          constructor = c.getConstructor(WXSDKInstance.class, WXVContainer.class, boolean.class, BasicComponentData.class);
-        } catch (NoSuchMethodException e1) {
-          try {
-            //compatible deprecated constructor with 5 args
-            constructor = c.getConstructor(WXSDKInstance.class, WXVContainer.class, String.class, boolean.class, BasicComponentData.class);
-          } catch (NoSuchMethodException e2) {
-            throw new WXRuntimeException("Can't find constructor of component.");
-          }
-        }
-      }
-      mConstructor = constructor;
-    }
-
-    @Override
-    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-      if(mConstructor == null){
-        loadConstructor();
-      }
-      int parameters = mConstructor.getParameterTypes().length;
-      WXComponent component;
-
-      if(parameters == 3){
-        component =  mConstructor.newInstance(instance,parent, basicComponentData);
-      }else if(parameters == 4){
-        component =  mConstructor.newInstance(instance,parent,false, basicComponentData);
-      }else{
-        //compatible deprecated constructor
-        component =  mConstructor.newInstance(instance,parent,instance.getInstanceId(),parent.isLazy());
-      }
-      return component;
-    }
-  }
-
-  public SimpleComponentHolder(Class<? extends WXComponent> clz) {
-    this(clz,new ClazzComponentCreator(clz));
-  }
-
-  public SimpleComponentHolder(Class<? extends WXComponent> clz,ComponentCreator customCreator) {
-    this.mClz = clz;
-    this.mCreator = customCreator;
-  }
-
-  @Override
-  public void loadIfNonLazy() {
-    Annotation[] annotations = mClz.getDeclaredAnnotations();
-    for (Annotation annotation :
-      annotations) {
-      if (annotation instanceof Component){
-        if(!((Component) annotation).lazyload() && mMethodInvokers == null){
-          generate();
-        }
-        return;
-      }
-    }
-  }
-
-  private synchronized void generate(){
-    if(WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d(TAG, "Generate Component:" + mClz.getSimpleName());
-    }
-
-    Pair<Map<String, Invoker>, Map<String, Invoker>> methodPair = getMethods(mClz);
-    mPropertyInvokers = methodPair.first;
-    mMethodInvokers = methodPair.second;
-  }
-
-  public static Pair<Map<String,Invoker>,Map<String,Invoker>> getMethods(Class clz){
-    Map<String, Invoker> methods = new HashMap<>();
-    Map<String, Invoker> mInvokers = new HashMap<>();
-
-    Annotation[] annotations;
-    Annotation anno;
-    try {
-      for (Method method : clz.getMethods()) {
-        try {
-          annotations = method.getDeclaredAnnotations();
-          for (int i = 0, annotationsCount = annotations.length;
-               i < annotationsCount; ++i) {
-            anno = annotations[i];
-            if(anno == null){
-              continue;
-            }
-            if (anno instanceof WXComponentProp) {
-              String name = ((WXComponentProp) anno).name();
-              methods.put(name, new MethodInvoker(method,true));
-              break;
-            }else if(anno instanceof JSMethod){
-              JSMethod methodAnno = (JSMethod)anno;
-              String name = methodAnno.alias();
-              if(JSMethod.NOT_SET.equals(name)){
-                name = method.getName();
-              }
-              mInvokers.put(name, new MethodInvoker(method,methodAnno.uiThread()));
-              break;
-            }
-          }
-        } catch (ArrayIndexOutOfBoundsException | IncompatibleClassChangeError e) {
-          //ignore: getDeclaredAnnotations may throw this
-        }
-      }
-    }catch (IndexOutOfBoundsException e){
-      e.printStackTrace();
-      //ignore: getMethods may throw this
-    }catch (Exception e){ // in meizhu mobile, throw class not found exception in getMethods
-      WXLogUtils.e(TAG, e);
-    }
-    return new Pair<>(methods,mInvokers);
-  }
-
-
-
-  @Override
-  public synchronized WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-    WXComponent component = mCreator.createInstance(instance, parent, basicComponentData);
-
-    component.bindHolder(this);
-    return component;
-  }
-
-  @Override
-  public synchronized Invoker getPropertyInvoker(String name){
-      if (mPropertyInvokers == null) {
-        generate();
-      }
-
-    return mPropertyInvokers.get(name);
-  }
-
-  @Override
-  public Invoker getMethodInvoker(String name) {
-    if(mMethodInvokers == null){
-      generate();
-    }
-    return mMethodInvokers.get(name);
-  }
-
-  @Override
-  public synchronized String[] getMethods() {
-    if(mMethodInvokers == null){
-      generate();
-    }
-    Set<String> keys = mMethodInvokers.keySet();
-    try {
-      return keys.toArray(new String[keys.size()]);
-    } catch (Throwable throwable) {
-      if(mClz != null) {
-        String name = mClz.getName();
-        String errorMsg = name + ": gen methods failed";
-        WXExceptionUtils.commitCriticalExceptionRT(null,
-                WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT,
-                METHOD_REGISTER_COMPONENTS, errorMsg,
-                null);
-      }
-
-      return new String[1];
-    }
-
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/WXComponentRegistry.java b/android/sdk/src/main/java/com/taobao/weex/ui/WXComponentRegistry.java
deleted file mode 100644
index 9aaf6a0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/WXComponentRegistry.java
+++ /dev/null
@@ -1,148 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import android.text.TextUtils;
-import android.util.Log;
-
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.WXException;
-import com.taobao.weex.ui.config.AutoScanConfigRegister;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.cache.RegisterCache;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map;
-import java.util.Objects;
-import java.util.concurrent.ConcurrentHashMap;
-
-/**
- * All components must be registered within this class before used.
- */
-public class WXComponentRegistry {
-
-  private static Map<String, IFComponentHolder> sTypeComponentMap = new ConcurrentHashMap<>();
-  private static ArrayList<Map<String, Object>> sComponentInfos=new ArrayList<>();
-
-  public static synchronized boolean registerComponent(Map<String, RegisterCache.ComponentCache> componentCacheMap) {
-    if (componentCacheMap.isEmpty())
-      return true;
-    final Iterator<Map.Entry<String, RegisterCache.ComponentCache>> iterator = componentCacheMap.entrySet().iterator();
-    WXBridgeManager.getInstance().post(new Runnable() {
-      @Override
-      public void run() {
-        ArrayList<Map<String, Object>> coms = new ArrayList<>();
-        while (iterator.hasNext()) {
-          Map.Entry<String, RegisterCache.ComponentCache> next = iterator.next();
-          try {
-            RegisterCache.ComponentCache value = next.getValue();
-            Map<String, Object> registerInfo = value.componentInfo;
-            if (registerInfo == null) {
-              registerInfo = new HashMap<>();
-            }
-            registerInfo.put("type", value.type);
-            registerInfo.put("methods", value.holder.getMethods());
-            registerNativeComponent(value.type, value.holder);
-            sComponentInfos.add(registerInfo);
-            coms.add(registerInfo);
-          } catch (WXException e) {
-            e.printStackTrace();
-          }
-        }
-        WXSDKManager.getInstance().registerComponents(coms);
-      }
-    });
-    return true;
-  }
-
-  public static synchronized boolean registerComponent(final String type, final IFComponentHolder holder, final Map<String, Object> componentInfo) throws WXException {
-    if (holder == null || TextUtils.isEmpty(type)) {
-      return false;
-    }
-
-    if(RegisterCache.getInstance().cacheComponent(type,holder,componentInfo)) {
-      return true;
-    }
-
-    //execute task in js thread to make sure register order is same as the order invoke register method.
-    WXBridgeManager.getInstance()
-        .post(new Runnable() {
-      @Override
-      public void run() {
-        try {
-          Map<String, Object> registerInfo = componentInfo;
-          if (registerInfo == null){
-            registerInfo = new HashMap<>();
-          }
-
-          registerInfo.put("type",type);
-          registerInfo.put("methods",holder.getMethods());
-          registerNativeComponent(type, holder);
-          registerJSComponent(registerInfo);
-          sComponentInfos.add(registerInfo);
-        } catch (WXException e) {
-          WXLogUtils.e("register component error:", e);
-        }
-
-      }
-    });
-    return true;
-  }
-
-  private static boolean registerNativeComponent(String type, IFComponentHolder holder) throws WXException {
-    try {
-      holder.loadIfNonLazy();
-      sTypeComponentMap.put(type, holder);
-    }catch (ArrayStoreException e){
-      e.printStackTrace();
-      //ignore: ArrayStoreException: java.lang.String cannot be stored in an array of type java.util.HashMap$HashMapEntry[]
-    }
-    return true;
-  }
-
-  private static boolean registerJSComponent(Map<String, Object> componentInfo) throws WXException {
-    ArrayList<Map<String, Object>> coms = new ArrayList<>();
-    coms.add(componentInfo);
-    WXSDKManager.getInstance().registerComponents(coms);
-    return true;
-  }
-
-  public static IFComponentHolder getComponent(String type) {
-    return sTypeComponentMap.get(type);
-  }
-
-  public static void reload(){
-    WXBridgeManager.getInstance().post(new Runnable() {
-      @Override
-      public void run() {
-        try {
-          for(Map<String,Object> com:sComponentInfos){
-            registerJSComponent(com);
-          }
-        } catch (WXException e) {
-          WXLogUtils.e("", e);
-        }
-      }
-    });
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/WXRenderHandler.java b/android/sdk/src/main/java/com/taobao/weex/ui/WXRenderHandler.java
deleted file mode 100644
index 2bfb685..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/WXRenderHandler.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui;
-
-import android.os.Handler;
-import android.os.Looper;
-import android.os.Message;
-
-class WXRenderHandler extends Handler {
-
-    public WXRenderHandler() {
-        super(Looper.getMainLooper());
-    }
-
-    public final boolean post(String instanceId, Runnable r) {
-        Message msg = Message.obtain(this, r);
-        // Use what to match runnable. Make sure don't override callback method.
-        msg.what = instanceId.hashCode();
-        return sendMessageDelayed(msg, 0);
-    }
-
-    @Override
-    public void handleMessage(Message msg) {
-        super.handleMessage(msg);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/WXRenderManager.java b/android/sdk/src/main/java/com/taobao/weex/ui/WXRenderManager.java
deleted file mode 100644
index 85f54b7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/WXRenderManager.java
+++ /dev/null
@@ -1,312 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import android.opengl.GLES10;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.dom.RenderContext;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.ui.action.BasicGraphicAction;
-import com.taobao.weex.ui.action.GraphicActionBatchAction;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-
-import javax.microedition.khronos.egl.EGL10;
-import javax.microedition.khronos.egl.EGLConfig;
-import javax.microedition.khronos.egl.EGLContext;
-import javax.microedition.khronos.egl.EGLDisplay;
-import javax.microedition.khronos.egl.EGLSurface;
-
-
-
-/**
- * Manager class for render operation, mainly for managing {@link RenderContextImpl}.
- * This is <strong>not</strong> a thread-safe class
- */
-public class WXRenderManager {
-
-  private volatile ConcurrentHashMap<String, RenderContextImpl> mRenderContext;
-  private WXRenderHandler mWXRenderHandler;
-  private String mCurrentBatchInstanceId = null;
-  private ArrayList<Map<String,Object>> mBatchActions = new ArrayList<>();
-  private final int MAX_DROP_FRAME_NATIVE_BATCH = 2000;
-  private final static  String sKeyAction = "Action";
-  private static int nativeBatchTimes = 0;
-  private static int mOpenGLRenderLimitValue = 0;
-
-  public WXRenderManager() {
-    mRenderContext = new ConcurrentHashMap<>();
-    mWXRenderHandler = new WXRenderHandler();
-  }
-
-  public RenderContext getRenderContext(String instanceId) {
-    return mRenderContext.get(instanceId);
-  }
-
-  public @Nullable
-  WXComponent getWXComponent(String instanceId, String ref) {
-    if (instanceId == null || TextUtils.isEmpty(ref)) {
-      return null;
-    }
-    RenderContext stmt = getRenderContext(instanceId);
-    return stmt == null ? null : stmt.getComponent(ref);
-  }
-
-  public WXSDKInstance getWXSDKInstance(String instanceId) {
-    RenderContextImpl statement = mRenderContext.get(instanceId);
-    if (statement == null) {
-      return null;
-    }
-    return statement.getWXSDKInstance();
-  }
-
-    public static int getOpenGLRenderLimitValue() {
-      if(mOpenGLRenderLimitValue == 0){
-          int maxsize = 0;
-              try {
-                  EGL10 egl = (EGL10) EGLContext.getEGL();
-                  EGLDisplay dpy = egl.eglGetDisplay(EGL10.EGL_DEFAULT_DISPLAY);
-                  int[] vers = new int[2];
-                  egl.eglInitialize(dpy, vers);
-                  int[] configAttr = {
-                          EGL10.EGL_COLOR_BUFFER_TYPE, EGL10.EGL_RGB_BUFFER,
-                          EGL10.EGL_LEVEL, 0,
-                          EGL10.EGL_SURFACE_TYPE, EGL10.EGL_PBUFFER_BIT,
-                          EGL10.EGL_NONE};
-                  EGLConfig[] configs = new EGLConfig[1];
-                  int[] numConfig = new int[1];
-                  egl.eglChooseConfig(dpy, configAttr, configs, 1, numConfig);
-                  if(numConfig[0] == 0){
-                      //There is something wrong with opengl environment.
-                      maxsize = -1;
-                      egl.eglTerminate(dpy);
-                  }else {
-                      EGLConfig config = configs[0];
-                      int[] surfAttr = {
-                              EGL10.EGL_WIDTH, 64,
-                              EGL10.EGL_HEIGHT, 64,
-                              EGL10.EGL_NONE};
-                      EGLSurface surf = egl.eglCreatePbufferSurface(dpy, config, surfAttr);
-                      final int EGL_CONTEXT_CLIENT_VERSION = 0x3098;// missing in EGL10
-                      int[] ctxAttrib = {
-                              EGL_CONTEXT_CLIENT_VERSION, 1,
-                              EGL10.EGL_NONE};
-                      EGLContext ctx = egl.eglCreateContext(dpy, config, EGL10.EGL_NO_CONTEXT, ctxAttrib);
-                      egl.eglMakeCurrent(dpy, surf, surf, ctx);
-                      int[] maxSize = new int[1];
-                      GLES10.glGetIntegerv(GLES10.GL_MAX_TEXTURE_SIZE, maxSize, 0);
-                      egl.eglMakeCurrent(dpy, EGL10.EGL_NO_SURFACE, EGL10.EGL_NO_SURFACE,
-                              EGL10.EGL_NO_CONTEXT);
-                      egl.eglDestroySurface(dpy, surf);
-                      egl.eglDestroyContext(dpy, ctx);
-                      egl.eglTerminate(dpy);
-                      maxsize = maxSize[0];
-                  }
-              } catch(Exception e){
-                  WXLogUtils.e(WXLogUtils.getStackTrace(e));
-              }
-          mOpenGLRenderLimitValue = maxsize;
-      }
-      return mOpenGLRenderLimitValue;
-    }
-
-  @RestrictTo(Scope.LIBRARY)
-  public void postOnUiThread(Runnable runnable, long delayMillis) {
-    mWXRenderHandler.postDelayed(WXThread.secure(runnable), delayMillis);
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  public void postOnUiThread(Runnable runnable,final String instanceId){
-    mWXRenderHandler.post(instanceId, WXThread.secure(runnable));
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  public void postOnUiThread(Runnable runnable){
-    mWXRenderHandler.post(WXThread.secure(runnable));
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  public void removeTask(Runnable runnable){
-    mWXRenderHandler.removeCallbacks(runnable);
-  }
-
-  /**
-   * Remove renderStatement, can only be invoked in UI thread.
-   *
-   * @param instanceId {@link WXSDKInstance#mInstanceId}
-   */
-  public void removeRenderStatement(String instanceId) {
-    if (!WXUtils.isUiThread()) {
-      throw new WXRuntimeException("[WXRenderManager] removeRenderStatement can only be called in main thread");
-    }
-    RenderContextImpl statement = mRenderContext.remove(instanceId);
-
-    if (statement != null) {
-      statement.destroy();
-    }
-    if(instanceId == null) {
-      mWXRenderHandler.removeCallbacksAndMessages(null);
-    } else {
-      // use hashCode to match message's what.
-      mWXRenderHandler.removeMessages(instanceId.hashCode());
-    }
-  }
-
-  private void postAllStashedGraphicAction(final String instanceId,final BasicGraphicAction action) {
-      final RenderContextImpl renderContext = mRenderContext.get(instanceId);
-
-      /// keep actions if renderContext still exist
-      ArrayList<Map<String, Object>> tmpList = null;
-      if (renderContext != null) {
-        tmpList = new ArrayList<>(mBatchActions);
-      }
-
-      // clear stashed actions
-      this.mBatchActions.clear();
-      mCurrentBatchInstanceId = null;
-      nativeBatchTimes = 0;
-
-      // return if renderContext has been destroyed
-      if (renderContext == null) {
-        return;
-      }
-
-      /// post actions if renderContext still exist
-      ArrayList<BasicGraphicAction> actions = new ArrayList<>(tmpList.size());
-      for (int i = 0 ; i < tmpList.size(); i ++) {
-          Map<String, Object> item = tmpList.get(i);
-          Object mustBeAction = item.get(sKeyAction);
-          if (!(mustBeAction instanceof BasicGraphicAction)) {
-            continue;
-          }
-          BasicGraphicAction tmpAction = (BasicGraphicAction)mustBeAction;
-          if (tmpAction.mActionType == BasicGraphicAction.ActionTypeBatchBegin || tmpAction.mActionType == BasicGraphicAction.ActionTypeBatchEnd) {
-            continue;
-          }
-          actions.add(tmpAction);
-      }
-      postGraphicAction(instanceId, new GraphicActionBatchAction(action.getWXSDKIntance(),action.getRef(), actions));
-  }
-
-  public void postGraphicAction(final String instanceId, final BasicGraphicAction action) {
-    final RenderContextImpl renderContext = mRenderContext.get(instanceId);
-    if (renderContext == null) {
-      return;
-    }
-
-    // If more than two pages exist and mCurrentBatchInstanceId not matches new instanceId, we will post all stashed actions at once.
-    // That will cause losing efficacy of batch action, but it is acceptable because it's not serious problem.
-    if (mCurrentBatchInstanceId != null && instanceId != null && !mCurrentBatchInstanceId.equals(instanceId) && mBatchActions.size() > 0) {
-      Map<String, Object> lastItem = mBatchActions.get(mBatchActions.size() - 1);
-      Object mustBeAction = lastItem.get(sKeyAction);
-      if (mustBeAction instanceof BasicGraphicAction) {
-        BasicGraphicAction lastAction = (BasicGraphicAction)mustBeAction;
-        postAllStashedGraphicAction(mCurrentBatchInstanceId, lastAction);
-      }
-    }
-
-    if (action.mActionType == BasicGraphicAction.ActionTypeBatchEnd) {
-        postAllStashedGraphicAction(instanceId,action);
-        return;
-    } else if (action.mActionType == BasicGraphicAction.ActionTypeBatchBegin || this.mBatchActions.size() > 0 ) {
-        nativeBatchTimes ++ ;
-        if (nativeBatchTimes > MAX_DROP_FRAME_NATIVE_BATCH) {
-            postAllStashedGraphicAction(instanceId,action);
-        } else {
-            HashMap<String, Object> item = new HashMap<>(1);
-            item.put(sKeyAction, action);
-            mBatchActions.add(item);
-            mCurrentBatchInstanceId = instanceId;
-            return;
-        }
-    }
-
-    mWXRenderHandler.post(instanceId, action);
-  }
-
-  public void registerInstance(WXSDKInstance instance) {
-    if (instance.getInstanceId() == null) {
-      WXExceptionUtils.commitCriticalExceptionRT(null,
-              WXErrorCode.WX_RENDER_ERR_INSTANCE_ID_NULL,
-              "registerInstance",
-              WXErrorCode.WX_RENDER_ERR_INSTANCE_ID_NULL.getErrorMsg() + "instanceId is null",
-              null);
-    } else {
-      mRenderContext.put(instance.getInstanceId(), new RenderContextImpl(instance));
-    }
-  }
-
-  public List<WXSDKInstance> getAllInstances() {
-    ArrayList<WXSDKInstance> instances = null;
-    if (mRenderContext != null && !mRenderContext.isEmpty()) {
-      instances = new ArrayList<WXSDKInstance>();
-      for (Map.Entry<String, RenderContextImpl> entry : mRenderContext.entrySet()) {
-        RenderContextImpl renderStatement = entry.getValue();
-        if (renderStatement != null) {
-          instances.add(renderStatement.getWXSDKInstance());
-        }
-      }
-    }
-    return instances;
-  }
-
-  public void registerComponent(String instanceId, String ref, WXComponent comp) {
-    RenderContextImpl statement = mRenderContext.get(instanceId);
-    if (statement != null) {
-      statement.registerComponent(ref, comp);
-      if (null != statement.getInstance()){
-        statement.getInstance().getApmForInstance().updateMaxStats(
-            WXInstanceApm.KEY_PAGE_STATS_MAX_COMPONENT_NUM,
-            statement.getComponentCount()
-        );
-      }
-    }
-  }
-
-  public WXComponent unregisterComponent(String instanceId, String ref) {
-    RenderContextImpl statement = mRenderContext.get(instanceId);
-    if (statement != null) {
-      if (null != statement.getInstance()){
-        statement.getInstance().getApmForInstance().updateMaxStats(
-            WXInstanceApm.KEY_PAGE_STATS_MAX_COMPONENT_NUM,
-            statement.getComponentCount()
-        );
-      }
-      return statement.unregisterComponent(ref);
-    } else {
-      return null;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionAddRule.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionAddRule.java
deleted file mode 100644
index 5e3febe..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionAddRule.java
+++ /dev/null
@@ -1,87 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-import android.text.TextUtils;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.font.FontAdapter;
-import com.taobao.weex.utils.FontDO;
-import com.taobao.weex.utils.TypefaceUtil;
-
-/**
- * Created by listen on 18/01/10.
- */
-public class ActionAddRule implements IExecutable {
-
-  private final String mPageId;
-  private final String mType;
-  private final JSONObject mData;
-
-  public ActionAddRule(String pageId, String type, JSONObject data) {
-    this.mPageId = pageId;
-    this.mType = type;
-    this.mData = data;
-  }
-
-  @Override
-  public void executeAction() {
-    WXSDKInstance instance = WXSDKManager.getInstance().getWXRenderManager().getWXSDKInstance(mPageId);
-    if (instance == null || instance.isDestroy()) {
-      return;
-    }
-
-    if (!Constants.Name.FONT_FACE.equals(mType)) {
-      return;
-    }
-
-    FontDO fontDO = parseFontDO(mData, instance);
-    if (fontDO != null && !TextUtils.isEmpty(fontDO.getFontFamilyName())) {
-      notifyAddFontRule(instance, fontDO);
-      FontDO cacheFontDO = TypefaceUtil.getFontDO(fontDO.getFontFamilyName());
-      if (cacheFontDO == null || !TextUtils.equals(cacheFontDO.getUrl(), fontDO.getUrl())) {
-        TypefaceUtil.putFontDO(fontDO);
-        TypefaceUtil.loadTypeface(fontDO, true);
-      } else {
-        TypefaceUtil.loadTypeface(cacheFontDO, true);
-      }
-    }
-
-  }
-
-  private FontDO parseFontDO(JSONObject jsonObject,WXSDKInstance instance) {
-    if(jsonObject == null) {
-      return null;
-    }
-    String src = jsonObject.getString(Constants.Name.SRC);
-    String name = jsonObject.getString(Constants.Name.FONT_FAMILY);
-
-    return new FontDO(name, src,instance);
-  }
-
-
-  private void notifyAddFontRule(WXSDKInstance instance, FontDO fontDO){
-    FontAdapter fontAdapter = WXSDKManager.getInstance().getFontAdapter();
-    if(fontAdapter != null){
-        fontAdapter.onAddFontRule(instance.getInstanceId(), fontDO.getFontFamilyName(), fontDO.getUrl());
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionGetComponentRect.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionGetComponentRect.java
deleted file mode 100644
index 78c2875..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionGetComponentRect.java
+++ /dev/null
@@ -1,120 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.graphics.Rect;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-import android.view.View;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.SimpleJSCallback;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by listen on 18/01/10.
- */
-public class ActionGetComponentRect extends BasicGraphicAction {
-
-  private final String mCallback;
-
-  public ActionGetComponentRect(WXSDKInstance instance, String ref, String callback) {
-    super(instance, ref);
-    this.mCallback = callback;
-  }
-
-  @Override
-  public void executeAction() {
-    WXSDKInstance instance = getWXSDKIntance();
-    if (instance == null || instance.isDestroy()) {
-      return;
-    }
-
-    JSCallback jsCallback = new SimpleJSCallback(instance.getInstanceId(), mCallback);
-
-    if (TextUtils.isEmpty(getRef())) {
-      Map<String, Object> options = new HashMap<>();
-      options.put("result", false);
-      options.put("errMsg", "Illegal parameter");
-      jsCallback.invoke(options);
-    } else if ("viewport".equalsIgnoreCase(getRef())) {
-      callbackViewport(instance, jsCallback);
-    } else {
-      WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-      if (component == null) {
-        return;
-      }
-
-      Map<String, Object> options = new HashMap<>();
-      if (component != null) {
-        int viewPort = instance.getInstanceViewPortWidth();
-        Map<String, Float> size = new HashMap<>();
-        Rect sizes = component.getComponentSize();
-        size.put("width", getWebPxValue(sizes.width(),viewPort));
-        size.put("height", getWebPxValue(sizes.height(),viewPort));
-        size.put("bottom", getWebPxValue(sizes.bottom,viewPort));
-        size.put("left", getWebPxValue(sizes.left,viewPort));
-        size.put("right", getWebPxValue(sizes.right,viewPort));
-        size.put("top", getWebPxValue(sizes.top,viewPort));
-        options.put("size", size);
-        options.put("result", true);
-      } else {
-        options.put("errMsg", "Component does not exist");
-      }
-      jsCallback.invoke(options);
-    }
-  }
-
-  private void callbackViewport(WXSDKInstance instance, JSCallback jsCallback) {
-    View container;
-    if ((container = instance.getContainerView()) != null) {
-      Map<String, Object> options = new HashMap<>();
-      Map<String, Float> sizes = new HashMap<>();
-      int[] location = new int[2];
-      instance.getContainerView().getLocationOnScreen(location);
-      int viewport = instance.getInstanceViewPortWidth();
-      sizes.put("left", 0f);
-      sizes.put("top", 0f);
-      sizes.put("right", getWebPxValue(container.getWidth(),viewport));
-      sizes.put("bottom", getWebPxValue(container.getHeight(),viewport));
-      sizes.put("width", getWebPxValue(container.getWidth(),viewport));
-      sizes.put("height", getWebPxValue(container.getHeight(),viewport));
-      options.put("size", sizes);
-      options.put("result", true);
-      jsCallback.invoke(options);
-    } else {
-      Map<String, Object> options = new HashMap<>();
-      options.put("result", false);
-      options.put("errMsg", "Component does not exist");
-      jsCallback.invoke(options);
-    }
-  }
-
-  @NonNull
-  private float getWebPxValue(int value,int viewport) {
-    return WXViewUtils.getWebPxByWidth(value, viewport);
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionGetLayoutDirection.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionGetLayoutDirection.java
deleted file mode 100644
index 039bdfc..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionGetLayoutDirection.java
+++ /dev/null
@@ -1,117 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-import android.view.View;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.SimpleJSCallback;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by listen on 18/09/12.
- */
-public class ActionGetLayoutDirection extends BasicGraphicAction {
-
-  private final String mCallback;
-
-  public ActionGetLayoutDirection(WXSDKInstance instance, String ref, String callback) {
-    super(instance, ref);
-    this.mCallback = callback;
-  }
-
-  @Override
-  public void executeAction() {
-    WXSDKInstance instance = getWXSDKIntance();
-    if (instance == null || instance.isDestroy()) {
-      return;
-    }
-
-    JSCallback jsCallback = new SimpleJSCallback(instance.getInstanceId(), mCallback);
-
-    if (TextUtils.isEmpty(getRef())) {
-      Map<String, Object> options = new HashMap<>();
-      options.put("result", false);
-      options.put("errMsg", "Illegal parameter");
-      jsCallback.invoke(options);
-    } else if ("viewport".equalsIgnoreCase(getRef())) {
-      callbackViewport(instance, jsCallback);
-    } else {
-      WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-      if (component == null) {
-        return;
-      }
-
-      String directionRet = "ltr";
-      if (component != null) {
-        int direction = NativeRenderObjectUtils.nativeRenderObjectGetLayoutDirectionFromPathNode(component.getRenderObjectPtr());
-        switch (direction) {
-          case 0: {
-            directionRet = "inherit";
-            break;
-          }
-          case 1: {
-            directionRet = "ltr";
-            break;
-          }
-          case 2: {
-            directionRet = "rtl";
-            break;
-          }
-          default: {
-            directionRet = "ltr";
-            break;
-          }
-
-        }
-      }
-      jsCallback.invoke(directionRet);
-    }
-  }
-
-  private void callbackViewport(WXSDKInstance instance, JSCallback jsCallback) {
-    View container;
-    if ((container = instance.getContainerView()) != null) {
-      Map<String, Object> options = new HashMap<>();
-      options.put("direction", "ltr");
-      options.put("result", true);
-      jsCallback.invoke(options);
-    } else {
-      Map<String, Object> options = new HashMap<>();
-      options.put("result", false);
-      options.put("errMsg", "Component does not exist");
-      jsCallback.invoke(options);
-    }
-  }
-
-  @NonNull
-  private float getWebPxValue(int value,int viewport) {
-    return WXViewUtils.getWebPxByWidth(value, viewport);
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionInvokeMethod.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionInvokeMethod.java
deleted file mode 100644
index f078d1b..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionInvokeMethod.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.alibaba.fastjson.JSONArray;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.WXLogUtils;
-
-/**
- * Created by listen on 18/01/10.
- */
-public class ActionInvokeMethod implements IExecutable {
-
-  private static final String TAG = "ActionInvokeMethod";
-
-  private final String mMethod;
-  private final JSONArray mArgs;
-  private String mPageId;
-  private String mRef;
-
-  public ActionInvokeMethod(String pageId, String ref, String method, JSONArray args) {
-    this.mPageId = pageId;
-    this.mRef = ref;
-    this.mMethod = method;
-    this.mArgs = args;
-  }
-
-  @Override
-  public void executeAction() {
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(mPageId, mRef);
-    if(component == null){
-      WXLogUtils.e(TAG,"target component not found.");
-      return;
-    }
-    component.invoke(mMethod,mArgs);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionReloadPage.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionReloadPage.java
deleted file mode 100644
index 42705f6..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/ActionReloadPage.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.util.Log;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-
-/**
- * Created by listen on 18/01/09.
- */
-public class ActionReloadPage implements IExecutable {
-
-  private final String TAG = "ReloadPageAction";
-  private boolean mReloadThis;
-  private String mPageId;
-
-  public ActionReloadPage(String pageId, boolean reloadThis) {
-    this.mPageId = pageId;
-    this.mReloadThis = reloadThis;
-  }
-
-  @Override
-  public void executeAction() {
-    final WXSDKInstance instance = WXSDKManager.getInstance().getWXRenderManager().getWXSDKInstance(mPageId);
-    if (instance != null) {
-      instance.reloadPage(mReloadThis);
-    } else {
-      Log.e(TAG, "ReloadPageAction executeDom reloadPage instance is null");
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/BasicComponentData.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/BasicComponentData.java
deleted file mode 100644
index 9d12450..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/BasicComponentData.java
+++ /dev/null
@@ -1,310 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.annotation.NonNull;
-import android.view.View;
-
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.Map;
-import java.util.Set;
-
-public class BasicComponentData<T extends View> {
-
-  public String mRef;
-  public String mComponentType;
-  public String mParentRef;
-  private WXStyle mStyles;
-  private WXAttr mAttributes;
-  private WXEvent mEvents;
-  private CSSShorthand mMargins;
-  private CSSShorthand mPaddings;
-  private CSSShorthand mBorders;
-  private long renderObjectPr = 0;
-
-  public BasicComponentData(String ref, String componentType, String parentRef) {
-    this.mRef = ref;
-    this.mComponentType = componentType;
-    this.mParentRef = parentRef;
-  }
-
-  public void addStyle(Map<String, Object> styles) {
-    addStyle(styles, false);
-  }
-
-  public final void addStyle(Map<String, Object> styles, boolean byPesudo) {
-    if (styles == null || styles.isEmpty()) {
-      return;
-    }
-    if (mStyles == null) {
-      mStyles = new WXStyle(styles);
-    }
-    else {
-      mStyles.putAll(styles, byPesudo);
-    }
-  }
-
-  public final void addAttr(Map<String, Object> attrs) {
-    if (attrs == null || attrs.isEmpty()) {
-      return;
-    }
-    if (mAttributes == null) {
-      mAttributes = new WXAttr(attrs, 0);
-    }
-    else {
-      mAttributes.putAll(attrs);
-    }
-  }
-
-  public final void addEvent(Set<String> events) {
-    if (events == null || events.isEmpty()) {
-      return;
-    }
-    if (mEvents == null) {
-      mEvents = new WXEvent();
-    }
-    mEvents.addAll(events);
-  }
-
-  public final void addShorthand(float[] shorthand, CSSShorthand.TYPE type) {
-    if (shorthand == null) {
-      shorthand = new float[] {0, 0, 0, 0};
-    }
-    if (shorthand.length == 4) {
-      switch (type) {
-        case MARGIN:
-          if (mMargins == null) {
-            mMargins = new CSSShorthand(shorthand);
-          } else {
-            mMargins.replace(shorthand);
-          }
-          break;
-        case PADDING:
-          if (mPaddings == null) {
-            mPaddings = new CSSShorthand(shorthand);
-          } else {
-            mPaddings.replace(shorthand);
-          }
-          break;
-        case BORDER:
-          if (mBorders == null) {
-            mBorders = new CSSShorthand(shorthand);
-          } else {
-            mBorders.replace(shorthand);
-          }
-          break;
-        default:
-          break;
-      }
-    }
-  }
-
-  public final void addShorthand(Map<String, String> shorthand) {
-    if (shorthand != null && !shorthand.isEmpty()) {
-      for (Map.Entry<String, String> item : shorthand.entrySet()) {
-        String key = item.getKey();
-        switch (key) {
-          case Constants.Name.MARGIN:
-            addMargin(CSSShorthand.EDGE.ALL, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.MARGIN_LEFT:
-            addMargin(CSSShorthand.EDGE.LEFT, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.MARGIN_TOP:
-            addMargin(CSSShorthand.EDGE.TOP, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.MARGIN_RIGHT:
-            addMargin(CSSShorthand.EDGE.RIGHT, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.MARGIN_BOTTOM:
-            addMargin(CSSShorthand.EDGE.BOTTOM,WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.BORDER_WIDTH:
-            addBorder(CSSShorthand.EDGE.ALL, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.BORDER_TOP_WIDTH:
-            addBorder(CSSShorthand.EDGE.TOP, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.BORDER_RIGHT_WIDTH:
-            addBorder(CSSShorthand.EDGE.RIGHT, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.BORDER_BOTTOM_WIDTH:
-            addBorder(CSSShorthand.EDGE.BOTTOM, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.BORDER_LEFT_WIDTH:
-            addBorder(CSSShorthand.EDGE.LEFT, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.PADDING:
-            addPadding(CSSShorthand.EDGE.ALL, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.PADDING_LEFT:
-            addPadding(CSSShorthand.EDGE.LEFT, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.PADDING_TOP:
-            addPadding(CSSShorthand.EDGE.TOP, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.PADDING_RIGHT:
-            addPadding(CSSShorthand.EDGE.RIGHT, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-          case Constants.Name.PADDING_BOTTOM:
-            addPadding(CSSShorthand.EDGE.BOTTOM, WXUtils.fastGetFloat(shorthand.get(key)));
-            break;
-        }
-      }
-    }
-  }
-
-  private void addMargin(CSSShorthand.EDGE spacingType, float margin) {
-    if (mMargins == null) {
-      mMargins = new CSSShorthand();
-    }
-    mMargins.set(spacingType, margin);
-  }
-
-  private void addPadding(CSSShorthand.EDGE spacingType, float padding) {
-    if (mPaddings == null) {
-      mPaddings = new CSSShorthand();
-    }
-    mPaddings.set(spacingType, padding);
-  }
-
-  private void addBorder(CSSShorthand.EDGE spacingType, float border) {
-    if (mBorders == null) {
-      mBorders = new CSSShorthand();
-    }
-    mBorders.set(spacingType, border);
-  }
-
-  public final @NonNull
-  WXStyle getStyles() {
-    if (mStyles == null) {
-      mStyles = new WXStyle();
-    }
-    return mStyles;
-  }
-
-  public final @NonNull
-  WXAttr getAttrs() {
-    if (mAttributes == null) {
-      mAttributes = new WXAttr();
-    }
-    return mAttributes;
-  }
-
-  public final @NonNull
-  WXEvent getEvents() {
-    if (mEvents == null) {
-      mEvents = new WXEvent();
-    }
-    return mEvents;
-  }
-
-  /**
-   * Get this node's margin, as defined by cssstyle + default margin.
-   */
-  public final @NonNull
-  CSSShorthand getMargin() {
-    if (mMargins == null) {
-      mMargins = new CSSShorthand();
-    }
-    return mMargins;
-  }
-
-  /**
-   * Get this node's padding, as defined by cssstyle + default padding.
-   */
-  public final @NonNull
-  CSSShorthand getPadding() {
-    if (mPaddings == null) {
-      mPaddings = new CSSShorthand();
-    }
-    return mPaddings;
-  }
-
-  /**
-   * Get this node's border, as defined by cssstyle.
-   */
-  public @NonNull
-  CSSShorthand getBorder() {
-    if (mBorders == null) {
-      mBorders = new CSSShorthand();
-    }
-    return mBorders;
-  }
-
-  public final void setMargins(@NonNull CSSShorthand mMargins) {
-    this.mMargins = mMargins;
-  }
-
-  public final void setPaddings(@NonNull CSSShorthand mPaddings) {
-    this.mPaddings = mPaddings;
-  }
-
-  public final void setBorders(@NonNull CSSShorthand mBorders) {
-    this.mBorders = mBorders;
-  }
-
-
-
-  @Override
-  public BasicComponentData clone() throws CloneNotSupportedException {
-    BasicComponentData basicComponentData = new BasicComponentData(mRef, mComponentType, mParentRef);
-    basicComponentData.setBorders(getBorder().clone());
-    basicComponentData.setMargins(getMargin().clone());
-    basicComponentData.setPaddings(getPadding().clone());
-    if(mAttributes != null){
-      basicComponentData.mAttributes = mAttributes.clone();
-    }
-    if(mStyles != null){
-      basicComponentData.mStyles = mStyles.clone();
-    }
-    if(mEvents != null){
-      basicComponentData.mEvents = mEvents.clone();
-    }
-
-    if(renderObjectPr != 0){
-      basicComponentData.setRenderObjectPr(NativeRenderObjectUtils.nativeCopyRenderObject(renderObjectPr));
-    }
-    return basicComponentData;
-  }
-
-  public long getRenderObjectPr() {
-    return renderObjectPr;
-  }
-
-  public boolean isRenderPtrEmpty(){
-    return  renderObjectPr == 0;
-  }
-
-  public synchronized void setRenderObjectPr(long renderObjectPr) {
-    if(this.renderObjectPr != renderObjectPr){
-      if(this.renderObjectPr != 0){
-        throw  new  RuntimeException("RenderObjectPr has " + renderObjectPr + " old renderObjectPtr " + this.renderObjectPr);
-      }
-      this.renderObjectPr = renderObjectPr;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/BasicGraphicAction.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/BasicGraphicAction.java
deleted file mode 100644
index e232584..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/BasicGraphicAction.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.text.TextUtils;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.utils.WXLogUtils;
-
-public abstract class BasicGraphicAction implements IExecutable, Runnable {
-
-  private WXSDKInstance mInstance;
-  private final String mRef;
-  public int mActionType = ActionTypeNormal;
-  public static final int ActionTypeBatchBegin = 1;
-  public static final int ActionTypeBatchEnd = 2;
-  public static final int ActionTypeNormal = 0;
-
-
-  public BasicGraphicAction(WXSDKInstance instance, String ref) {
-    this.mInstance = instance;
-    this.mRef = ref;
-  }
-
-  public final WXSDKInstance getWXSDKIntance() {
-    return mInstance;
-  }
-
-  public final String getPageId() {
-    return mInstance.getInstanceId();
-  }
-
-  public final String getRef() {
-    return mRef;
-  }
-
-  public void executeActionOnRender() {
-    if (TextUtils.isEmpty(mInstance.getInstanceId())) {
-        WXLogUtils.e("[BasicGraphicAction] pageId can not be null");
-        if (WXEnvironment.isApkDebugable()) {
-            throw new RuntimeException("["+getClass().getName()+"] pageId can not be null");
-        }
-        return;
-    }
-    WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(mInstance.getInstanceId(), this);
-  }
-
-  @Override
-  public void run() {
-    try {
-      executeAction();
-    } catch (Throwable e) {
-      //catch everything may throw from exection.
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e("BasicGraphicAction",
-            "SafeRunnable run throw expection:" + e.getMessage());
-        throw e;
-      }
-      WXLogUtils.w("BasicGraphicAction", e);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAbstractAddElement.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAbstractAddElement.java
deleted file mode 100644
index 88baced..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAbstractAddElement.java
+++ /dev/null
@@ -1,102 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.v4.util.ArrayMap;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXComponentFactory;
-import com.taobao.weex.ui.component.WXVContainer;
-import java.util.Map;
-import java.util.Set;
-
-public abstract class GraphicActionAbstractAddElement extends BasicGraphicAction {
-
-  protected String mComponentType;
-  protected String mParentRef;
-  protected int mIndex = -1;
-  protected Map<String, String> mStyle;
-  protected Map<String, String> mAttributes;
-  protected Set<String> mEvents;
-  protected float[] mMargins;
-  protected float[] mPaddings;
-  protected float[] mBorders;
-  private long startTime;
-
-  public GraphicActionAbstractAddElement(WXSDKInstance instance, String ref) {
-    super(instance, ref);
-    startTime = System.currentTimeMillis();
-  }
-
-  protected WXComponent createComponent(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    long createComponentStart = System.currentTimeMillis();
-    if (basicComponentData != null) {
-      basicComponentData.addStyle(mStyle);
-      basicComponentData.addAttr(mAttributes);
-      basicComponentData.addEvent(mEvents);
-      basicComponentData.addShorthand(mMargins, CSSShorthand.TYPE.MARGIN);
-      basicComponentData.addShorthand(mPaddings, CSSShorthand.TYPE.PADDING);
-      basicComponentData.addShorthand(mBorders, CSSShorthand.TYPE.BORDER);
-    }
-
-    WXComponent component = WXComponentFactory.newInstance(instance, parent, basicComponentData);
-    WXSDKManager.getInstance().getWXRenderManager().registerComponent(getPageId(), getRef(), component);
-    if(mStyle != null && mStyle.containsKey(Constants.Name.TRANSFORM) && component.getTransition() == null) {
-      Map<String, Object> animationMap = new ArrayMap<>(2);
-      animationMap.put(Constants.Name.TRANSFORM, mStyle.get(Constants.Name.TRANSFORM));
-      animationMap
-          .put(Constants.Name.TRANSFORM_ORIGIN, mStyle.get(Constants.Name.TRANSFORM_ORIGIN));
-      component.addAnimationForElement(animationMap);
-    }
-    instance.onComponentCreate(component,System.currentTimeMillis() -createComponentStart);
-    return component;
-  }
-
-  @Override
-  public void executeAction() {
-    getWXSDKIntance().callActionAddElementTime(System.currentTimeMillis() - startTime);
-  }
-
-  public String getComponentType() {
-    return mComponentType;
-  }
-
-  public String getParentRef() {
-    return mParentRef;
-  }
-
-  public int getIndex() {
-    return mIndex;
-  }
-
-  public Map<String, String> getStyle() {
-    return mStyle;
-  }
-
-  public Map<String, String> getAttributes() {
-    return mAttributes;
-  }
-
-  public Set<String> getEvents() {
-    return mEvents;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddChildToRichtext.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddChildToRichtext.java
deleted file mode 100755
index bddad36..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddChildToRichtext.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.annotation.NonNull;
-import android.util.Log;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.richtext.WXRichText;
-
-import java.util.HashMap;
-
-public class GraphicActionAddChildToRichtext extends BasicGraphicAction {
-
-    public GraphicActionAddChildToRichtext(@NonNull WXSDKInstance instance, String nodeType, String ref, String parentRef, String richTextRef,
-                                           HashMap<String, String> styles, HashMap<String, String> attrs){
-        super(instance,richTextRef);
-        if(WXSDKManager.getInstance() != null && WXSDKManager.getInstance().getWXRenderManager() != null) {
-            WXRichText richText = (WXRichText) WXSDKManager.getInstance().getWXRenderManager()
-                    .getWXComponent(getPageId(), richTextRef);
-            if (richText != null) {
-                richText.AddChildNode(ref, nodeType, parentRef, styles, attrs);
-            }
-        }
-    }
-    @Override
-    public void executeAction() {
-
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddElement.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddElement.java
deleted file mode 100644
index a0b2005..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddElement.java
+++ /dev/null
@@ -1,214 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.annotation.NonNull;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.support.annotation.WorkerThread;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-import android.util.Log;
-import com.taobao.weex.BuildConfig;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.dom.transition.WXTransition;
-import com.taobao.weex.performance.WXAnalyzerDataTransfer;
-import com.taobao.weex.performance.WXStateRecord;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.Arrays;
-import java.util.Locale;
-import java.util.Map;
-import java.util.Set;
-
-public class GraphicActionAddElement extends GraphicActionAbstractAddElement {
-
-  private WXVContainer parent;
-  private WXComponent child;
-  private GraphicPosition layoutPosition;
-  private GraphicSize layoutSize;
-  private boolean isLayoutRTL;
-
-  public GraphicActionAddElement(@NonNull WXSDKInstance instance, String ref,
-                                 String componentType, String parentRef,
-                                 int index,
-                                 Map<String, String> style,
-                                 Map<String, String> attributes,
-                                 Set<String> events,
-                                 float[] margins,
-                                 float[] paddings,
-                                 float[] borders) {
-    super(instance, ref);
-    this.mComponentType = componentType;
-    this.mParentRef = parentRef;
-    this.mIndex = index;
-    this.mStyle = style;
-    this.mAttributes = attributes;
-    this.mEvents = events;
-    this.mPaddings = paddings;
-    this.mMargins = margins;
-    this.mBorders = borders;
-
-    if (instance.getContext() == null) {
-      return;
-    }
-      if (WXAnalyzerDataTransfer.isInteractionLogOpen()){
-        Log.d(WXAnalyzerDataTransfer.INTERACTION_TAG, "[client][addelementStart]"+instance.getInstanceId()+","+componentType+","+ref);
-      }
-    try {
-      parent = (WXVContainer) WXSDKManager.getInstance().getWXRenderManager()
-          .getWXComponent(getPageId(), mParentRef);
-      long start = WXUtils.getFixUnixTime();
-      BasicComponentData basicComponentData = new BasicComponentData(ref, mComponentType,
-          mParentRef);
-      child = createComponent(instance, parent, basicComponentData);
-      child.setTransition(WXTransition.fromMap(child.getStyles(), child));
-      long diff = WXUtils.getFixUnixTime()-start;
-      instance.getApmForInstance().componentCreateTime += diff;
-      if (null != parent && parent.isIgnoreInteraction){
-        child.isIgnoreInteraction = true;
-      }
-      if (!child.isIgnoreInteraction ){
-        Object flag = null;
-        if (null != child.getAttrs()){
-          flag = child.getAttrs().get("ignoreInteraction");
-        }
-        if ("false".equals(flag) || "0".equals(flag)){
-          child.isIgnoreInteraction = false;
-        }else if ("1".equals(flag) || "true".equals(flag) || child.isFixed()){
-          child.isIgnoreInteraction = true;
-        }
-      }
-      WXStateRecord.getInstance().recordAction(instance.getInstanceId(),"addElement");
-
-    } catch (ClassCastException e) {
-      Map<String, String> ext = new ArrayMap<>();
-      WXComponent parent = WXSDKManager.getInstance().getWXRenderManager()
-          .getWXComponent(getPageId(), mParentRef);
-
-      if (mStyle != null && !mStyle.isEmpty()) {
-        ext.put("child.style", mStyle.toString());
-      }
-      if (parent != null && parent.getStyles() != null && !parent.getStyles().isEmpty()) {
-        ext.put("parent.style", parent.getStyles().toString());
-      }
-
-      if (mAttributes != null && !mAttributes.isEmpty()) {
-        ext.put("child.attr", mAttributes.toString());
-      }
-      if (parent != null && parent.getAttrs() != null && !parent.getAttrs().isEmpty()) {
-        ext.put("parent.attr", parent.getAttrs().toString());
-      }
-
-      if (mEvents != null && !mEvents.isEmpty()) {
-        ext.put("child.event", mEvents.toString());
-      }
-      if (parent != null && parent.getEvents() != null && !parent.getEvents().isEmpty()) {
-        ext.put("parent.event", parent.getEvents().toString());
-      }
-
-      if (mMargins != null && mMargins.length > 0) {
-        ext.put("child.margin", Arrays.toString(mMargins));
-      }
-      if (parent != null && parent.getMargin() != null) {
-        ext.put("parent.margin", parent.getMargin().toString());
-      }
-
-      if (mPaddings != null && mPaddings.length > 0) {
-        ext.put("child.padding", Arrays.toString(mPaddings));
-      }
-      if (parent != null && parent.getPadding() != null) {
-        ext.put("parent.padding", parent.getPadding().toString());
-      }
-
-      if (mBorders != null && mBorders.length > 0) {
-        ext.put("child.border", Arrays.toString(mBorders));
-      }
-      if (parent != null && parent.getBorder() != null) {
-        ext.put("parent.border", parent.getBorder().toString());
-      }
-
-      WXExceptionUtils.commitCriticalExceptionRT(instance.getInstanceId(),
-          WXErrorCode.WX_RENDER_ERR_CONTAINER_TYPE,
-          "GraphicActionAddElement",
-          String.format(Locale.ENGLISH,"You are trying to add a %s to a %2$s, which is illegal as %2$s is not a container",
-              componentType,
-              WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), mParentRef).getComponentType()),
-          ext);
-    }
-
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  @WorkerThread
-  public void setRTL(boolean isRTL){
-    this.isLayoutRTL = isRTL;
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  @WorkerThread
-  public void setSize(GraphicSize graphicSize){
-    this.layoutSize = graphicSize;
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  @WorkerThread
-  public void setPosition(GraphicPosition position){
-    this.layoutPosition = position;
-  }
-
-  @RestrictTo(Scope.LIBRARY)
-  @WorkerThread
-  public void setIndex(int index){
-    mIndex = index;
-  }
-
-  @Override
-  public void executeAction() {
-    super.executeAction();
-    try {
-      if (!TextUtils.equals(mComponentType, "video") && !TextUtils.equals(mComponentType, "videoplus"))
-        child.mIsAddElementToTree = true;
-
-      long start = WXUtils.getFixUnixTime();
-      parent.addChild(child, mIndex);
-      parent.createChildViewAt(mIndex);
-
-      child.setIsLayoutRTL(isLayoutRTL);
-      if(layoutPosition !=null && layoutSize != null) {
-        child.setDemission(layoutSize, layoutPosition);
-      }
-      child.applyLayoutAndEvent(child);
-      child.bindData(child);
-      long diff = WXUtils.getFixUnixTime() - start;
-      if (null != getWXSDKIntance()){
-        getWXSDKIntance().getApmForInstance().viewCreateTime +=diff;
-      }
-
-    } catch (Exception e) {
-      WXLogUtils.e("add component failed.", e);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddEvent.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddEvent.java
deleted file mode 100644
index 3ef4a6c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAddEvent.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.tracing.Stopwatch;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by listen on 18/01/11.
- */
-public class GraphicActionAddEvent extends BasicGraphicAction {
-
-  private final String mEvent;
-
-  public GraphicActionAddEvent(WXSDKInstance instance, String ref, Object event) {
-    super(instance, ref);
-    this.mEvent = WXEvent.getEventName(event);
-  }
-
-  @Override
-  public void executeAction() {
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null) {
-      return;
-    }
-
-    Stopwatch.tick();
-    if (!component.getEvents().contains(mEvent)) {
-      component.getEvents().addEvent(mEvent);
-    }
-    component.addEvent(mEvent);
-    Stopwatch.split("addEventToComponent");
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAnimation.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAnimation.java
deleted file mode 100644
index 4023b0c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAnimation.java
+++ /dev/null
@@ -1,289 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.animation.Animator;
-import android.animation.AnimatorListenerAdapter;
-import android.animation.ArgbEvaluator;
-import android.animation.ObjectAnimator;
-import android.animation.PropertyValuesHolder;
-import android.graphics.drawable.ColorDrawable;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v4.view.animation.PathInterpolatorCompat;
-import android.text.TextUtils;
-import android.util.Pair;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.animation.AccelerateDecelerateInterpolator;
-import android.view.animation.AccelerateInterpolator;
-import android.view.animation.DecelerateInterpolator;
-import android.view.animation.Interpolator;
-import android.view.animation.LinearInterpolator;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.animation.BackgroundColorProperty;
-import com.taobao.weex.ui.animation.HeightProperty;
-import com.taobao.weex.ui.animation.WXAnimationBean;
-import com.taobao.weex.ui.animation.WXAnimationModule;
-import com.taobao.weex.ui.animation.WidthProperty;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.list.template.TemplateDom;
-import com.taobao.weex.ui.view.border.BorderDrawable;
-import com.taobao.weex.utils.SingleFunctionParser;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.HashMap;
-import java.util.List;
-
-public class GraphicActionAnimation extends BasicGraphicAction {
-
-  private final static String TAG = "GraphicActionAnimation";
-
-  private final boolean styleNeedInit;
-
-  @Nullable
-  private
-  final String callback;
-
-  @Nullable
-  private
-  WXAnimationBean mAnimationBean;
-
-  public GraphicActionAnimation(@NonNull WXSDKInstance instance, @NonNull String ref, @NonNull WXAnimationBean animationBean) {
-    super(instance, ref);
-    this.styleNeedInit = false;
-    this.callback = null;
-    this.mAnimationBean = animationBean;
-  }
-
-  public GraphicActionAnimation(@NonNull WXSDKInstance instance, @NonNull String ref, @Nullable String animation,
-                                @Nullable final String callBack) {
-    super(instance, ref);
-    this.styleNeedInit = true;
-    this.callback = callBack;
-    if (!TextUtils.isEmpty(animation)) {
-      this.mAnimationBean = JSONObject.parseObject(animation, WXAnimationBean.class);
-    }
-  }
-  public GraphicActionAnimation(@NonNull WXSDKInstance instance, @NonNull String ref, @NonNull WXAnimationBean animationBean,
-                                @Nullable final String callBack) {
-    super(instance, ref);
-    this.styleNeedInit = false;
-    this.mAnimationBean = animationBean;
-    this.callback = callBack;
-  }
-
-  @Override
-  public void executeAction() {
-    if (null == mAnimationBean) {
-      return;
-    }
-
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null) {
-      if(!TemplateDom.isVirtualDomRef(getRef())){
-        return;
-      }
-      component = TemplateDom.findVirtualComponentByVRef(getPageId(), getRef());
-      if(component == null){
-        return;
-      }
-    }
-
-    WXSDKInstance instance = WXSDKManager.getInstance().getWXRenderManager().getWXSDKInstance(getPageId());
-    if (instance == null) {
-      return;
-    }
-
-    if (null != mAnimationBean.styles) {
-      if(styleNeedInit) {
-        // Synchronize transformOrigin between component styles and animation style before
-        // animation start.
-        String transformOrigin = (String) component.getStyles().get(Constants.Name.TRANSFORM_ORIGIN);
-        if (TextUtils.isEmpty(mAnimationBean.styles.transformOrigin)) {
-          mAnimationBean.styles.transformOrigin = transformOrigin;
-        }
-        mAnimationBean.styles.init(mAnimationBean.styles.transformOrigin,
-            mAnimationBean.styles.transform, (int) component.getLayoutWidth(),
-            (int) component.getLayoutHeight(),
-            instance.getInstanceViewPortWidth(), instance);
-      }
-      startAnimation(instance, component);
-    }
-  }
-
-
-
-  private void startAnimation(@NonNull WXSDKInstance instance, @Nullable WXComponent component) {
-    if (component != null) {
-      if (mAnimationBean != null) {
-        component.setNeedLayoutOnAnimation(mAnimationBean.needLayout);
-      }
-      if (component.getHostView() == null) {
-        WXAnimationModule.AnimationHolder holder = new WXAnimationModule.AnimationHolder(mAnimationBean, callback);
-        component.postAnimation(holder);
-      } else {
-        try {
-          Animator animator = createAnimator(component.getHostView(), instance
-              .getInstanceViewPortWidth());
-          if (animator != null) {
-            Animator.AnimatorListener animatorCallback = createAnimatorListener(instance, callback);
-            if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR2 && component
-                .isLayerTypeEnabled() ) {
-              component.getHostView().setLayerType(View.LAYER_TYPE_HARDWARE, null);
-            }
-            Interpolator interpolator = createTimeInterpolator();
-            if (animatorCallback != null) {
-              animator.addListener(animatorCallback);
-            }
-            if (interpolator != null) {
-              animator.setInterpolator(interpolator);
-            }
-            component.getHostView().setCameraDistance(mAnimationBean.styles.getCameraDistance());
-            animator.setDuration(mAnimationBean.duration);
-            animator.start();
-          }
-        } catch (RuntimeException e) {
-          WXLogUtils.e(TAG, WXLogUtils.getStackTrace(e));
-        }
-      }
-    }
-  }
-
-  private
-  @Nullable
-  ObjectAnimator createAnimator(final View target, final int viewPortWidth) {
-    if (target == null) {
-      return null;
-    }
-    WXAnimationBean.Style style = mAnimationBean.styles;
-    if (style != null) {
-      ObjectAnimator animator;
-      List<PropertyValuesHolder> holders = style.getHolders();
-      if (!TextUtils.isEmpty(style.backgroundColor)) {
-        BorderDrawable borderDrawable;
-        if ((borderDrawable = WXViewUtils.getBorderDrawable(target)) != null) {
-          holders.add(PropertyValuesHolder.ofObject(
-              new BackgroundColorProperty(), new ArgbEvaluator(),
-              borderDrawable.getColor(),
-              WXResourceUtils.getColor(style.backgroundColor)));
-        } else if (target.getBackground() instanceof ColorDrawable) {
-          holders.add(PropertyValuesHolder.ofObject(
-              new BackgroundColorProperty(), new ArgbEvaluator(),
-              ((ColorDrawable) target.getBackground()).getColor(),
-              WXResourceUtils.getColor(style.backgroundColor)));
-        }
-      }
-
-      if (target.getLayoutParams() != null &&
-          (!TextUtils.isEmpty(style.width) || !TextUtils.isEmpty(style.height))) {
-        ViewGroup.LayoutParams layoutParams = target.getLayoutParams();
-        if (!TextUtils.isEmpty(style.width)) {
-          holders.add(PropertyValuesHolder.ofInt(new WidthProperty(), layoutParams.width,
-              (int) WXViewUtils.getRealPxByWidth(WXUtils.getFloat(style.width), viewPortWidth)));
-        }
-        if (!TextUtils.isEmpty(style.height)) {
-          holders.add(PropertyValuesHolder.ofInt(new HeightProperty(), layoutParams.height,
-              (int) WXViewUtils.getRealPxByWidth(WXUtils.getFloat(style.height), viewPortWidth)));
-        }
-      }
-
-      if (style.getPivot() != null) {
-        Pair<Float, Float> pair = style.getPivot();
-        target.setPivotX(pair.first);
-        target.setPivotY(pair.second);
-      }
-      animator = ObjectAnimator.ofPropertyValuesHolder(
-          target, holders.toArray(new PropertyValuesHolder[holders.size()]));
-      animator.setStartDelay(mAnimationBean.delay);
-      return animator;
-    } else {
-      return null;
-    }
-  }
-
-  private
-  @Nullable
-  Animator.AnimatorListener createAnimatorListener(final WXSDKInstance instance, @Nullable final String callBack) {
-    if (!TextUtils.isEmpty(callBack)) {
-      return new AnimatorListenerAdapter() {
-        @Override
-        public void onAnimationEnd(Animator animation) {
-          if (instance == null || instance.isDestroy()) {
-            WXLogUtils.e("RenderContextImpl-onAnimationEnd WXSDKInstance == null NPE or instance is destroyed");
-          } else {
-            WXSDKManager.getInstance().callback(instance.getInstanceId(),
-                                                callBack,
-                                                new HashMap<String, Object>());
-          }
-        }
-      };
-    } else {
-      return null;
-    }
-  }
-
-  private
-  @Nullable
-  Interpolator createTimeInterpolator() {
-    String interpolator = mAnimationBean.timingFunction;
-    if (!TextUtils.isEmpty(interpolator)) {
-      switch (interpolator) {
-        case WXAnimationBean.EASE_IN:
-          return new AccelerateInterpolator();
-        case WXAnimationBean.EASE_OUT:
-          return new DecelerateInterpolator();
-        case WXAnimationBean.EASE_IN_OUT:
-          return new AccelerateDecelerateInterpolator();
-        case WXAnimationBean.LINEAR:
-          return new LinearInterpolator();
-        default:
-          //Parse cubic-bezier
-          try {
-            SingleFunctionParser<Float> parser = new SingleFunctionParser<>(
-                mAnimationBean.timingFunction,
-                new SingleFunctionParser.FlatMapper<Float>() {
-                  @Override
-                  public Float map(String raw) {
-                    return Float.parseFloat(raw);
-                  }
-                });
-            List<Float> params = parser.parse(WXAnimationBean.CUBIC_BEZIER);
-            if (params != null && params.size() == WXAnimationBean.NUM_CUBIC_PARAM) {
-              return PathInterpolatorCompat.create(
-                  params.get(0), params.get(1), params.get(2), params.get(3));
-            } else {
-              return null;
-            }
-          } catch (RuntimeException e) {
-            return null;
-          }
-      }
-    }
-    return null;
-  }
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAppendTreeCreateFinish.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAppendTreeCreateFinish.java
deleted file mode 100644
index 0fe09f0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionAppendTreeCreateFinish.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-
-/**
- * Created by listen on 18/01/09.
- */
-public class GraphicActionAppendTreeCreateFinish extends BasicGraphicAction {
-
-  WXComponent component;
-
-  public GraphicActionAppendTreeCreateFinish(WXSDKInstance instance, String ref) {
-    super(instance, ref);
-
-    component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), ref);
-    if (null != component && component instanceof WXVContainer) {
-      ((WXVContainer)component).appendTreeCreateFinish();
-    }
-  }
-
-  @Override
-  public void executeAction() {
-
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchAction.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchAction.java
deleted file mode 100644
index 901db40..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchAction.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-
-import java.util.ArrayList;
-import java.util.List;
-
-public class GraphicActionBatchAction extends BasicGraphicAction {
-    private List<BasicGraphicAction> mActions;
-
-    public GraphicActionBatchAction(WXSDKInstance instance, String ref, List<BasicGraphicAction> mActions) {
-        super(instance, ref);
-        this.mActions = new ArrayList<>(mActions);
-    }
-
-    @Override
-    public void executeAction() {
-        for (int i = 0;i < mActions.size();i ++) {
-            mActions.get(i).executeAction();
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchBegin.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchBegin.java
deleted file mode 100644
index d61540a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchBegin.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-
-public class GraphicActionBatchBegin extends BasicGraphicAction {
-    public GraphicActionBatchBegin(WXSDKInstance instance, String ref) {
-        super(instance, ref);
-        this.mActionType = ActionTypeBatchBegin;
-    }
-
-    @Override
-    public void executeAction() {
-
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchEnd.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchEnd.java
deleted file mode 100644
index 45d9744..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionBatchEnd.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-
-public class GraphicActionBatchEnd extends BasicGraphicAction {
-    public GraphicActionBatchEnd(WXSDKInstance instance, String ref) {
-        super(instance, ref);
-        this.mActionType = ActionTypeBatchEnd;
-    }
-
-    @Override
-    public void executeAction() {
-
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionCreateBody.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionCreateBody.java
deleted file mode 100644
index 49eef03..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionCreateBody.java
+++ /dev/null
@@ -1,93 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.annotation.NonNull;
-import android.widget.ScrollView;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.dom.transition.WXTransition;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXScroller;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.Map;
-import java.util.Set;
-
-public class GraphicActionCreateBody extends GraphicActionAbstractAddElement {
-
-  private WXComponent component;
-
-  public GraphicActionCreateBody(@NonNull WXSDKInstance instance, String ref,
-                                 String componentType,
-                                 Map<String, String> style,
-                                 Map<String, String> attributes,
-                                 Set<String> events,
-                                 float[] margins,
-                                 float[] paddings,
-                                 float[] borders) {
-    super(instance, ref);
-    this.mComponentType = componentType;
-    this.mStyle = style;
-    this.mAttributes = attributes;
-    this.mEvents = events;
-    this.mMargins = margins;
-    this.mPaddings = paddings;
-    this.mBorders = borders;
-
-    if (instance.getContext() == null) {
-      return;
-    }
-
-    BasicComponentData basicComponentData = new BasicComponentData(getRef(), mComponentType, null);
-    component = createComponent(instance, null, basicComponentData);
-    if (component == null) {
-      return;
-    }
-    component.setTransition(WXTransition.fromMap(component.getStyles(), component));
-  }
-
-  @Override
-  public void executeAction() {
-    super.executeAction();
-    try {
-      component.createView();
-      component.applyLayoutAndEvent(component);
-      component.bindData(component);
-      WXSDKInstance instance = getWXSDKIntance();
-
-      if (component instanceof WXScroller) {
-        WXScroller scroller = (WXScroller) component;
-        if (scroller.getInnerView() instanceof ScrollView) {
-          instance.setRootScrollView((ScrollView) scroller.getInnerView());
-        }
-      }
-
-      instance.onRootCreated(component);
-
-      if (instance.getRenderStrategy() != WXRenderStrategy.APPEND_ONCE) {
-        instance.onCreateFinish();
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("create body failed.", e);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionCreateFinish.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionCreateFinish.java
deleted file mode 100644
index c768b08..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionCreateFinish.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.annotation.NonNull;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.RenderTypes;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by listen on 18/01/09.
- */
-public class GraphicActionCreateFinish extends BasicGraphicAction {
-
-  private int mLayoutWidth;
-  private int mLayoutHeight;
-
-  public GraphicActionCreateFinish(@NonNull WXSDKInstance instance) {
-    super(instance, "");
-    WXComponent component = instance.getRootComponent();
-    if (null != component) {
-        this.mLayoutWidth = (int) component.getLayoutWidth();
-        this.mLayoutHeight = (int) component.getLayoutHeight();
-    }
-    instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_CREATE_FINISH);
-    instance.getApmForInstance().extInfo.put(WXInstanceApm.KEY_PAGE_STAGES_CREATE_FINISH,true);
-  }
-
-  @Override
-  public void executeAction() {
-    final WXSDKInstance instance = getWXSDKIntance();
-    if (instance == null || instance.getContext() == null) {
-      return;
-    }
-    if(instance.mHasCreateFinish){
-        return;
-    }
-
-    if (instance.getRenderStrategy() == WXRenderStrategy.APPEND_ONCE) {
-      instance.onCreateFinish();
-    }else{
-      if(!RenderTypes.RENDER_TYPE_NATIVE.equals(instance.getRenderType())){
-          instance.onCreateFinish();
-      }
-    }
-
-    instance.mHasCreateFinish = true;
-
-    if (null != instance.getWXPerformance()){
-      instance.getWXPerformance().callCreateFinishTime = System.currentTimeMillis()-instance.getWXPerformance().renderTimeOrigin;
-    }
-    instance.onOldFsRenderTimeLogic();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionLayout.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionLayout.java
deleted file mode 100644
index cffef17..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionLayout.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.WXComponent;
-
-public class GraphicActionLayout extends BasicGraphicAction {
-
-  private final GraphicPosition mLayoutPosition;
-  private final GraphicSize mLayoutSize;
-  private final boolean mIsLayoutRTL;
-
-  public GraphicActionLayout(WXSDKInstance instance, String ref, GraphicPosition layoutPosition, GraphicSize layoutSize, boolean isRTL) {
-    super(instance, ref);
-    this.mLayoutPosition = layoutPosition;
-    this.mLayoutSize = layoutSize;
-    this.mIsLayoutRTL = isRTL;
-  }
-
-  @Override
-  public void executeAction() {
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null) {
-      return;
-    }
-
-    component.setIsLayoutRTL(mIsLayoutRTL);
-    component.setDemission(mLayoutSize, mLayoutPosition);
-    component.setSafeLayout(component);
-    component.setPadding(component.getPadding(), component.getBorder());
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionMoveElement.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionMoveElement.java
deleted file mode 100644
index 424ee84..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionMoveElement.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-
-public class GraphicActionMoveElement extends BasicGraphicAction {
-
-  private String mParentref;
-  private int mIndex;
-
-  public GraphicActionMoveElement(WXSDKInstance instance, String ref, String parentRef, int index) {
-    super(instance, ref);
-    this.mParentref = parentRef;
-    this.mIndex = index;
-  }
-
-  @Override
-  public void executeAction() {
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if(component == null) {
-      return;
-    }
-    WXVContainer oldParent = component.getParent();
-    WXComponent newParent = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), mParentref);
-    if (oldParent == null
-            || newParent == null || !(newParent instanceof WXVContainer)) {
-      return;
-    }
-
-    if (component.getHostView() != null && !TextUtils.equals(component.getComponentType(), "video") && !TextUtils.equals(component.getComponentType(), "videoplus")) {
-      int[] location = new  int[2] ;
-      component.getHostView().getLocationInWindow(location);
-    }
-
-    oldParent.remove(component, false);
-
-    ((WXVContainer) newParent).addChild(component, mIndex);
-
-    if (component.getHostView() != null && !TextUtils.equals(component.getComponentType(), "video") && !TextUtils.equals(component.getComponentType(), "videoplus")) {
-      int[] location = new  int[2] ;
-      component.getHostView().getLocationInWindow(location);
-    }
-
-    if (!component.isVirtualComponent()) {
-      ((WXVContainer) newParent).addSubView(component.getHostView(), mIndex);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRefreshFinish.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRefreshFinish.java
deleted file mode 100644
index 0cc78bf..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRefreshFinish.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.annotation.NonNull;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by listen on 18/01/09.
- */
-public class GraphicActionRefreshFinish extends BasicGraphicAction {
-
-  private int mLayoutWidth;
-  private int mLayoutHeight;
-
-  public GraphicActionRefreshFinish(@NonNull WXSDKInstance instance) {
-    super(instance, "");
-    WXComponent component = instance.getRootComponent();
-    if (null != component) {
-        this.mLayoutWidth = (int) component.getLayoutWidth();
-        this.mLayoutHeight = (int) component.getLayoutHeight();
-    }
-  }
-
-  @Override
-  public void executeAction() {
-    final WXSDKInstance instance = getWXSDKIntance();
-    if (instance == null || instance.getContext() == null) {
-      return;
-    }
-
-    instance.onRefreshSuccess(mLayoutWidth, mLayoutHeight);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveChildFromRichtext.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveChildFromRichtext.java
deleted file mode 100755
index 5c5cf2c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveChildFromRichtext.java
+++ /dev/null
@@ -1,43 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.richtext.WXRichText;
-import com.taobao.weex.ui.component.richtext.node.RichTextNode;
-
-public class GraphicActionRemoveChildFromRichtext extends BasicGraphicAction{
-    private String ref;
-    private String parentRef;
-    private WXRichText richText;
-    public GraphicActionRemoveChildFromRichtext(WXSDKInstance instance,String ref,String parentRef,String richtextRef){
-        super(instance, richtextRef);
-        this.ref = ref;
-        this.parentRef = parentRef;
-        richText = (WXRichText) WXSDKManager.getInstance().getWXRenderManager().
-                getWXComponent(instance.getInstanceId(),richtextRef);
-        if(richText != null){
-            richText.removeChildNode(parentRef,ref);
-        }
-    }
-    @Override
-    public void executeAction() {
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveElement.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveElement.java
deleted file mode 100644
index b7e4551..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveElement.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-
-public class GraphicActionRemoveElement extends BasicGraphicAction {
-
-  public GraphicActionRemoveElement(WXSDKInstance instance, String ref) {
-    super(instance, ref);
-  }
-
-  @Override
-  public void executeAction() {
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null || component.getParent() == null || component.getInstance() == null) {
-      return;
-    }
-    clearRegistryForComponent(component);
-    WXVContainer parent = component.getParent();
-
-    if (component.getHostView() != null && !TextUtils.equals(component.getComponentType(), "video") && !TextUtils.equals(component.getComponentType(), "videoplus")) {
-      int[] location = new  int[2];
-      component.getHostView().getLocationInWindow(location);
-      //component.getInstance().onChangeElement(parent, location[1] > component.getInstance().getWeexHeight() + 1);
-    }
-
-    parent.remove(component, true);
-  }
-
-  private void clearRegistryForComponent(WXComponent component) {
-    WXComponent removedComponent = WXSDKManager.getInstance().getWXRenderManager().unregisterComponent(getPageId(), getRef());
-    if (removedComponent != null) {
-      removedComponent.removeAllEvent();
-      removedComponent.removeStickyStyle();
-    }
-    if (component instanceof WXVContainer) {
-      WXVContainer container = (WXVContainer) component;
-      int count = container.childCount();
-      for (int i = count - 1; i >= 0; --i) {
-        clearRegistryForComponent(container.getChild(i));
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveEvent.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveEvent.java
deleted file mode 100644
index 67fe133..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRemoveEvent.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.tracing.Stopwatch;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by listen on 18/01/11.
- */
-public class GraphicActionRemoveEvent extends BasicGraphicAction {
-
-  private final String mEvent;
-
-  public GraphicActionRemoveEvent(WXSDKInstance instance, String ref, Object event) {
-    super(instance, ref);
-    this.mEvent = WXEvent.getEventName(event);
-  }
-
-  @Override
-  public void executeAction() {
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null) {
-      return;
-    }
-
-    Stopwatch.tick();
-    component.removeEvent(mEvent);
-    Stopwatch.split("removeEventFromComponent");
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRenderSuccess.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRenderSuccess.java
deleted file mode 100644
index ecd12b1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionRenderSuccess.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.annotation.NonNull;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.ui.component.WXComponent;
-
-public class GraphicActionRenderSuccess extends BasicGraphicAction {
-
-    public GraphicActionRenderSuccess(@NonNull WXSDKInstance instance) {
-        super(instance, "");
-    }
-
-    @Override
-    public void executeAction() {
-        final WXSDKInstance instance = getWXSDKIntance();
-        if (instance == null || instance.getContext() == null) {
-            return;
-        }
-        WXComponent component = instance.getRootComponent();
-        int layoutWidth = 0;
-        int layoutHeight = 0;
-        if (null != component) {
-            layoutWidth = (int) component.getLayoutWidth();
-            layoutHeight = (int) component.getLayoutHeight();
-        }
-        instance.onRenderSuccess(layoutWidth, layoutHeight);
-    }
-
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionScrollToElement.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionScrollToElement.java
deleted file mode 100644
index c03e930..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionScrollToElement.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.Scrollable;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by listen on 18/01/09.
- */
-public class GraphicActionScrollToElement extends BasicGraphicAction {
-
-  private final JSONObject mOptions;
-
-  public GraphicActionScrollToElement(WXSDKInstance instance, String ref, JSONObject options) {
-    super(instance, ref);
-    this.mOptions = options;
-  }
-
-  @Override
-  public void executeAction() {
-    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null) {
-      return;
-    }
-
-    Scrollable scroller = component.getParentScroller();
-    if (scroller == null) {
-      return;
-    }
-    scroller.scrollTo(component, mOptions);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateAttr.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateAttr.java
deleted file mode 100644
index 4e6a00f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateAttr.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.WXComponent;
-
-import java.util.Map;
-
-public class GraphicActionUpdateAttr extends BasicGraphicAction {
-
-  private Map<String, String> mAttrs;
-  private WXComponent component;
-
-  public GraphicActionUpdateAttr(WXSDKInstance instance, String ref,
-                                 Map<String, String> attrs) {
-    super(instance, ref);
-    this.mAttrs = attrs;
-
-    component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null) {
-      return;
-    }
-    if (mAttrs != null) {
-      component.addAttr(mAttrs);
-    }
-  }
-
-  @Override
-  public void executeAction() {
-    if (component == null) {
-      return;
-    }
-    component.getAttrs().mergeAttr();
-    component.updateAttrs(mAttrs);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateRichtextAttr.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateRichtextAttr.java
deleted file mode 100755
index 3c30eb5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateRichtextAttr.java
+++ /dev/null
@@ -1,43 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.richtext.WXRichText;
-import java.util.HashMap;
-import java.util.Map;
-
-public class GraphicActionUpdateRichtextAttr extends BasicGraphicAction{
-
-    public GraphicActionUpdateRichtextAttr(WXSDKInstance instance, String ref, HashMap<String, String> attrs, String parentRef, String richTextRef){
-        super(instance, richTextRef);
-        WXRichText richText =  (WXRichText) WXSDKManager.getInstance().getWXRenderManager()
-                .getWXComponent(getPageId(), richTextRef);
-        if(richText != null) {
-            Map<String, Object> map = new HashMap<>();
-            map.putAll(attrs);
-            richText.updateChildNodeAttrs(ref, map);
-        }
-    }
-    @Override
-    public void executeAction() {
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateRichtextStyle.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateRichtextStyle.java
deleted file mode 100755
index c5c3231..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateRichtextStyle.java
+++ /dev/null
@@ -1,45 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.richtext.WXRichText;
-import com.taobao.weex.ui.component.richtext.node.RichTextNode;
-
-import java.util.HashMap;
-import java.util.Map;
-
-public class GraphicActionUpdateRichtextStyle  extends BasicGraphicAction{
-    public GraphicActionUpdateRichtextStyle(WXSDKInstance instance, String ref, HashMap<String, String> styles, String parentRef, String richTextRef){
-        super(instance, richTextRef);
-        WXRichText richText =  (WXRichText) WXSDKManager.getInstance().getWXRenderManager()
-                .getWXComponent(getPageId(), richTextRef);
-        if(richText != null){
-                Map<String, Object> map = new HashMap<>();
-                map.putAll(styles);
-                richText.updateChildNodeStyles(ref, map);
-
-        }
-    }
-    @Override
-    public void executeAction() {
-
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateStyle.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateStyle.java
deleted file mode 100644
index bddb338..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicActionUpdateStyle.java
+++ /dev/null
@@ -1,142 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.support.v4.util.ArrayMap;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.dom.transition.WXTransition;
-import com.taobao.weex.ui.component.WXComponent;
-
-import java.util.Map;
-
-public class GraphicActionUpdateStyle extends BasicGraphicAction {
-
-  private Map<String, Object> mStyle;
-  private WXComponent component;
-  private boolean mIsCausedByPesudo;
-  private boolean mIsBorderSet;
-
-  public GraphicActionUpdateStyle(WXSDKInstance instance, String ref,
-                                  Map<String, Object> style,
-                                  Map<String, String> paddings,
-                                  Map<String, String> margins,
-                                  Map<String, String> borders) {
-    this(instance, ref, style, paddings, margins, borders, false);
-  }
-
-  public GraphicActionUpdateStyle(WXSDKInstance instance, String ref,
-                                  Map<String, Object> style,
-                                  CSSShorthand paddings,
-                                  CSSShorthand margins,
-                                  CSSShorthand borders, boolean byPesudo) {
-    super(instance, ref);
-    this.mStyle = style;
-    this.mIsCausedByPesudo = byPesudo;
-
-    component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null) {
-      return;
-    }
-    if (null != mStyle) {
-      component.updateStyle(mStyle, mIsCausedByPesudo);
-      if(style.containsKey(Constants.Name.TRANSFORM) && component.getTransition() == null) {
-        Map<String, Object> animationMap = new ArrayMap<>(2);
-        animationMap.put(Constants.Name.TRANSFORM, style.get(Constants.Name.TRANSFORM));
-        animationMap
-            .put(Constants.Name.TRANSFORM_ORIGIN, style.get(Constants.Name.TRANSFORM_ORIGIN));
-        component.addAnimationForElement(animationMap);
-      }
-    }
-
-    if (null != paddings) {
-      component.setPaddings(paddings);
-    }
-
-    if (null != margins) {
-      component.setMargins(margins);
-    }
-
-    if (null != borders) {
-      mIsBorderSet = true;
-      component.setBorders(borders);
-    }
-  }
-
-  public GraphicActionUpdateStyle(WXSDKInstance instance, String ref,
-                                  Map<String, Object> style,
-                                  Map<String, String> paddings,
-                                  Map<String, String> margins,
-                                  Map<String, String> borders, boolean byPesudo) {
-    super(instance, ref);
-    this.mStyle = style;
-    this.mIsCausedByPesudo = byPesudo;
-
-    component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-    if (component == null) {
-      return;
-    }
-    if (null != mStyle) {
-      component.addStyle(mStyle, mIsCausedByPesudo);
-      if(style.containsKey(Constants.Name.TRANSFORM) && component.getTransition() == null){
-        Map<String, Object> animationMap = new ArrayMap<>(2);
-        animationMap.put(Constants.Name.TRANSFORM, style.get(Constants.Name.TRANSFORM));
-        animationMap.put(Constants.Name.TRANSFORM_ORIGIN, style.get(Constants.Name.TRANSFORM_ORIGIN));
-        component.addAnimationForElement(animationMap);
-        WXBridgeManager.getInstance().markDirty(component.getInstanceId(), component.getRef(), true);
-      }
-    }
-
-    if (null != paddings) {
-      component.addShorthand(paddings);
-    }
-
-    if (null != margins) {
-      component.addShorthand(margins);
-    }
-
-    if (null != borders) {
-      mIsBorderSet = true;
-      component.addShorthand(borders);
-    }
-  }
-
-  @Override
-  public void executeAction() {
-    if (component == null) return;
-    if (mStyle != null) {
-      if(component.getTransition() != null){
-        component.getTransition().updateTranstionParams(mStyle);
-        if(component.getTransition().hasTransitionProperty(mStyle)){
-          component.getTransition().startTransition(mStyle);
-        }
-      } else {
-        component.setTransition(WXTransition.fromMap(mStyle, component));
-        component.updateStyles(mStyle);
-      }
-    } else if (mIsBorderSet) {
-      component.updateStyles(component);
-    }
-  }
-}
-
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicPosition.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicPosition.java
deleted file mode 100644
index 9837809..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicPosition.java
+++ /dev/null
@@ -1,74 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-public class GraphicPosition {
-
-  private float mLeft;
-  private float mTop;
-  private float mRight;
-  private float mBottom;
-
-  public GraphicPosition(float left, float top, float right, float bottom) {
-    this.mLeft = left;
-    this.mTop = top;
-    this.mRight = right;
-    this.mBottom = bottom;
-  }
-
-  public float getLeft() {
-    return mLeft;
-  }
-
-  public void setLeft(float left) {
-    this.mLeft = left;
-  }
-
-  public float getTop() {
-    return mTop;
-  }
-
-  public void setTop(float top) {
-    this.mTop = top;
-  }
-
-  public float getRight() {
-    return mRight;
-  }
-
-  public void setRight(float right) {
-    this.mRight = right;
-  }
-
-  public float getBottom() {
-    return mBottom;
-  }
-
-  public void setBottom(float bottom) {
-    this.mBottom = bottom;
-  }
-
-
-  public void update(float top, float bottom, float left, float right) {
-    this.mTop = top;
-    this.mBottom = bottom;
-    this.mLeft = left;
-    this.mRight = right;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicSize.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicSize.java
deleted file mode 100644
index 35d6439..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/GraphicSize.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-public class GraphicSize {
-
-  private float mWidth;
-  private float mHeight;
-
-  public GraphicSize(float width, float height) {
-    this.mWidth = width;
-    this.mHeight = height;
-  }
-
-  public float getWidth() {
-    return mWidth;
-  }
-
-  public void setWidth(float width) {
-    this.mWidth = width;
-  }
-
-  public float getHeight() {
-    return mHeight;
-  }
-
-  public void setHeight(float height) {
-    this.mHeight = height;
-  }
-
-  public void update(float width, float height) {
-    this.mWidth = width;
-    this.mHeight = height;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/IExecutable.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/IExecutable.java
deleted file mode 100644
index 399d249..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/IExecutable.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-public interface IExecutable {
-
-  void executeAction();
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/action/UpdateComponentDataAction.java b/android/sdk/src/main/java/com/taobao/weex/ui/action/UpdateComponentDataAction.java
deleted file mode 100644
index b5e412e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/action/UpdateComponentDataAction.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.action;
-
-import android.text.TextUtils;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.SimpleJSCallback;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.list.template.CellDataManager;
-import com.taobao.weex.ui.component.list.template.WXRecyclerTemplateList;
-import com.taobao.weex.utils.WXLogUtils;
-
-
-/**
- * Created by furture on 2018/1/23.
- */
-
-public class UpdateComponentDataAction extends BasicGraphicAction{
-
-    private String virtualComponentId;
-    private JSONObject data;
-    private String callback;
-
-
-    public UpdateComponentDataAction(WXSDKInstance instance, String virtualComponentId,
-                                     JSONObject data, String callback) {
-        super(instance, CellDataManager.getListRef(virtualComponentId));
-        this.virtualComponentId = virtualComponentId;
-        this.data = data;
-        this.callback = callback;
-    }
-
-    @Override
-    public void executeAction() {
-        if(TextUtils.isEmpty(getRef())){
-            WXLogUtils.e("wrong virtualComponentId split error " + virtualComponentId);
-            return;
-        }
-        WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
-        if(component instanceof WXRecyclerTemplateList){
-            WXRecyclerTemplateList templateList = (WXRecyclerTemplateList) component;
-            templateList.getCellDataManager().updateVirtualComponentData(virtualComponentId, data);
-            templateList.notifyUpdateList();
-            SimpleJSCallback jsCallback = new SimpleJSCallback(component.getInstanceId(), callback);
-            jsCallback.invoke(true);
-        }else{
-            WXLogUtils.e("recycler-list wrong virtualComponentId " + virtualComponentId);
-        }
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/animation/BackgroundColorProperty.java b/android/sdk/src/main/java/com/taobao/weex/ui/animation/BackgroundColorProperty.java
deleted file mode 100644
index 219f295..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/animation/BackgroundColorProperty.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.ui.animation;
-
-
-import android.graphics.Color;
-import android.graphics.drawable.ColorDrawable;
-import android.util.Property;
-import android.view.View;
-
-import com.taobao.weex.ui.view.border.BorderDrawable;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-public class BackgroundColorProperty extends Property<View, Integer> {
-
-  private final static String TAG = "BackgroundColorAnimation";
-
-  public BackgroundColorProperty() {
-    super(Integer.class, WXAnimationBean.Style.BACKGROUND_COLOR);
-  }
-
-  @Override
-  public Integer get(View object) {
-    int color;
-    BorderDrawable borderDrawable;
-    if ((borderDrawable = WXViewUtils.getBorderDrawable(object)) != null) {
-      color = borderDrawable.getColor();
-    } else if (object.getBackground() instanceof ColorDrawable) {
-      color = ((ColorDrawable) object.getBackground()).getColor();
-    } else {
-      color = Color.TRANSPARENT;
-      WXLogUtils.e(TAG, "Unsupported background type");
-    }
-    return color;
-  }
-
-  @Override
-  public void set(View object, Integer value) {
-    BorderDrawable borderDrawable;
-    if ((borderDrawable = WXViewUtils.getBorderDrawable(object)) != null) {
-      borderDrawable.setColor(value);
-    } else if (object.getBackground() instanceof ColorDrawable) {
-      ((ColorDrawable) object.getBackground()).setColor(value);
-    } else {
-      WXLogUtils.e(TAG, "Unsupported background type");
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/animation/CameraDistanceProperty.java b/android/sdk/src/main/java/com/taobao/weex/ui/animation/CameraDistanceProperty.java
deleted file mode 100644
index 67b9235..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/animation/CameraDistanceProperty.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.animation;
-
-import android.os.Build.VERSION;
-import android.os.Build.VERSION_CODES;
-import android.util.Property;
-import android.view.View;
-
-
-class CameraDistanceProperty extends Property<View, Float> {
-
-  private final static String TAG = "CameraDistance";
-  private static CameraDistanceProperty instance;
-
-  static Property<View, Float> getInstance(){
-    return instance;
-  }
-
-  private CameraDistanceProperty() {
-    super(Float.class, TAG);
-  }
-
-  @Override
-  public Float get(View view) {
-    if (VERSION.SDK_INT >= VERSION_CODES.JELLY_BEAN) {
-      return view.getCameraDistance();
-    }
-    else{
-      return Float.NaN;
-    }
-  }
-
-  @Override
-  public void set(View object, Float value) {
-    object.setCameraDistance(value);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/animation/HeightProperty.java b/android/sdk/src/main/java/com/taobao/weex/ui/animation/HeightProperty.java
deleted file mode 100644
index b268ed2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/animation/HeightProperty.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.animation;
-
-
-import android.view.ViewGroup.LayoutParams;
-
-public class HeightProperty extends LayoutParamsProperty {
-
-  @Override
-  protected Integer getProperty(LayoutParams layoutParams) {
-    return layoutParams.height;
-  }
-
-  @Override
-  protected void setProperty(LayoutParams layoutParams, Integer expected) {
-    layoutParams.height = expected;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/animation/LayoutParamsProperty.java b/android/sdk/src/main/java/com/taobao/weex/ui/animation/LayoutParamsProperty.java
deleted file mode 100644
index 312180e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/animation/LayoutParamsProperty.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.animation;
-
-
-import android.util.Property;
-import android.view.View;
-import android.view.ViewGroup.LayoutParams;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.view.IRenderResult;
-
-/**
- * android.util.IntProperty<T> cannot be applied here, as it is only added at API 24.
- */
-abstract class LayoutParamsProperty extends Property<View, Integer> {
-
-  LayoutParamsProperty() {
-    super(Integer.class, "layoutParams");
-  }
-
-  @Override
-  public Integer get(View object) {
-    LayoutParams layoutParams;
-    if (object != null && (layoutParams = object.getLayoutParams()) != null) {
-      return getProperty(layoutParams);
-    }
-    return 0;
-  }
-
-  @Override
-  public void set(View object, Integer value) {
-    LayoutParams layoutParams;
-    if (object != null && (layoutParams = object.getLayoutParams()) != null) {
-      setProperty(layoutParams, value);
-      if (object instanceof IRenderResult) {
-        WXComponent component = ((IRenderResult) object).getComponent();
-        if (component != null) {
-            component.notifyNativeSizeChanged(layoutParams.width, layoutParams.height);
-        }
-      }
-      object.requestLayout();
-    }
-  }
-
-  protected abstract Integer getProperty(LayoutParams layoutParams);
-
-  protected abstract void setProperty(LayoutParams layoutParams, Integer expected);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/animation/TransformParser.java b/android/sdk/src/main/java/com/taobao/weex/ui/animation/TransformParser.java
deleted file mode 100644
index 38eb709..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/animation/TransformParser.java
+++ /dev/null
@@ -1,310 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.animation;
-
-import android.animation.PropertyValuesHolder;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-import android.util.Pair;
-import android.util.Property;
-import android.view.View;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.utils.FunctionParser;
-import com.taobao.weex.utils.WXDataStructureUtil;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.LinkedHashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Created by furture on 2017/10/24.
- */
-
-public class TransformParser {
-
-    public final static String WX_TRANSLATE = "translate";
-    public final static String WX_TRANSLATE_X = "translateX";
-    public final static String WX_TRANSLATE_Y = "translateY";
-    public final static String WX_ROTATE = "rotate";
-    public final static String WX_ROTATE_X ="rotateX";
-    public final static String WX_ROTATE_Y ="rotateY";
-    public final static String WX_ROTATE_Z ="rotateZ";
-    public final static String WX_SCALE = "scale";
-    public final static String WX_SCALE_X = "scaleX";
-    public final static String WX_SCALE_Y = "scaleY";
-
-    public final static String BACKGROUND_COLOR = Constants.Name.BACKGROUND_COLOR;
-    public final static String WIDTH = Constants.Name.WIDTH;
-    public final static String HEIGHT = Constants.Name.HEIGHT;
-    public final static String TOP = "top";
-    public final static String BOTTOM = "bottom";
-    public final static String RIGHT = "right";
-    public final static String LEFT = "left";
-    public final static String CENTER = "center";
-    private static final String HALF = "50%";
-    private static final String FULL = "100%";
-    private static final String ZERO = "0%";
-    private static final String PX = "px";
-    private static final String DEG = "deg";
-    public static Map<String, List<Property<View,Float>>> wxToAndroidMap = new ArrayMap<>();
-
-
-    static {
-        wxToAndroidMap.put(WX_TRANSLATE, Arrays.asList
-                (View.TRANSLATION_X, View.TRANSLATION_Y));
-        wxToAndroidMap.put(WX_TRANSLATE_X, Collections.singletonList(View.TRANSLATION_X));
-        wxToAndroidMap.put(WX_TRANSLATE_Y, Collections.singletonList(View.TRANSLATION_Y));
-        wxToAndroidMap.put(WX_ROTATE, Collections.singletonList(View.ROTATION));
-        wxToAndroidMap.put(WX_ROTATE_Z, Collections.singletonList(View.ROTATION));
-        wxToAndroidMap.put(WX_ROTATE_X, Collections.singletonList(View.ROTATION_X));
-        wxToAndroidMap.put(WX_ROTATE_Y, Collections.singletonList(View.ROTATION_Y));
-        wxToAndroidMap.put(WX_SCALE, Arrays.asList(View.SCALE_X, View.SCALE_Y));
-        wxToAndroidMap.put(WX_SCALE_X, Collections.singletonList(View.SCALE_X));
-        wxToAndroidMap.put(WX_SCALE_Y, Collections.singletonList(View.SCALE_Y));
-        wxToAndroidMap.put(Constants.Name.PERSPECTIVE, Collections.singletonList(CameraDistanceProperty.getInstance()));
-        wxToAndroidMap = Collections.unmodifiableMap(wxToAndroidMap);
-    }
-
-    public static PropertyValuesHolder[] toHolders(Map<Property<View,Float>, Float> transformMap){
-        PropertyValuesHolder[]  holders = new PropertyValuesHolder[transformMap.size()];
-        int i=0;
-        for (Map.Entry<Property<View, Float>, Float> entry : transformMap.entrySet()) {
-            holders[i] = PropertyValuesHolder.ofFloat(entry.getKey(), entry.getValue());
-            i++;
-        }
-        return holders;
-    }
-
-    public static Map<Property<View,Float>, Float> parseTransForm(String instanceId, @Nullable String rawTransform, final int width,
-                                                                  final int height, final int viewportW) {
-        try{
-
-            if (!TextUtils.isEmpty(rawTransform)) {
-                FunctionParser<Property<View,Float>, Float> parser = new FunctionParser<>
-                        (rawTransform, new FunctionParser.Mapper<Property<View,Float>, Float>() {
-                            @Override
-                            public Map<Property<View,Float>, Float> map(String functionName, List<String> raw) {
-                                if (raw != null && !raw.isEmpty()) {
-                                    if (wxToAndroidMap.containsKey(functionName)) {
-                                        return convertParam(width, height,viewportW, wxToAndroidMap.get(functionName), raw);
-                                    }
-                                }
-                                return new HashMap<>();
-                            }
-
-                            private Map<Property<View,Float>, Float> convertParam(int width, int height, int viewportW,
-                                                                                  @NonNull List<Property<View,Float>> propertyList,
-                                                                                  @NonNull List<String> rawValue) {
-
-                                Map<Property<View,Float>, Float> result = WXDataStructureUtil.newHashMapWithExpectedSize(propertyList.size());
-                                List<Float> convertedList = new ArrayList<>(propertyList.size());
-                                if (propertyList.contains(View.ROTATION) ||
-                                        propertyList.contains(View.ROTATION_X) ||
-                                        propertyList.contains(View.ROTATION_Y)) {
-                                    convertedList.addAll(parseRotationZ(rawValue));
-                                }else if (propertyList.contains(View.TRANSLATION_X) ||
-                                        propertyList.contains(View.TRANSLATION_Y)) {
-                                    convertedList.addAll(parseTranslation(propertyList, width, height, rawValue,viewportW));
-                                } else if (propertyList.contains(View.SCALE_X) ||
-                                        propertyList.contains(View.SCALE_Y)) {
-                                    convertedList.addAll(parseScale(propertyList.size(), rawValue));
-                                }
-                                else if(propertyList.contains(CameraDistanceProperty.getInstance())){
-                                    convertedList.add(parseCameraDistance(rawValue));
-                                }
-                                if (propertyList.size() == convertedList.size()) {
-                                    for (int i = 0; i < propertyList.size(); i++) {
-                                        result.put(propertyList.get(i), convertedList.get(i));
-                                    }
-                                }
-                                return result;
-                            }
-
-                            private List<Float> parseScale(int size, @NonNull List<String> rawValue) {
-                                List<Float> convertedList = new ArrayList<>(rawValue.size() * 2);
-                                List<Float> rawFloat = new ArrayList<>(rawValue.size());
-                                for (String item : rawValue) {
-                                    rawFloat.add(WXUtils.fastGetFloat(item));
-                                }
-                                convertedList.addAll(rawFloat);
-                                if (size != 1 && rawValue.size() == 1) {
-                                    convertedList.addAll(rawFloat);
-                                }
-                                return convertedList;
-                            }
-
-                            private @NonNull
-                            List<Float> parseRotationZ(@NonNull List<String> rawValue) {
-                                List<Float> convertedList = new ArrayList<>(1);
-                                int suffix;
-                                for (String raw : rawValue) {
-                                    if ((suffix = raw.lastIndexOf(DEG)) != -1) {
-                                        convertedList.add(WXUtils.fastGetFloat(raw.substring(0, suffix)));
-                                    } else {
-                                        convertedList.add((float) Math.toDegrees(WXUtils.fastGetFloat(raw)));
-                                    }
-                                }
-                                return convertedList;
-                            }
-
-                            /**
-                             * As "translate(50%, 25%)" or "translate(25px, 30px)" both are valid,
-                             * parsing translate is complicated than other method.
-                             * Add your waste time here if you try to optimize this method like {@link #parseScale(int, List)}
-                             * Time: 0.5h
-                             */
-                            private List<Float> parseTranslation(List<Property<View,Float>> propertyList,
-                                                                 int width, int height,
-                                                                 @NonNull List<String> rawValue, int viewportW) {
-                                List<Float> convertedList = new ArrayList<>(2);
-                                String first = rawValue.get(0);
-                                if (propertyList.size() == 1) {
-                                    parseSingleTranslation(propertyList, width, height, convertedList, first,viewportW);
-                                } else {
-                                    parseDoubleTranslation(width, height, rawValue, convertedList, first,viewportW);
-                                }
-                                return convertedList;
-                            }
-
-                            private void parseSingleTranslation(List<Property<View,Float>> propertyList, int width, int height,
-                                                                List<Float> convertedList, String first, int viewportW) {
-                                if (propertyList.contains(View.TRANSLATION_X)) {
-                                    convertedList.add(parsePercentOrPx(first, width,viewportW));
-                                } else if (propertyList.contains(View.TRANSLATION_Y)) {
-                                    convertedList.add(parsePercentOrPx(first, height,viewportW));
-                                }
-                            }
-
-                            private void parseDoubleTranslation(int width, int height,
-                                                                @NonNull List<String> rawValue,
-                                                                List<Float> convertedList, String first, int viewportW) {
-                                String second;
-                                if (rawValue.size() == 1) {
-                                    second = first;
-                                } else {
-                                    second = rawValue.get(1);
-                                }
-                                convertedList.add(parsePercentOrPx(first, width,viewportW));
-                                convertedList.add(parsePercentOrPx(second, height,viewportW));
-                            }
-
-                            private Float parseCameraDistance(List<String> rawValue){
-                                float ret= Float.MAX_VALUE;
-                                if(rawValue.size() == 1){
-                                    float value = WXViewUtils.getRealPxByWidth(WXUtils.getFloat(rawValue.get(0)), viewportW);
-                                    float scale = WXEnvironment.getApplication().getResources().getDisplayMetrics().density;
-                                    if (!Float.isNaN(value) && value > 0) {
-                                        ret = value * scale;
-                                    }
-                                }
-                                return ret;
-                            }
-                        });
-                return parser.parse();
-            }
-        }catch (Exception e){
-            WXLogUtils.e("TransformParser", e);
-            WXExceptionUtils.commitCriticalExceptionRT(instanceId,
-                    WXErrorCode.WX_RENDER_ERR_TRANSITION,
-                    "parse animation transition",
-                    WXErrorCode.WX_RENDER_ERR_TRANSITION.getErrorMsg() + "parse transition error: " +  e.getMessage(),
-                    null);
-        }
-        return new LinkedHashMap<>();
-    }
-
-    private static Pair<Float, Float> parsePivot(@Nullable String transformOrigin,
-                                                 int width, int height, int viewportW) {
-        if (!TextUtils.isEmpty(transformOrigin)) {
-            int firstSpace = transformOrigin.indexOf(FunctionParser.SPACE);
-            if (firstSpace != -1) {
-                int i = firstSpace;
-                for (; i < transformOrigin.length(); i++) {
-                    if (transformOrigin.charAt(i) != FunctionParser.SPACE) {
-                        break;
-                    }
-                }
-                if (i < transformOrigin.length() && transformOrigin.charAt(i) != FunctionParser.SPACE) {
-                    List<String> list = new ArrayList<>(2);
-                    list.add(transformOrigin.substring(0, firstSpace).trim());
-                    list.add(transformOrigin.substring(i, transformOrigin.length()).trim());
-                    return parsePivot(list, width, height,viewportW);
-                }
-            }
-        }
-        return null;
-    }
-
-    private static Pair<Float, Float> parsePivot(@NonNull List<String> list, int width, int height, int viewportW) {
-        return new Pair<>(
-                parsePivotX(list.get(0), width,viewportW), parsePivotY(list.get(1), height,viewportW));
-    }
-
-    private static float parsePivotX(String x, int width, int viewportW) {
-        String value = x;
-        if (WXAnimationBean.Style.LEFT.equals(x)) {
-            value = ZERO;
-        } else if (WXAnimationBean.Style.RIGHT.equals(x)) {
-            value = FULL;
-        } else if (WXAnimationBean.Style.CENTER.equals(x)) {
-            value = HALF;
-        }
-        return parsePercentOrPx(value, width,viewportW);
-    }
-
-    private static float parsePivotY(String y, int height, int viewportW) {
-        String value = y;
-        if (WXAnimationBean.Style.TOP.equals(y)) {
-            value = ZERO;
-        } else if (WXAnimationBean.Style.BOTTOM.equals(y)) {
-            value = FULL;
-        } else if (WXAnimationBean.Style.CENTER.equals(y)) {
-            value = HALF;
-        }
-        return parsePercentOrPx(value, height,viewportW);
-    }
-
-    private static float parsePercentOrPx(String raw, int unit, int viewportW) {
-        final int precision = 1;
-        int suffix;
-        if ((suffix = raw.lastIndexOf(WXUtils.PERCENT)) != -1) {
-            return parsePercent(raw.substring(0, suffix), unit, precision);
-        } else if ((suffix = raw.lastIndexOf(PX)) != -1) {
-            return WXViewUtils.getRealPxByWidth(WXUtils.fastGetFloat(raw.substring(0, suffix), precision),viewportW);
-        }
-        return WXViewUtils.getRealPxByWidth(WXUtils.fastGetFloat(raw, precision),viewportW);
-    }
-
-    private static float parsePercent(String percent, int unit, int precision) {
-        return WXUtils.fastGetFloat(percent, precision) / 100 * unit;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/animation/WXAnimationBean.java b/android/sdk/src/main/java/com/taobao/weex/ui/animation/WXAnimationBean.java
deleted file mode 100644
index 4401cb9..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/animation/WXAnimationBean.java
+++ /dev/null
@@ -1,242 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.animation;
-
-import android.animation.PropertyValuesHolder;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-import android.util.Pair;
-import android.util.Property;
-import android.view.View;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.Constants.Name;
-import com.taobao.weex.utils.FunctionParser;
-import com.taobao.weex.utils.WXDataStructureUtil;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.LinkedHashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-import java.util.Map.Entry;
-
-public class WXAnimationBean {
-
-  public final static String LINEAR = "linear";
-  public final static String EASE_IN_OUT = "ease-in-out";
-  public final static String EASE_IN = "ease-in";
-  public final static String EASE_OUT = "ease-out";
-  public final static String CUBIC_BEZIER = "cubic-bezier";
-  public final static int NUM_CUBIC_PARAM = 4;
-  public long delay;
-  public long duration;
-  public String timingFunction;
-  public @Nullable Style styles;
-  public boolean needLayout;
-
-  public static class Style {
-
-    public final static String WX_TRANSLATE = "translate";
-    public final static String WX_TRANSLATE_X = "translateX";
-    public final static String WX_TRANSLATE_Y = "translateY";
-    public final static String WX_ROTATE = "rotate";
-    public final static String WX_SCALE_X = "scaleX";
-    public final static String WX_SCALE_Y = "scaleY";
-    public final static String WX_SCALE = "scale";
-    public final static String WX_ROTATE_X ="rotateX";
-    public final static String WX_ROTATE_Y ="rotateY";
-    public final static String BACKGROUND_COLOR = Constants.Name.BACKGROUND_COLOR;
-    public final static String WIDTH = Constants.Name.WIDTH;
-    public final static String HEIGHT = Constants.Name.HEIGHT;
-    public final static String TOP = "top";
-    public final static String BOTTOM = "bottom";
-    public final static String RIGHT = "right";
-    public final static String LEFT = "left";
-    public final static String CENTER = "center";
-    private static final String HALF = "50%";
-    private static final String FULL = "100%";
-    private static final String ZERO = "0%";
-    private static final String PX = "px";
-    private static final String DEG = "deg";
-    public static Map<String, List<Property<View,Float>>> wxToAndroidMap = new ArrayMap<>();
-    private static Map<Property<View, Float>, Float> defaultMap= new ArrayMap<>();
-
-
-    static {
-      wxToAndroidMap.put(WX_TRANSLATE, Arrays.asList
-              (View.TRANSLATION_X, View.TRANSLATION_Y));
-      wxToAndroidMap.put(WX_TRANSLATE_X, Collections.singletonList(View.TRANSLATION_X));
-      wxToAndroidMap.put(WX_TRANSLATE_Y, Collections.singletonList(View.TRANSLATION_Y));
-      wxToAndroidMap.put(WX_ROTATE, Collections.singletonList(View.ROTATION));
-      wxToAndroidMap.put(WX_ROTATE_X, Collections.singletonList(View.ROTATION_X));
-      wxToAndroidMap.put(WX_ROTATE_Y, Collections.singletonList(View.ROTATION_Y));
-      wxToAndroidMap.put(WX_SCALE, Arrays.asList(View.SCALE_X, View.SCALE_Y));
-      wxToAndroidMap.put(WX_SCALE_X, Collections.singletonList(View.SCALE_X));
-      wxToAndroidMap.put(WX_SCALE_Y, Collections.singletonList(View.SCALE_Y));
-      wxToAndroidMap.put(Name.PERSPECTIVE, Collections.singletonList(CameraDistanceProperty.getInstance()));
-      wxToAndroidMap = Collections.unmodifiableMap(wxToAndroidMap);
-      defaultMap.put(View.TRANSLATION_X, 0f);
-      defaultMap.put(View.TRANSLATION_Y, 0f);
-      defaultMap.put(View.SCALE_X, 1f);
-      defaultMap.put(View.SCALE_Y, 1f);
-      defaultMap.put(View.ROTATION, 0f);
-      defaultMap.put(View.ROTATION_X, 0f);
-      defaultMap.put(View.ROTATION_Y, 0f);
-    }
-
-    public String opacity;
-    public String backgroundColor;
-    public String width;
-    public String height;
-    public String transform;
-    public String transformOrigin;
-    private Map<Property<View, Float>, Float> transformMap = new LinkedHashMap<>();
-    private Pair<Float, Float> pivot;
-    private List<PropertyValuesHolder> holders=new LinkedList<>();
-    private float cameraDistance = Float.MAX_VALUE;
-
-
-    private static Pair<Float, Float> parsePivot(@Nullable String transformOrigin,
-                                                 int width, int height,int viewportW) {
-      if (!TextUtils.isEmpty(transformOrigin)) {
-        int firstSpace = transformOrigin.indexOf(FunctionParser.SPACE);
-        if (firstSpace != -1) {
-          int i = firstSpace;
-          for (; i < transformOrigin.length(); i++) {
-            if (transformOrigin.charAt(i) != FunctionParser.SPACE) {
-              break;
-            }
-          }
-          if (i < transformOrigin.length() && transformOrigin.charAt(i) != FunctionParser.SPACE) {
-            List<String> list = new ArrayList<>(2);
-            list.add(transformOrigin.substring(0, firstSpace).trim());
-            list.add(transformOrigin.substring(i, transformOrigin.length()).trim());
-            return parsePivot(list, width, height,viewportW);
-          }
-        }
-      }
-      return null;
-    }
-
-    private static Pair<Float, Float> parsePivot(@NonNull List<String> list, int width, int height,int viewportW) {
-      return new Pair<>(
-              parsePivotX(list.get(0), width,viewportW), parsePivotY(list.get(1), height,viewportW));
-    }
-
-    private static float parsePivotX(String x, int width,int viewportW) {
-      String value = x;
-      if (WXAnimationBean.Style.LEFT.equals(x)) {
-        value = ZERO;
-      } else if (WXAnimationBean.Style.RIGHT.equals(x)) {
-        value = FULL;
-      } else if (WXAnimationBean.Style.CENTER.equals(x)) {
-        value = HALF;
-      }
-      return parsePercentOrPx(value, width,viewportW);
-    }
-
-    private static float parsePivotY(String y, int height,int viewportW) {
-      String value = y;
-      if (WXAnimationBean.Style.TOP.equals(y)) {
-        value = ZERO;
-      } else if (WXAnimationBean.Style.BOTTOM.equals(y)) {
-        value = FULL;
-      } else if (WXAnimationBean.Style.CENTER.equals(y)) {
-        value = HALF;
-      }
-      return parsePercentOrPx(value, height,viewportW);
-    }
-
-    private static float parsePercentOrPx(String raw, int unit,int viewportW) {
-      final int precision = 1;
-      int suffix;
-      if ((suffix = raw.lastIndexOf(WXUtils.PERCENT)) != -1) {
-        return parsePercent(raw.substring(0, suffix), unit, precision);
-      } else if ((suffix = raw.lastIndexOf(PX)) != -1) {
-        return WXViewUtils.getRealPxByWidth(WXUtils.fastGetFloat(raw.substring(0, suffix), precision),viewportW);
-      }
-      return WXViewUtils.getRealPxByWidth(WXUtils.fastGetFloat(raw, precision),viewportW);
-    }
-
-    private static float parsePercent(String percent, int unit, int precision) {
-      return WXUtils.fastGetFloat(percent, precision) / 100 * unit;
-    }
-
-    private void resetToDefaultIfAbsent() {
-      for (Entry<Property<View, Float>, Float> entry : defaultMap.entrySet()) {
-        if (!transformMap.containsKey(entry.getKey())) {
-          transformMap.put(entry.getKey(), entry.getValue());
-        }
-      }
-    }
-
-    public @Nullable Pair<Float, Float> getPivot() {
-      return pivot;
-    }
-
-    public void init(@Nullable String transformOrigin,@Nullable String rawTransform,
-                     final int width, final int height,int viewportW, WXSDKInstance instance){
-      pivot = parsePivot(transformOrigin,width,height,viewportW);
-      transformMap.putAll(TransformParser.parseTransForm(instance.getInstanceId(), rawTransform, width,height,viewportW));
-      resetToDefaultIfAbsent();
-      if (transformMap.containsKey(CameraDistanceProperty.getInstance())) {
-        cameraDistance = transformMap.remove(CameraDistanceProperty.getInstance());
-      }
-      initHolders();
-    }
-
-    /**
-     * Use this method to init if you already have a list of Property
-     * The key is something like {@link View#TRANSLATION_X} and the value is a {@link Pair},
-     * of which the first is beginning value and the second is ending value.
-     * @param styles a list of Property
-     */
-    public void init(@NonNull Map<Property<View, Float>, Pair<Float, Float>> styles){
-      for(Entry<Property<View, Float>, Pair<Float, Float>> entry:styles.entrySet()){
-        holders.add(PropertyValuesHolder.ofFloat(entry.getKey(), entry.getValue().first, entry.getValue().second));
-      }
-    }
-
-    private void initHolders(){
-      for (Map.Entry<Property<View, Float>, Float> entry : transformMap.entrySet()) {
-        holders.add(PropertyValuesHolder.ofFloat(entry.getKey(), entry.getValue()));
-      }
-      if (!TextUtils.isEmpty(opacity)) {
-        holders.add(PropertyValuesHolder.ofFloat(View.ALPHA, WXUtils.fastGetFloat(opacity, 3)));
-      }
-    }
-
-    public List<PropertyValuesHolder> getHolders(){
-      return holders;
-    }
-
-    public float getCameraDistance(){
-      return cameraDistance;
-    }
-  }
-}
-
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/animation/WXAnimationModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/animation/WXAnimationModule.java
deleted file mode 100644
index a614ba3..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/animation/WXAnimationModule.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.animation;
-
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.ui.action.GraphicActionAnimation;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.list.template.TemplateDom;
-
-public class WXAnimationModule extends WXModule {
-
-  @JSMethod
-  public void transition(@Nullable String ref, @Nullable String animation, @Nullable String callBack) {
-    if (!TextUtils.isEmpty(ref) && !TextUtils.isEmpty(animation) && mWXSDKInstance != null) {
-      //Due to animation module rely on the result of the css-layout and the batch mechanism of
-      //css-layout, the animation.transition must be delayed the batch time.
-      GraphicActionAnimation action = new GraphicActionAnimation(mWXSDKInstance, ref, animation, callBack);
-      WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-    }
-  }
-
-
- 
-
-  //add by moxun on 12/26/2016
-  public static class AnimationHolder {
-
-    private WXAnimationBean wxAnimationBean;
-    private String callback;
-
-    public void execute(WXSDKInstance instance, WXComponent component) {
-      if (null != instance && null != component) {
-        GraphicActionAnimation action = new GraphicActionAnimation(instance, component.getRef(), wxAnimationBean, callback);
-        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
-      }
-    }
-
-    public AnimationHolder(WXAnimationBean wxAnimationBean, String callback) {
-      this.wxAnimationBean = wxAnimationBean;
-      this.callback = callback;
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/animation/WidthProperty.java b/android/sdk/src/main/java/com/taobao/weex/ui/animation/WidthProperty.java
deleted file mode 100644
index ca4288f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/animation/WidthProperty.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.animation;
-
-
-import android.view.ViewGroup.LayoutParams;
-
-public class WidthProperty extends LayoutParamsProperty {
-
-  @Override
-  protected Integer getProperty(LayoutParams layoutParams) {
-    return layoutParams.width;
-  }
-
-  @Override
-  protected void setProperty(LayoutParams layoutParams, Integer expected) {
-    layoutParams.width = expected;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/AbstractEditComponent.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/AbstractEditComponent.java
deleted file mode 100644
index 351ac08..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/AbstractEditComponent.java
+++ /dev/null
@@ -1,1066 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.app.Activity;
-import android.content.Context;
-import android.graphics.Rect;
-import android.support.annotation.NonNull;
-import android.text.Editable;
-import android.text.InputFilter;
-import android.text.InputType;
-import android.text.TextPaint;
-import android.text.TextUtils;
-import android.text.TextWatcher;
-import android.text.method.DigitsKeyListener;
-import android.text.method.PasswordTransformationMethod;
-import android.util.Log;
-import android.util.TypedValue;
-import android.view.Gravity;
-import android.view.KeyEvent;
-import android.view.View;
-import android.view.inputmethod.EditorInfo;
-import android.view.inputmethod.InputMethodManager;
-import android.widget.EditText;
-import android.widget.TextView;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.dom.CSSConstants;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.layout.ContentBoxMeasurement;
-import com.taobao.weex.layout.MeasureMode;
-import com.taobao.weex.layout.MeasureSize;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.helper.SoftKeyboardDetector;
-import com.taobao.weex.ui.component.helper.WXTimeInputHelper;
-import com.taobao.weex.ui.view.WXEditText;
-import com.taobao.weex.utils.TypefaceUtil;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.regex.Pattern;
-import java.util.regex.PatternSyntaxException;
-
-import static com.taobao.weex.dom.WXStyle.UNSET;
-
-/**
- * Created by sospartan on 7/11/16.
- */
-public abstract class AbstractEditComponent extends WXComponent<WXEditText> {
-
-  private final InputMethodManager mInputMethodManager;
-  private String mBeforeText = "";
-  private boolean mAutoFocus;
-  private String mType = "text";
-  private String mMax = null;
-  private String mMin = null;
-  private String mLastValue = "";
-  private int mEditorAction = EditorInfo.IME_ACTION_DONE;
-  private String mReturnKeyType = null;
-  private List<TextView.OnEditorActionListener> mEditorActionListeners;
-  private boolean mListeningKeyboard = false;
-  private SoftKeyboardDetector.Unregister mUnregister;
-  private boolean mIgnoreNextOnInputEvent = false;
-  private boolean mKeepSelectionIndex = false;
-  private TextFormatter mFormatter = null;
-  private List<TextWatcher> mTextChangedListeners;
-  private TextWatcher mTextChangedEventDispatcher;
-  private int mFormatRepeatCount = 0;
-  private static final int MAX_TEXT_FORMAT_REPEAT = 3;
-
-  private TextPaint mPaint = new TextPaint();
-  private int mLineHeight = UNSET;
-
-  public AbstractEditComponent(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-    super(instance, parent, isLazy, basicComponentData);
-    mInputMethodManager = (InputMethodManager) getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
-    setContentBoxMeasurement(new ContentBoxMeasurement() {
-      /** uiThread = false **/
-      @Override
-      public void measureInternal(float width, float height, int widthMeasureMode, int heightMeasureMode) {
-        if (CSSConstants.isUndefined(width) || widthMeasureMode == MeasureMode.UNSPECIFIED) {
-          width = 0;
-        }
-        mMeasureWidth = width;
-        mMeasureHeight = getMeasureHeight();
-      }
-
-      /** uiThread = false **/
-      @Override
-      public void layoutBefore() {
-        updateStyleAndAttrs();
-      }
-
-      /** uiThread = false **/
-      @Override
-      public void layoutAfter(float computedWidth, float computedHeight) {
-
-      }
-    });
-  }
-
-  @Override
-  protected void layoutDirectionDidChanged(boolean isRTL) {
-    String alignStr = (String) getStyles().get(Constants.Name.TEXT_ALIGN);
-    int textAlign = getTextAlign(alignStr);
-    if (textAlign <= 0) {
-      textAlign = Gravity.START;
-    }
-    if (getHostView() instanceof WXEditText) {
-      getHostView().setGravity(textAlign | getVerticalGravity());
-    }
-  }
-
-  protected final float getMeasuredLineHeight() {
-    return mLineHeight != UNSET && mLineHeight > 0 ? mLineHeight : mPaint.getFontMetrics(null);
-  }
-
-  protected float getMeasureHeight() {
-    return getMeasuredLineHeight();
-  }
-
-  protected void updateStyleAndAttrs() {
-    if (getStyles().size() > 0) {
-      int fontSize = UNSET, fontStyle = UNSET, fontWeight = UNSET;
-      String fontFamily = null;
-      if (getStyles().containsKey(Constants.Name.FONT_SIZE)) {
-        fontSize = WXStyle.getFontSize(getStyles(),getViewPortWidth());
-      }
-
-      if (getStyles().containsKey(Constants.Name.FONT_FAMILY)) {
-        fontFamily = WXStyle.getFontFamily(getStyles());
-      }
-
-      if (getStyles().containsKey(Constants.Name.FONT_STYLE)) {
-        fontStyle = WXStyle.getFontStyle(getStyles());
-      }
-
-      if (getStyles().containsKey(Constants.Name.FONT_WEIGHT)) {
-        fontWeight = WXStyle.getFontWeight(getStyles());
-      }
-
-      int lineHeight = WXStyle.getLineHeight(getStyles(),getViewPortWidth());
-      if (lineHeight != UNSET)
-        mLineHeight = lineHeight;
-
-      if (fontSize != UNSET)
-        mPaint.setTextSize(fontSize);
-
-      if (fontFamily != null) {
-        TypefaceUtil.applyFontStyle(mPaint, fontStyle, fontWeight, fontFamily);
-      }
-    }
-  }
-
-  @Override
-  protected WXEditText initComponentHostView(@NonNull Context context) {
-    final WXEditText inputView = new WXEditText(context);
-    appleStyleAfterCreated(inputView);
-    return inputView;
-  }
-
-  @Override
-  protected void onHostViewInitialized(WXEditText host) {
-    super.onHostViewInitialized(host);
-    addFocusChangeListener(new OnFocusChangeListener() {
-      @Override
-      public void onFocusChange(boolean hasFocus) {
-        if (!hasFocus) {
-          decideSoftKeyboard();
-        }
-        setPseudoClassStatus(Constants.PSEUDO.FOCUS,hasFocus);
-      }
-    });
-
-    addKeyboardListener(host);
-  }
-
-  @Override
-  protected boolean isConsumeTouch() {
-    //EditText always consume touch event except disabled.
-    return !isDisabled();
-  }
-
-  private OnClickListener mOnClickListener = new OnClickListener() {
-    @Override
-    public void onHostViewClick() {
-      switch (mType) {
-        case Constants.Value.DATE:
-          hideSoftKeyboard();
-          if (getParent() != null) {
-            getParent().interceptFocus();
-          }
-          WXTimeInputHelper.pickDate(mMax, mMin, AbstractEditComponent.this);
-          break;
-        case Constants.Value.TIME:
-          hideSoftKeyboard();
-          if (getParent() != null) {
-            getParent().interceptFocus();
-          }
-          WXTimeInputHelper.pickTime(AbstractEditComponent.this);
-          break;
-      }
-    }
-  };
-
-  private void applyOnClickListener() {
-    addClickListener(mOnClickListener);
-  }
-
-
-  protected int getVerticalGravity(){
-    return Gravity.CENTER_VERTICAL;
-  }
-
-  /**
-   * Process view after created.
-   *
-   * @param editText
-   */
-  protected void appleStyleAfterCreated(final WXEditText editText) {
-    String alignStr = (String) getStyles().get(Constants.Name.TEXT_ALIGN);
-    int textAlign = getTextAlign(alignStr);
-    if (textAlign <= 0) {
-      textAlign = Gravity.START;
-    }
-    editText.setGravity(textAlign | getVerticalGravity());
-    final int colorInt = WXResourceUtils.getColor("#999999");
-    if (colorInt != Integer.MIN_VALUE) {
-      editText.setHintTextColor(colorInt);
-    }
-
-    mTextChangedEventDispatcher = new TextWatcher() {
-      @Override
-      public void beforeTextChanged(CharSequence s, int start, int count, int after) {
-        if (mTextChangedListeners != null) {
-          for (TextWatcher watcher : mTextChangedListeners) {
-            watcher.beforeTextChanged(s, start, count, after);
-          }
-        }
-      }
-
-      @Override
-      public void onTextChanged(CharSequence s, int start, int before, int count) {
-        if (mFormatter != null) {
-          String raw = mFormatter.recover(s.toString());
-          String result = mFormatter.format(raw);
-          // prevent infinite loop caused by bad format and recover regexp
-          if (!result.equals(s.toString()) && mFormatRepeatCount < MAX_TEXT_FORMAT_REPEAT) {
-            mFormatRepeatCount = mFormatRepeatCount + 1;
-            int index = editText.getSelectionStart();
-            int cursorIndex = mFormatter.format(mFormatter.recover(s.subSequence(0, index).toString())).length();
-            editText.setText(result);
-            editText.setSelection(cursorIndex);
-            return;
-          }
-
-          mFormatRepeatCount = 0;
-        }
-
-        if (mTextChangedListeners != null) {
-          for (TextWatcher watcher : mTextChangedListeners) {
-            watcher.onTextChanged(s, start, before, count);
-          }
-        }
-      }
-
-      @Override
-      public void afterTextChanged(Editable s) {
-        if (mTextChangedListeners != null) {
-          for (TextWatcher watcher : mTextChangedListeners) {
-            watcher.afterTextChanged(s);
-          }
-        }
-      }
-    };
-    editText.addTextChangedListener(mTextChangedEventDispatcher);
-
-    editText.setTextSize(TypedValue.COMPLEX_UNIT_PX, WXStyle.getFontSize(getStyles(), getInstance().getInstanceViewPortWidth()));
-  }
-
-
-  @Override
-  public void addEvent(final String type) {
-    super.addEvent(type);
-    if (getHostView() == null || TextUtils.isEmpty(type)) {
-      return;
-    }
-    final TextView text = getHostView();
-
-    if (type.equals(Constants.Event.CHANGE)) {
-      addFocusChangeListener(new OnFocusChangeListener() {
-        @Override
-        public void onFocusChange(boolean hasFocus) {
-          if (hasFocus) {
-            mLastValue = text.getText().toString();
-          } else {
-            CharSequence newValue = text.getText();
-            newValue = newValue == null ? "" : newValue;
-            if (!newValue.toString().equals(mLastValue)) {
-              fireEvent(Constants.Event.CHANGE, newValue.toString());
-              mLastValue = text.getText().toString();
-            }
-          }
-        }
-      });
-
-      addEditorActionListener(new TextView.OnEditorActionListener() {
-        @Override
-        public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
-          if (actionId == mEditorAction) {
-            CharSequence newValue = text.getText();
-            newValue = newValue == null ? "" : newValue;
-            if (!newValue.toString().equals(mLastValue)) {
-              fireEvent(Constants.Event.CHANGE, newValue.toString());
-              mLastValue = text.getText().toString();
-            }
-            if (getParent() != null) {
-              getParent().interceptFocus();
-            }
-            hideSoftKeyboard();
-            return true;
-          }
-          return false;
-        }
-      });
-    } else if (type.equals(Constants.Event.INPUT)) {
-      addTextChangedListener(new TextWatcher() {
-        @Override
-        public void beforeTextChanged(CharSequence s, int start, int count, int after) {
-
-        }
-
-        @Override
-        public void onTextChanged(CharSequence s, int start, int before, int count) {
-          if (mIgnoreNextOnInputEvent) {
-            mIgnoreNextOnInputEvent = false;
-            mBeforeText = s.toString();
-            return;
-          }
-
-          if (mBeforeText.equals(s.toString())) {
-            return;
-          }
-
-          mBeforeText = s.toString();
-
-          fireEvent(Constants.Event.INPUT, s.toString());
-        }
-
-        @Override
-        public void afterTextChanged(Editable s) {
-
-        }
-      });
-    }
-
-    if (Constants.Event.RETURN.equals(type)) {
-      addEditorActionListener(new TextView.OnEditorActionListener() {
-        @Override
-        public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
-          if (actionId == mEditorAction) {
-            Map<String, Object> ret = new HashMap<>(2);
-            ret.put("returnKeyType", mReturnKeyType);
-            ret.put("value", v.getText().toString());
-            fireEvent(Constants.Event.RETURN, ret);
-            return true;
-          }
-          return false;
-        }
-      });
-    }
-
-    if (Constants.Event.KEYBOARD.equals(type)) {
-      mListeningKeyboard = true;
-    }
-  }
-
-  private void fireEvent(String event, String value) {
-    if (event != null) {
-      Map<String, Object> params = new HashMap<>(2);
-      params.put("value", value);
-      params.put("timeStamp", System.currentTimeMillis());
-
-      Map<String, Object> domChanges = new HashMap<>();
-      Map<String, Object> attrsChanges = new HashMap<>();
-      attrsChanges.put("value", value);
-      domChanges.put("attrs", attrsChanges);
-
-      WXSDKManager.getInstance().fireEvent(getInstanceId(), getRef(), event, params, domChanges);
-    }
-  }
-
-  public void performOnChange(String value) {
-    if (getEvents() != null) {
-      String event = getEvents().contains(Constants.Event.CHANGE) ? Constants.Event.CHANGE : null;
-      fireEvent(event, value);
-    }
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.DISABLED:
-        Boolean disabled = WXUtils.getBoolean(param, null);
-        if (disabled != null && mHost != null) {
-          if (disabled) {
-            mHost.setFocusable(false);
-            mHost.setFocusableInTouchMode(false);
-          } else {
-            mHost.setFocusableInTouchMode(true);
-            mHost.setFocusable(true);
-          }
-        }
-        return true;
-      case Constants.Name.PLACEHOLDER:
-        String placeholder = WXUtils.getString(param, null);
-        if (placeholder != null)
-          setPlaceholder(placeholder);
-        return true;
-      case Constants.Name.PLACEHOLDER_COLOR:
-        String placeholder_color = WXUtils.getString(param, null);
-        if (placeholder_color != null)
-          setPlaceholderColor(placeholder_color);
-        return true;
-      case Constants.Name.TYPE:
-        String input_type = WXUtils.getString(param, null);
-        if (input_type != null)
-          setType(input_type);
-        return true;
-      case Constants.Name.AUTOFOCUS:
-        Boolean result = WXUtils.getBoolean(param, null);
-        if (result != null)
-          setAutofocus(result);
-        return true;
-      case Constants.Name.COLOR:
-        String color = WXUtils.getString(param, null);
-        if (color != null)
-          setColor(color);
-        return true;
-      case Constants.Name.FONT_SIZE:
-        String fontsize = WXUtils.getString(param, null);
-        if (fontsize != null)
-          setFontSize(fontsize);
-        return true;
-      case Constants.Name.TEXT_ALIGN:
-        String text_align = WXUtils.getString(param, null);
-        if (text_align != null)
-          setTextAlign(text_align);
-        return true;
-      case Constants.Name.SINGLELINE:
-        Boolean singLineResult = WXUtils.getBoolean(param, null);
-        if (singLineResult != null)
-          setSingleLine(singLineResult);
-        return true;
-      case Constants.Name.LINES:
-        Integer lines = WXUtils.getInteger(param, null);
-        if (lines != null)
-          setLines(lines);
-        return true;
-      case Constants.Name.MAX_LENGTH:
-        Integer maxlength = WXUtils.getInteger(param, null);
-        if (maxlength != null)
-          setMaxLength(maxlength);
-        return true;
-      case Constants.Name.MAXLENGTH:
-        Integer maxLength = WXUtils.getInteger(param, null);
-        if (maxLength != null)
-          setMaxLength(maxLength);
-        return true;
-      case Constants.Name.MAX:
-        setMax(String.valueOf(param));
-        return true;
-      case Constants.Name.MIN:
-        setMin(String.valueOf(param));
-        return true;
-      case Constants.Name.RETURN_KEY_TYPE:
-        setReturnKeyType(String.valueOf(param));
-        return true;
-      case Constants.Name.KEEP_SELECTION_INDEX:
-        boolean keepIndex = WXUtils.getBoolean(param, false);
-        mKeepSelectionIndex = keepIndex;
-        return true;
-      case Constants.Name.ALLOW_COPY_PASTE:
-        boolean allowCopyPaste = WXUtils.getBoolean(param, true);
-        if (getHostView() != null) {
-          getHostView().setAllowCopyPaste(allowCopyPaste);
-        }
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @WXComponentProp(name = Constants.Name.RETURN_KEY_TYPE)
-  public void setReturnKeyType(String type) {
-    if (getHostView() == null) {
-      return;
-    }
-    mReturnKeyType = type;
-    switch (type) {
-      case ReturnTypes.DEFAULT:
-        mEditorAction = EditorInfo.IME_ACTION_UNSPECIFIED;
-        break;
-      case ReturnTypes.GO:
-        mEditorAction = EditorInfo.IME_ACTION_GO;
-        break;
-      case ReturnTypes.NEXT:
-        mEditorAction = EditorInfo.IME_ACTION_NEXT;
-        break;
-      case ReturnTypes.SEARCH:
-        mEditorAction = EditorInfo.IME_ACTION_SEARCH;
-        break;
-      case ReturnTypes.SEND:
-        mEditorAction = EditorInfo.IME_ACTION_SEND;
-        break;
-      case ReturnTypes.DONE:
-        mEditorAction = EditorInfo.IME_ACTION_DONE;
-        break;
-      default:
-        break;
-    }
-
-    //remove focus and hide keyboard first, the ImeOptions will take effect when show keyboard next time
-    blur();
-    getHostView().setImeOptions(mEditorAction);
-  }
-
-  @WXComponentProp(name = Constants.Name.PLACEHOLDER)
-  public void setPlaceholder(String placeholder) {
-    if (placeholder == null || getHostView() == null) {
-      return;
-    }
-    ((WXEditText) getHostView()).setHint(placeholder);
-  }
-
-  @WXComponentProp(name = Constants.Name.PLACEHOLDER_COLOR)
-  public void setPlaceholderColor(String color) {
-    if (getHostView() != null && !TextUtils.isEmpty(color)) {
-      int colorInt = WXResourceUtils.getColor(color);
-      if (colorInt != Integer.MIN_VALUE) {
-        ((WXEditText) getHostView()).setHintTextColor(colorInt);
-      }
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.TYPE)
-  public void setType(String type) {
-    Log.e("weex", "setType=" + type);
-    if (type == null || getHostView() == null) {
-      return;
-    }
-    mType = type;
-    ((EditText) getHostView()).setInputType(getInputType(mType));
-    switch (mType) {
-      case Constants.Value.DATE:
-      case Constants.Value.TIME:
-        applyOnClickListener();
-        break;
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.AUTOFOCUS)
-  public void setAutofocus(boolean autofocus) {
-    if (getHostView() == null) {
-      return;
-    }
-    mAutoFocus = autofocus;
-    EditText inputView = getHostView();
-    if (mAutoFocus) {
-      inputView.setFocusable(true);
-      inputView.requestFocus();
-      inputView.setFocusableInTouchMode(true);
-      showSoftKeyboard();
-    } else {
-      hideSoftKeyboard();
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.VALUE)
-  public void setValue(String value) {
-    WXEditText view;
-    if ((view = getHostView()) == null) {
-      return;
-    }
-    if (TextUtils.equals(view.getText(), value)) {
-      return;
-    }
-
-    mIgnoreNextOnInputEvent = true;
-    int oldIndex = view.getSelectionStart();
-    view.setText(value);
-    int index = mKeepSelectionIndex ? oldIndex : value.length();
-    view.setSelection(value == null ? 0 : index);
-  }
-
-  @WXComponentProp(name = Constants.Name.COLOR)
-  public void setColor(String color) {
-    if (getHostView() != null && !TextUtils.isEmpty(color)) {
-      int colorInt = WXResourceUtils.getColor(color);
-      if (colorInt != Integer.MIN_VALUE) {
-        getHostView().setTextColor(colorInt);
-      }
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.FONT_SIZE)
-  public void setFontSize(String fontSize) {
-    if (getHostView() != null && fontSize != null ) {
-      Map<String, Object> map = new HashMap<>(1);
-      map.put(Constants.Name.FONT_SIZE, fontSize);
-      getHostView().setTextSize(TypedValue.COMPLEX_UNIT_PX, WXStyle.getFontSize(map, getInstance().getInstanceViewPortWidth()));
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.TEXT_ALIGN)
-  public void setTextAlign(String textAlign) {
-    int align = getTextAlign(textAlign);
-    if (align > 0) {
-      getHostView().setGravity(align | getVerticalGravity());
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.SINGLELINE)
-  public void setSingleLine(boolean singleLine) {
-    if (getHostView() == null) {
-      return;
-    }
-    getHostView().setSingleLine(singleLine);
-  }
-
-  @WXComponentProp(name = Constants.Name.LINES)
-  public void setLines(int lines) {
-    if (getHostView() == null) {
-      return;
-    }
-    getHostView().setLines(lines);
-  }
-
-  /**
-   * Compatible with both 'max-length' and 'maxlength'
-   * @param maxLength
-   */
-  @WXComponentProp(name = Constants.Name.MAX_LENGTH)
-  public void setMaxLength(int maxLength) {
-    if (getHostView() == null) {
-      return;
-    }
-    getHostView().setFilters(new InputFilter[]{new InputFilter.LengthFilter(maxLength)});
-  }
-
-  /**
-   * Compatible with both 'max-length' and 'maxlength'
-   * @param maxLength
-   */
-  @WXComponentProp(name = Constants.Name.MAXLENGTH)
-  @Deprecated
-  public void setMaxlength(int maxLength) {
-    setMaxLength(maxLength);
-  }
-
-  private int getInputType(String type) {
-    int inputType;
-    switch (type) {
-      case Constants.Value.TEXT:
-        inputType = InputType.TYPE_CLASS_TEXT;
-        break;
-      case Constants.Value.DATE:
-        inputType = InputType.TYPE_NULL;
-        getHostView().setFocusable(false);
-        break;
-      case Constants.Value.DATETIME:
-        inputType = InputType.TYPE_CLASS_DATETIME;
-        break;
-      case Constants.Value.EMAIL:
-        inputType = InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_EMAIL_ADDRESS;
-        break;
-      case Constants.Value.PASSWORD:
-        inputType = InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_PASSWORD;
-        if(getHostView() != null){
-            getHostView().setTransformationMethod(PasswordTransformationMethod.getInstance());
-        }
-        break;
-      case Constants.Value.TEL:
-        inputType = InputType.TYPE_CLASS_PHONE;
-        break;
-      case Constants.Value.TIME:
-        inputType = InputType.TYPE_NULL;
-        if(getHostView() != null){
-            getHostView().setFocusable(false);
-        }
-        break;
-      case Constants.Value.URL:
-        inputType = InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_URI;
-        break;
-      case Constants.Value.NUMBER:
-        inputType = InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_FLAG_DECIMAL;
-        break;
-      default:
-        inputType = InputType.TYPE_CLASS_TEXT;
-    }
-    return inputType;
-  }
-
-  @WXComponentProp(name = Constants.Name.MAX)
-  public void setMax(String max) {
-    mMax = max;
-  }
-
-  @WXComponentProp(name = Constants.Name.MIN)
-  public void setMin(String min) {
-    mMin = min;
-  }
-
-  private boolean showSoftKeyboard() {
-    if (getHostView() == null) {
-      return false;
-    } else {
-      getHostView().postDelayed(WXThread.secure(new Runnable() {
-        @Override
-        public void run() {
-          if (getInstance() != null && getInstance().getApmForInstance() != null){
-            getInstance().getApmForInstance().forceStopRecordInteraction = true;
-          }
-          mInputMethodManager.showSoftInput(getHostView(), InputMethodManager.SHOW_IMPLICIT);
-        }
-      }), 100);
-    }
-    return true;
-  }
-
-  private void hideSoftKeyboard() {
-    if (getHostView() != null) {
-      getHostView().postDelayed(WXThread.secure(new Runnable() {
-        @Override
-        public void run() {
-          mInputMethodManager.hideSoftInputFromWindow(getHostView().getWindowToken(), 0);
-        }
-      }), 16);
-    }
-  }
-
-  private int getTextAlign(String textAlign) {
-    boolean isRTL = isLayoutRTL();
-    int align = isRTL ? Gravity.END : Gravity.START;
-    if (TextUtils.isEmpty(textAlign)) {
-      return align;
-    }
-
-    if (textAlign.equals(Constants.Value.LEFT)) {
-      align = Gravity.START;
-    } else if (textAlign.equals(Constants.Value.CENTER)) {
-      align = Gravity.CENTER;
-    } else if (textAlign.equals(Constants.Value.RIGHT)) {
-      align = Gravity.END;
-    }
-    return align;
-  }
-
-  @JSMethod
-  public void blur() {
-    WXEditText host = getHostView();
-    if (host != null && host.hasFocus()) {
-      if (getParent() != null) {
-        getParent().interceptFocus();
-      }
-      host.clearFocus();
-      hideSoftKeyboard();
-    }
-  }
-
-  @JSMethod
-  public void focus() {
-    WXEditText host = getHostView();
-    if (host != null && !host.hasFocus()) {
-      if (getParent() != null) {
-        getParent().ignoreFocus();
-      }
-      host.requestFocus();
-      host.setFocusable(true);
-      host.setFocusableInTouchMode(true);
-      showSoftKeyboard();
-    }
-  }
-
-  @Override
-  protected Object convertEmptyProperty(String propName, Object originalValue) {
-    switch (propName) {
-      case Constants.Name.FONT_SIZE:
-        return WXText.sDEFAULT_SIZE;
-      case Constants.Name.COLOR:
-        return "black";
-    }
-    return super.convertEmptyProperty(propName, originalValue);
-  }
-
-  private void decideSoftKeyboard() {
-    View hostView;
-    if ((hostView = getHostView()) != null) {
-      final Context context = getContext();
-      if (context != null && context instanceof Activity) {
-        hostView.postDelayed(WXThread.secure(new Runnable() {
-          @Override
-          public void run() {
-            View currentFocus = ((Activity) context).getCurrentFocus();
-            if (!(currentFocus instanceof EditText)) {
-              mInputMethodManager.hideSoftInputFromWindow(getHostView().getWindowToken(), 0);
-            }
-          }
-        }), 16);
-      }
-    }
-  }
-
-  @JSMethod
-  public void setSelectionRange(int selectionStart, int selectionEnd) {
-    EditText hostView;
-    if ((hostView = getHostView()) != null) {
-      int length = getHostView().length();
-      if (selectionStart > length || selectionEnd > length) {
-        return;
-      }
-      focus();
-      hostView.setSelection(selectionStart, selectionEnd);
-    }
-  }
-
-  @JSMethod
-  public void getSelectionRange(String callbackId) {
-    EditText hostView;
-    Map<String, Object> result = new HashMap<>(2);
-    if ((hostView = getHostView()) != null) {
-      int start = hostView.getSelectionStart();
-      int end = hostView.getSelectionEnd();
-
-      if (!hostView.hasFocus()) {
-        //The default behavior, same as iOS and web
-        start = 0;
-        end = 0;
-      }
-
-      result.put(Constants.Name.SELECTION_START, start);
-      result.put(Constants.Name.SELECTION_END, end);
-    }
-    WXBridgeManager.getInstance().callback(getInstanceId(), callbackId, result, false);
-  }
-
-  @JSMethod
-  public void setTextFormatter(JSONObject params) {
-    try {
-      String formatRule = params.getString("formatRule");
-      String formatReplace = params.getString("formatReplace");
-      String recoverRule = params.getString("recoverRule");
-      String recoverReplace = params.getString("recoverReplace");
-
-      PatternWrapper format = parseToPattern(formatRule, formatReplace);
-      PatternWrapper recover = parseToPattern(recoverRule, recoverReplace);
-
-      if (format != null && recover != null) {
-        mFormatter = new TextFormatter(format, recover);
-      }
-    } catch (Throwable t) {
-      t.printStackTrace();
-    }
-  }
-
-  protected final void addEditorActionListener(TextView.OnEditorActionListener listener) {
-    TextView view;
-    if (listener != null && (view = getHostView()) != null) {
-      if (mEditorActionListeners == null) {
-        mEditorActionListeners = new ArrayList<>();
-        view.setOnEditorActionListener(new TextView.OnEditorActionListener() {
-          private boolean handled = true;
-
-          @Override
-          public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
-            for (TextView.OnEditorActionListener l : mEditorActionListeners) {
-              if (l != null) {
-                handled = handled & l.onEditorAction(v, actionId, event);
-              }
-            }
-            return handled;
-          }
-        });
-      }
-      mEditorActionListeners.add(listener);
-    }
-  }
-
-  public final void addTextChangedListener(TextWatcher watcher) {
-    if (mTextChangedListeners == null) {
-      mTextChangedListeners = new ArrayList<>();
-    }
-    mTextChangedListeners.add(watcher);
-  }
-
-  private void addKeyboardListener(final WXEditText host) {
-    if (host == null) {
-      return;
-    }
-    final Context context = host.getContext();
-    if (context != null && context instanceof Activity) {
-      SoftKeyboardDetector.registerKeyboardEventListener((Activity) context, new SoftKeyboardDetector.OnKeyboardEventListener() {
-        @Override
-        public void onKeyboardEvent(boolean isShown) {
-          if (mListeningKeyboard) {
-            Map<String, Object> event = new HashMap<>(1);
-            event.put("isShow", isShown);
-            if (isShown) {
-              Rect r = new Rect();
-              ((Activity) context).getWindow().getDecorView().getWindowVisibleDisplayFrame(r);
-              float keyboardSize = WXViewUtils.getWebPxByWidth(WXViewUtils.getScreenHeight(context) - (r.bottom - r.top),
-                      getInstance().getInstanceViewPortWidth());
-              event.put("keyboardSize", keyboardSize);
-            }
-            fireEvent(Constants.Event.KEYBOARD, event);
-          }
-          if (!isShown) {
-            blur();
-          }
-        }
-      });
-    }
-  }
-
-  @Override
-  public void destroy() {
-    super.destroy();
-    if (mUnregister != null) {
-      try {
-        mUnregister.execute();
-        mUnregister = null;
-      } catch (Throwable throwable) {
-        WXLogUtils.w("Unregister throw ", throwable);
-      }
-    }
-  }
-
-  private PatternWrapper parseToPattern(String jsPattern, String replace) {
-    if (jsPattern == null || replace == null) {
-      return null;
-    }
-
-    String checker = "/[\\S]+/[i]?[m]?[g]?";
-    if (!Pattern.compile(checker).matcher(jsPattern).matches()) {
-      WXLogUtils.w("WXInput", "Illegal js pattern syntax: " + jsPattern);
-      return null;
-    }
-
-    int flags = 0;
-    boolean global = false;
-    String flagsStr = jsPattern.substring(jsPattern.lastIndexOf("/") + 1);
-    String regExp = jsPattern.substring(jsPattern.indexOf("/") + 1, jsPattern.lastIndexOf("/"));
-
-    if (flagsStr.contains("i")) {
-      flags |= Pattern.CASE_INSENSITIVE;
-    }
-
-    if (flagsStr.contains("m")) {
-      flags |= Pattern.DOTALL;
-    }
-
-    if (flagsStr.contains("g")) {
-      global = true;
-    }
-
-    Pattern pattern = null;
-    try {
-      pattern = Pattern.compile(regExp, flags);
-    } catch (PatternSyntaxException e) {
-      WXLogUtils.w("WXInput", "Pattern syntax error: " + regExp);
-    }
-    if (pattern == null) {
-      return null;
-    }
-
-    PatternWrapper wrapper = new PatternWrapper();
-    wrapper.global = global;
-    wrapper.matcher = pattern;
-    wrapper.replace = replace;
-    return wrapper;
-  }
-
-  private interface ReturnTypes {
-    String DEFAULT = "default";
-    String GO = "go";
-    String NEXT = "next";
-    String SEARCH = "search";
-    String SEND = "send";
-    String DONE = "done";
-  }
-
-  private static class PatternWrapper {
-    private boolean global = false;
-    private Pattern matcher;
-    private String replace;
-  }
-
-  private static class TextFormatter {
-    private PatternWrapper format;
-    private PatternWrapper recover;
-
-    private TextFormatter(PatternWrapper format, PatternWrapper recover) {
-      this.format = format;
-      this.recover = recover;
-    }
-
-    private String format(String src) {
-      try {
-        if (format != null) {
-          if (format.global) {
-            return format.matcher.matcher(src).replaceAll(format.replace);
-          } else {
-            return format.matcher.matcher(src).replaceFirst(format.replace);
-          }
-        }
-      } catch (Throwable t) {
-        //maybe IndexOutOfBoundsException caused by illegal replace
-        WXLogUtils.w("WXInput", "[format] " + t.getMessage());
-      }
-      return src;
-    }
-
-    private String recover(String formatted) {
-      try {
-        if (recover != null) {
-          if (recover.global) {
-            return recover.matcher.matcher(formatted).replaceAll(recover.replace);
-          } else {
-            return recover.matcher.matcher(formatted).replaceFirst(recover.replace);
-          }
-        }
-      } catch (Throwable t) {
-        //same cause as format
-        WXLogUtils.w("WXInput", "[formatted] " + t.getMessage());
-      }
-      return formatted;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/AppearanceHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/AppearanceHelper.java
deleted file mode 100644
index 4481be8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/AppearanceHelper.java
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.graphics.Rect;
-import android.view.View;
-import com.taobao.weex.utils.WXLogUtils;
-
-
-/**
- * Created by sospartan on 8/19/16.
- */
-public class AppearanceHelper {
-
-  private final WXComponent mAwareChild;
-
-  private boolean mAppearStatus = false;
-  private boolean[] mWatchFlags = {false, false};
-
-  public static final int APPEAR = 0;
-  public static final int DISAPPEAR = 1;
-
-  public static final int RESULT_APPEAR = 1;
-  public static final int RESULT_DISAPPEAR = -1;
-  public static final int RESULT_NO_CHANGE = 0;
-
-  private Rect mVisibleRect = new Rect();
-
-  private int mCellPositionInScrollable;
-
-  /**
-   * @param awareChild child to notify when appearance changed.
-   */
-  public AppearanceHelper(WXComponent awareChild) {
-    this(awareChild, 0);
-  }
-
-  public AppearanceHelper(WXComponent awareChild, int cellPositionInScrollable) {
-    mAwareChild = awareChild;
-    mCellPositionInScrollable = cellPositionInScrollable;
-  }
-
-  public void setCellPosition(int pos){
-    mCellPositionInScrollable = pos;
-  }
-
-  public int getCellPositionINScollable() {
-    return mCellPositionInScrollable;
-  }
-
-  /**
-   * @param event  {@link #APPEAR} and {@link #DISAPPEAR}
-   * @param enable
-   */
-  public void setWatchEvent(int event, boolean enable) {
-    mWatchFlags[event] = enable;
-  }
-
-  /**
-   * @return
-   */
-  public boolean isWatch() {
-    return mWatchFlags[APPEAR] || mWatchFlags[DISAPPEAR];
-  }
-
-
-  public WXComponent getAwareChild() {
-    return mAwareChild;
-  }
-
-  public boolean isAppear() {
-    return mAppearStatus;
-  }
-
-  public int setAppearStatus(boolean newIsAppear) {
-    if (mAppearStatus != newIsAppear) {
-      mAppearStatus = newIsAppear;
-      return newIsAppear ? RESULT_APPEAR : RESULT_DISAPPEAR;
-    }
-
-    return RESULT_NO_CHANGE;
-  }
-
-  public boolean isViewVisible(boolean isList) {
-    View view = mAwareChild.getHostView();
-    if(isList){
-      if(view.getVisibility() == View.VISIBLE){
-        if(view.getMeasuredHeight()  == 0){
-          return  true;
-        }
-      }
-    }
-    return view != null && view.getLocalVisibleRect(mVisibleRect);
-
-  }
-
-  public boolean isViewVisible(View view) {
-    if(view.getVisibility() == View.VISIBLE){
-      if(view.getMeasuredHeight()  == 0){
-        return  true;
-      }
-    }
-    return view != null && view.getLocalVisibleRect(mVisibleRect);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/NestedContainer.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/NestedContainer.java
deleted file mode 100644
index 0451502..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/NestedContainer.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.view.ViewGroup;
-import com.taobao.weex.WXSDKInstance;
-
-/**
- * Created by sospartan on 8/24/16.
- */
-public interface NestedContainer {
-  void setOnNestEventListener(OnNestedInstanceEventListener listener);
-
-  ViewGroup getViewContainer();
-
-  void renderNewURL(String url);
-
-  void reload();
-
-  interface OnNestedInstanceEventListener {
-    void onException(NestedContainer comp, String errCode, String msg);
-
-    /**
-     *
-     * @param comp
-     * @param src
-     * @return true if keep load
-     */
-    boolean onPreCreate(NestedContainer comp, String src);
-
-    String transformUrl(String origin);
-
-    void onCreated(NestedContainer comp, WXSDKInstance nestedInstance);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/Scrollable.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/Scrollable.java
deleted file mode 100644
index 1094bd1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/Scrollable.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.view.ViewGroup;
-
-import java.util.Map;
-
-/**
- * Created by sospartan on 7/5/16.
- */
-public interface Scrollable {
-
-  void bindStickStyle(WXComponent component);
-
-  void unbindStickStyle(WXComponent component);
-
-  void bindAppearEvent(WXComponent component);
-
-  void bindDisappearEvent(WXComponent component);
-
-  void unbindAppearEvent(WXComponent component);
-
-  void unbindDisappearEvent(WXComponent component);
-
-  ViewGroup getView();
-
-  void scrollTo(WXComponent component, Map<String, Object> options);
-
-  String getRef();
-
-  int getScrollY();
-
-  int getScrollX();
-
-  /**
-   *
-   * @return {@link com.taobao.weex.common.Constants.Orientation#HORIZONTAL} or {@link com.taobao.weex.common.Constants.Orientation#VERTICAL}
-   */
-  int getOrientation();
-
-  boolean isScrollable();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/Textarea.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/Textarea.java
deleted file mode 100644
index acc9100..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/Textarea.java
+++ /dev/null
@@ -1,119 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.text.TextUtils;
-import android.view.Gravity;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXEditText;
-import com.taobao.weex.utils.WXUtils;
-
-/**
- * Created by sospartan on 7/11/16.
- */
-public class Textarea extends AbstractEditComponent {
-
-  public static final int DEFAULT_ROWS = 2;
-  private int mNumberOfLines = DEFAULT_ROWS;
-
-  public Textarea(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-    super(instance, parent, isLazy, basicComponentData);
-  }
-
-  @Override
-  protected void onHostViewInitialized(WXEditText host) {
-    host.setAllowDisableMovement(false);
-    super.onHostViewInitialized(host);
-  }
-
-  @Override
-  protected void appleStyleAfterCreated(WXEditText editText) {
-    super.appleStyleAfterCreated(editText);
-    String rowsStr = (String) getStyles().get(Constants.Name.ROWS);
-
-    int rows = DEFAULT_ROWS;
-    try{
-      if(!TextUtils.isEmpty(rowsStr)) {
-        rows = Integer.parseInt(rowsStr);
-      }
-    }catch (NumberFormatException e){
-      //ignore
-      e.printStackTrace();
-    }
-
-    editText.setLines(rows);
-    editText.setMinLines(rows);
-  }
-
-  @Override
-  protected int getVerticalGravity() {
-    return Gravity.TOP;
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.ROWS:
-        Integer rows = WXUtils.getInteger(param,null);
-        if (rows != null)
-          setRows(rows);
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @WXComponentProp(name = Constants.Name.ROWS)
-  public void setRows(int rows){
-    WXEditText text = getHostView();
-    if(text == null||rows <=0 ){
-      return;
-    }
-
-    text.setLines(rows);
-  }
-
-  @Override
-  protected float getMeasureHeight(){
-    return getMeasuredLineHeight() * mNumberOfLines;
-  }
-
-  @Override
-  protected void updateStyleAndAttrs() {
-    super.updateStyleAndAttrs();
-    Object raw = getAttrs().get(Constants.Name.ROWS);
-    if (raw == null) {
-      return;
-    } else if (raw instanceof String) {
-      String rowsStr = (String) raw;
-      try {
-        int lines = Integer.parseInt(rowsStr);
-        if (lines > 0) {
-          mNumberOfLines = lines;
-        }
-      } catch (NumberFormatException e) {
-        e.printStackTrace();
-      }
-    } else if (raw instanceof Integer) {
-      mNumberOfLines = (Integer) raw;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXA.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXA.java
deleted file mode 100644
index e0b8442..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXA.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXFrameLayout;
-import com.taobao.weex.utils.ATagUtil;
-
-@Component(lazyload = false)
-public class WXA extends WXDiv {
-
-  @Deprecated
-  public WXA(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, basicComponentData);
-  }
-
-  public WXA(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  @Override
-  protected void onHostViewInitialized(WXFrameLayout host) {
-    addClickListener(new OnClickListener() {
-      @Override
-      public void onHostViewClick() {
-        String href;
-        WXAttr attr = getAttrs();
-        if (attr !=null && (href = (String)attr.get("href")) != null) {
-          ATagUtil.onClick(null, getInstanceId(), href);
-        }
-      }
-    });
-    super.onHostViewInitialized(host);
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch(key){
-      case Constants.Name.HREF:
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXBaseRefresh.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXBaseRefresh.java
deleted file mode 100644
index 45a21e8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXBaseRefresh.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXFrameLayout;
-
-/**
- * div component
- */
-@Component(lazyload = false)
-
-public class WXBaseRefresh extends WXVContainer<WXFrameLayout> {
-
-  private WXLoadingIndicator mLoadingIndicator;
-
-  public WXBaseRefresh(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
-    super(instance, parent, lazy, basicComponentData);
-  }
-
-  @Override
-  public void addChild(WXComponent child) {
-    super.addChild(child);
-    this.checkLoadingIndicator(child);
-  }
-
-  @Override
-  protected WXFrameLayout initComponentHostView(@NonNull Context context) {
-    return new WXFrameLayout(context);
-  }
-
-  @Override
-  public void addChild(WXComponent child, int index) {
-    super.addChild(child, index);
-    this.checkLoadingIndicator(child);
-  }
-
-  private void checkLoadingIndicator(WXComponent child) {
-    if (child instanceof WXLoadingIndicator) {
-      mLoadingIndicator = (WXLoadingIndicator) child;
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXBasicComponentType.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXBasicComponentType.java
deleted file mode 100644
index 936206f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXBasicComponentType.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-/**
- * basic Component types
- */
-public class WXBasicComponentType {
-
-  public static final String TEXT = "text";
-  public static final String IMAGE = "image";
-  public static final String IMG = "img";
-  public static final String CONTAINER = "container";
-  public static final String DIV = "div";
-  public static final String SCROLLER = "scroller";
-  public static final String SLIDER = "slider";
-  public static final String SLIDER_NEIGHBOR = "slider-neighbor";
-  public static final String LIST = "list";
-  public static final String RECYCLER = "recycler";
-  public static final String WATERFALL = "waterfall";
-  public static final String VLIST = "vlist";
-  public static final String HLIST = "hlist";
-  public static final String CELL = "cell";
-  public static final String HEADER = "header";
-  public static final String FOOTER = "footer";
-  public static final String INDICATOR = "indicator";
-  public static final String VIDEO = "video";
-  public static final String INPUT = "input";
-  public static final String TEXTAREA = "textarea";
-  public static final String SWITCH = "switch";
-  public static final String A = "a";
-  public static final String EMBED = "embed";
-  public static final String WEB = "web";
-  public static final String REFRESH = "refresh";
-  public static final String LOADING = "loading";
-  public static final String LOADING_INDICATOR = "loading-indicator";
-  public static final String CYCLE_SLIDER = "cycleslider";
-  public static final String RICHTEXT = "richtext";
-
-  public static final String RECYCLE_LIST = "recycle-list";
-  public static final String CELL_SLOT = "cell-slot";
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponent.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponent.java
deleted file mode 100644
index 17630e1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponent.java
+++ /dev/null
@@ -1,2467 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.annotation.SuppressLint;
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.content.Intent;
-import android.content.res.ColorStateList;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Path;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.graphics.Shader;
-import android.graphics.drawable.ColorDrawable;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.LayerDrawable;
-import android.graphics.drawable.RippleDrawable;
-import android.os.Build;
-import android.support.annotation.CallSuper;
-import android.support.annotation.CheckResult;
-import android.support.annotation.IntDef;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.v4.view.AccessibilityDelegateCompat;
-import android.support.v4.view.ViewCompat;
-import android.support.v4.view.accessibility.AccessibilityNodeInfoCompat;
-import android.text.TextUtils;
-import android.util.Pair;
-import android.view.Gravity;
-import android.view.Menu;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewOverlay;
-import android.widget.FrameLayout;
-import com.alibaba.fastjson.JSONArray;
-import com.taobao.weex.ComponentObserver;
-import com.taobao.weex.IWXActivityStateListener;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXAccessibilityRoleAdapter;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.bridge.EventResult;
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.IWXObject;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXPerformance;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.dom.CSSShorthand.CORNER;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.dom.transition.WXTransition;
-import com.taobao.weex.layout.ContentBoxMeasurement;
-import com.taobao.weex.performance.WXAnalyzerDataTransfer;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.tracing.Stopwatch;
-import com.taobao.weex.tracing.WXTracing;
-import com.taobao.weex.ui.IFComponentHolder;
-import com.taobao.weex.ui.WXRenderManager;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.action.GraphicActionAnimation;
-import com.taobao.weex.ui.action.GraphicActionUpdateStyle;
-import com.taobao.weex.ui.action.GraphicPosition;
-import com.taobao.weex.ui.action.GraphicSize;
-import com.taobao.weex.ui.animation.WXAnimationBean;
-import com.taobao.weex.ui.animation.WXAnimationModule;
-import com.taobao.weex.ui.component.basic.WXBasicComponent;
-import com.taobao.weex.ui.component.binding.Statements;
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
-import com.taobao.weex.ui.component.pesudo.OnActivePseudoListner;
-import com.taobao.weex.ui.component.pesudo.PesudoStatus;
-import com.taobao.weex.ui.component.pesudo.TouchActivePseudoListener;
-import com.taobao.weex.ui.flat.FlatComponent;
-import com.taobao.weex.ui.flat.FlatGUIContext;
-import com.taobao.weex.ui.flat.WidgetContainer;
-import com.taobao.weex.ui.flat.widget.AndroidViewWidget;
-import com.taobao.weex.ui.flat.widget.Widget;
-import com.taobao.weex.ui.view.border.BorderDrawable;
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import com.taobao.weex.ui.view.gesture.WXGestureType;
-import com.taobao.weex.utils.BoxShadowUtil;
-import com.taobao.weex.utils.WXDataStructureUtil;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXReflectionUtils;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-import java.lang.reflect.Type;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Locale;
-import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.ConcurrentLinkedQueue;
-import java.util.concurrent.CountDownLatch;
-import java.util.concurrent.TimeUnit;
-
-/**
- * abstract component
- */
-public abstract class WXComponent<T extends View> extends WXBasicComponent implements IWXObject, IWXActivityStateListener, OnActivePseudoListner {
-
-  public static final String PROP_FIXED_SIZE = "fixedSize";
-  public static final String PROP_FS_MATCH_PARENT = "m";
-  public static final String PROP_FS_WRAP_CONTENT = "w";
-  public static final String TYPE = "type";
-  public static final String ROOT = "_root";
-
-  private int mFixedProp = 0;
-  /** package **/ T mHost;
-
-  private volatile WXVContainer mParent;
-  private WXSDKInstance mInstance;
-  private Context mContext;
-
-  private int mAbsoluteY = 0;
-  private int mAbsoluteX = 0;
-  private boolean isLastLayoutDirectionRTL = false;
-  @Nullable
-  private Set<String> mGestureType;
-
-  private BorderDrawable mBackgroundDrawable;
-  private Drawable mRippleBackground;
-  private int mPreRealWidth = 0;
-  private int mPreRealHeight = 0;
-  private int mPreRealLeft = 0;
-  private int mPreRealRight = 0;
-  private int mPreRealTop = 0;
-  private int mStickyOffset = 0;
-  protected WXGesture mGesture;
-  private IFComponentHolder mHolder;
-  private boolean isUsing = false;
-  private List<OnClickListener> mHostClickListeners;
-  private List<OnFocusChangeListener> mFocusChangeListeners;
-  private Set<String> mAppendEvents;
-  private WXAnimationModule.AnimationHolder mAnimationHolder;
-  private PesudoStatus mPesudoStatus;
-  private boolean mIsDestroyed = false;
-  private boolean mIsDisabled = false;
-  private int mType = TYPE_COMMON;
-  private boolean mNeedLayoutOnAnimation = false;
-  private String mLastBoxShadowId;
-  public int mDeepInComponentTree = 0;
-  public boolean mIsAddElementToTree = false;
-  //for fix element case
-  public int interactionAbsoluteX=0,interactionAbsoluteY=0;
-  //for fix slider case :cssLeft is not real left base parent;
-  protected int mChildrensWidth = 0;
-  private boolean mHasAddFocusListener = false;
-
-  public WXTracing.TraceInfo mTraceInfo = new WXTracing.TraceInfo();
-
-  public static final int TYPE_COMMON = 0;
-  public static final int TYPE_VIRTUAL = 1;
-
-  private boolean waste = false;
-  public boolean isIgnoreInteraction = false;
-
-  protected ContentBoxMeasurement contentBoxMeasurement;
-  private WXTransition mTransition;
-  private GraphicSize mPseudoResetGraphicSize;
-  @Nullable
-  private ConcurrentLinkedQueue<Pair<String, Map<String, Object>>> animations;
-
-  @Deprecated
-  public WXComponent(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-  @Deprecated
-  public WXComponent(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, basicComponentData);
-  }
-
-  public WXComponent(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    this(instance, parent, TYPE_COMMON, basicComponentData);
-  }
-
-  public WXComponent(WXSDKInstance instance, WXVContainer parent, int type, BasicComponentData basicComponentData) {
-    super(basicComponentData);
-    mInstance = instance;
-    mContext = mInstance.getContext();
-    mParent = parent;
-    mType = type;
-
-    if (instance != null)
-      setViewPortWidth(instance.getInstanceViewPortWidth());
-
-    onCreate();
-    ComponentObserver observer;
-    if ((observer = getInstance().getComponentObserver()) != null) {
-      observer.onCreate(this);
-    }
-  }
-
-
-
-  @Override
-  protected final void bindComponent(WXComponent component) {
-    super.bindComponent(component);
-    if (getInstance() != null) {
-      setViewPortWidth(getInstance().getInstanceViewPortWidth());
-    }
-    mParent = component.getParent();
-    mType = component.getType();
-  }
-
-  protected final void setContentBoxMeasurement(final ContentBoxMeasurement contentBoxMeasurement) {
-    this.contentBoxMeasurement = contentBoxMeasurement;
-    mInstance.addContentBoxMeasurement(getRenderObjectPtr(), contentBoxMeasurement);
-    WXBridgeManager.getInstance().bindMeasurementToRenderObject(getRenderObjectPtr());
-  }
-
-
-  @SuppressLint("RtlHardcoded")
-  public void setMarginsSupportRTL(ViewGroup.MarginLayoutParams lp, int left, int top, int right, int bottom) {
-      lp.setMargins(left, top, right, bottom);
-      if (lp instanceof FrameLayout.LayoutParams) {
-          FrameLayout.LayoutParams lp_frameLayout = (FrameLayout.LayoutParams) lp;
-          lp_frameLayout.gravity = Gravity.LEFT | Gravity.TOP;
-      }
-  }
-
-  public void updateStyles(WXComponent component) {
-    if (component != null) {
-      updateProperties(component.getStyles());
-      applyBorder(component);
-    }
-  }
-
-  public void updateStyles(Map<String, Object> styles) {
-    if (styles != null) {
-      updateProperties(styles);
-      applyBorder(this);
-    }
-  }
-
-  public void updateAttrs(WXComponent component) {
-    if (component != null) {
-      updateProperties(component.getAttrs());
-    }
-  }
-
-  public void updateAttrs(Map<String, Object> attrs) {
-    if (attrs != null) {
-      updateProperties(attrs);
-    }
-  }
-
-  private void applyBorder(WXComponent component) {
-    CSSShorthand border = component.getBorder();
-    float left = border.get(CSSShorthand.EDGE.LEFT);
-    float top = border.get(CSSShorthand.EDGE.TOP);
-    float right = border.get(CSSShorthand.EDGE.RIGHT);
-    float bottom = border.get(CSSShorthand.EDGE.BOTTOM);
-
-    if (mHost == null) {
-      return;
-    }
-
-    setBorderWidth(Constants.Name.BORDER_LEFT_WIDTH, left);
-    setBorderWidth(Constants.Name.BORDER_TOP_WIDTH, top);
-    setBorderWidth(Constants.Name.BORDER_RIGHT_WIDTH, right);
-    setBorderWidth(Constants.Name.BORDER_BOTTOM_WIDTH, bottom);
-  }
-
-  public void setPadding(CSSShorthand padding, CSSShorthand border) {
-    int left = (int) (padding.get(CSSShorthand.EDGE.LEFT) + border.get(CSSShorthand.EDGE.LEFT));
-    int top = (int) (padding.get(CSSShorthand.EDGE.TOP) + border.get(CSSShorthand.EDGE.TOP));
-    int right = (int) (padding.get(CSSShorthand.EDGE.RIGHT) + border.get(CSSShorthand.EDGE.RIGHT));
-    int bottom = (int) (padding.get(CSSShorthand.EDGE.BOTTOM) + border.get(CSSShorthand.EDGE.BOTTOM));
-
-    if (this instanceof FlatComponent && !((FlatComponent) this).promoteToView(true)) {
-      ((FlatComponent) this).getOrCreateFlatWidget().setContentBox(left, top, right, bottom);
-    } else if (mHost != null) {
-      mHost.setPadding(left, top, right, bottom);
-    }
-  }
-
-
-  public void applyComponentEvents(){
-       applyEvents();
-  }
-
-  private void applyEvents() {
-    if (getEvents() == null || getEvents().isEmpty())
-      return;
-    WXEvent event = getEvents();
-    int size = event.size();
-    for (int i=0; i<size; i++) {
-      if(i >= event.size()){
-        break;
-      }
-      String type = event.get(i);
-      addEvent(type);
-    }
-    setActiveTouchListener();
-  }
-
-  /**
-   * Do not use this method to add event, this only apply event already add to DomObject.
-   *
-   * @param type
-   */
-  public void addEvent(final String type) {
-    if (mAppendEvents == null) {
-      mAppendEvents = new HashSet<>();
-    }
-    if (TextUtils.isEmpty(type) || mAppendEvents.contains(type)) {
-      return;
-    }
-    final View view = getRealView();
-
-    if (type.equals(Constants.Event.LAYEROVERFLOW))
-      addLayerOverFlowListener(getRef());
-
-    if (type.equals(Constants.Event.CLICK)) {
-      if (view == null) {
-        // wait next time to add.
-        return;
-      }
-      if(mClickEventListener == null){
-        mClickEventListener = new OnClickListenerImp();
-      }
-      addClickListener(mClickEventListener);
-    } else if ((type.equals(Constants.Event.FOCUS) || type.equals(Constants.Event.BLUR))) {
-      if (!mHasAddFocusListener){
-        mHasAddFocusListener = true;
-        addFocusChangeListener(new OnFocusChangeListener() {
-        @Override
-        public void onFocusChange(boolean hasFocus) {
-          Map<String, Object> params = new HashMap<>();
-          params.put("timeStamp", System.currentTimeMillis());
-          fireEvent(hasFocus ? Constants.Event.FOCUS : Constants.Event.BLUR, params);
-        }
-      });
-      }
-    } else if (needGestureDetector(type)) {
-      if (null == view) {
-        // wait next time to add.
-        return;
-      }
-      if (view instanceof WXGestureObservable) {
-        if (mGesture == null) {
-          mGesture = new WXGesture(this, mContext);
-          boolean isPreventMove = WXUtils.getBoolean(getAttrs().get(Constants.Name.PREVENT_MOVE_EVENT), false);
-          mGesture.setPreventMoveEvent(isPreventMove);
-        }
-        if (mGestureType == null) {
-          mGestureType = new HashSet<>();
-        }
-        mGestureType.add(type);
-        ((WXGestureObservable)view).registerGestureListener(mGesture);
-      } else {
-        WXLogUtils.e(view.getClass().getSimpleName() + " don't implement " +
-            "WXGestureObservable, so no gesture is supported.");
-      }
-    } else {
-      final Scrollable scroller = getParentScroller();
-      if (scroller == null) {
-        // wait next time to add.
-        return;
-      }
-      if (type.equals(Constants.Event.APPEAR)) {
-        scroller.bindAppearEvent(this);
-      } else if (type.equals(Constants.Event.DISAPPEAR)) {
-        scroller.bindDisappearEvent(this);
-      }
-    }
-    // Final add to mAppendEvents.
-    mAppendEvents.add(type);
-  }
-
-  protected void onCreate() {
-
-  }
-
-  public void bindHolder(IFComponentHolder holder) {
-    mHolder = holder;
-  }
-
-
-  public WXSDKInstance getInstance() {
-    return mInstance;
-  }
-
-  public Context getContext() {
-    return mContext;
-  }
-
-  /**
-   * Find component by component reference.
-   *
-   * @param ref
-   * @return
-   */
-  protected final WXComponent findComponent(String ref) {
-    if (mInstance != null && ref != null) {
-      return WXSDKManager.getInstance()
-              .getWXRenderManager()
-              .getWXComponent(mInstance.getInstanceId(), ref);
-    }
-    return null;
-  }
-
-  public String getAttrByKey(String key) {
-    return "default";
-  }
-
-  //Holding the animation bean when component is uninitialized
-  public void postAnimation(WXAnimationModule.AnimationHolder holder) {
-    this.mAnimationHolder = holder;
-  }
-
-  //This method will be removed once flatGUI is completed.
-  @RestrictTo(RestrictTo.Scope.LIBRARY)
-  public boolean isFlatUIEnabled() {
-    return mParent != null && mParent.isFlatUIEnabled();
-  }
-
-  private class OnClickListenerImp implements OnClickListener{
-    @Override
-    public void onHostViewClick() {
-      Map<String, Object> param = WXDataStructureUtil.newHashMapWithExpectedSize(1);
-      Map<String, Object> position = WXDataStructureUtil.newHashMapWithExpectedSize(4);
-      int[] location = new int[2];
-      mHost.getLocationOnScreen(location);
-      position.put("x", WXViewUtils.getWebPxByWidth(location[0], mInstance.getInstanceViewPortWidth()));
-      position.put("y", WXViewUtils.getWebPxByWidth(location[1], mInstance.getInstanceViewPortWidth()));
-      position.put("width", WXViewUtils.getWebPxByWidth(getLayoutWidth(), mInstance.getInstanceViewPortWidth()));
-      position.put("height", WXViewUtils.getWebPxByWidth(getLayoutHeight(), mInstance.getInstanceViewPortWidth()));
-      param.put(Constants.Name.POSITION, position);
-      fireEvent(Constants.Event.CLICK, param);
-    }
-  };
-  private OnClickListenerImp mClickEventListener;
-
-  public String getInstanceId() {
-    return mInstance.getInstanceId();
-  }
-
-  public Rect getComponentSize() {
-    Rect size = new Rect();
-    if (mHost != null) {
-      int[] location = new int[2];
-      int[] anchor = new int[2];
-      mHost.getLocationOnScreen(location);
-      mInstance.getContainerView().getLocationOnScreen(anchor);
-
-      int left = location[0] - anchor[0];
-      int top = (location[1] - mStickyOffset) - anchor[1];
-      int width = (int) getLayoutWidth();
-      int height = (int) getLayoutHeight();
-      size.set(left, top, left + width, top + height);
-    }
-    return size;
-  }
-
-  public final void invoke(String method, JSONArray args) {
-    final Invoker invoker = mHolder.getMethodInvoker(method);
-    if (invoker != null) {
-      try {
-        getInstance()
-                .getNativeInvokeHelper()
-                .invoke(this, invoker, args);
-
-      } catch (Exception e) {
-        WXLogUtils.e("[WXComponent] updateProperties :" + "class:" + getClass() + "method:" + invoker.toString() + " function " + WXLogUtils.getStackTrace(e));
-      }
-    } else {
-      onInvokeUnknownMethod(method, args);
-    }
-  }
-
-  /**
-   * Will be invoked when request method not found.
-   * Subclass should override this method, If you return hard-code method list in {@link IFComponentHolder#getMethods()}
-   *
-   * @param method
-   * @param args
-   */
-  protected void onInvokeUnknownMethod(String method, JSONArray args) {
-
-  }
-
-  public interface OnClickListener {
-    void onHostViewClick();
-  }
-
-  public interface OnFocusChangeListener{
-    void onFocusChange(boolean hasFocus);
-  }
-
-  public final void fireEvent(String type){
-    fireEvent(type,null);
-  }
-
-  public final void fireEvent(String type, Map<String, Object> params){
-    if(WXUtils.getBoolean(getAttrs().get("fireEventSyn"), false)){
-      fireEventWait(type, params);
-    }else{
-      fireEvent(type, params,null, null);
-    }
-  }
-
-  public final EventResult fireEventWait(String type, Map<String, Object> params){
-    final CountDownLatch waitLatch = new CountDownLatch(1);
-    EventResult callback = new EventResult(){
-      @Override
-      public void onCallback(Object result) {
-        super.onCallback(result);
-        waitLatch.countDown();
-      }
-    };
-    try{
-      fireEvent(type, params, null, callback);
-      waitLatch.await(50, TimeUnit.MILLISECONDS);
-      return  callback;
-    }catch (Exception e){
-      if(WXEnvironment.isApkDebugable()){
-        WXLogUtils.e("fireEventWait", e);
-      }
-      return  callback;
-    }
-  }
-
-  protected final void fireEvent(String type, Map<String, Object> params,Map<String, Object> domChanges){
-    fireEvent(type, params, domChanges, null);
-  }
-
-
-  private final void fireEvent(String type, Map<String, Object> params,Map<String, Object> domChanges, EventResult callback){
-    if(mInstance != null) {
-      List<Object> eventArgsValues = null;
-      if(getEvents() != null && getEvents().getEventBindingArgsValues() != null){
-        eventArgsValues = getEvents().getEventBindingArgsValues().get(type);
-      }
-      if(params != null){
-        String componentId = Statements.getComponentId(this);
-        if(componentId != null) {
-          params.put("componentId", componentId);
-        }
-      }
-      mInstance.fireEvent(getRef(), type, params,domChanges, eventArgsValues, callback);
-    }
-  }
-
-  /**
-   * find certain class type parent
-   * */
-  public  Object findTypeParent(WXComponent component, Class type){
-    if(component.getClass() == type){
-      return component;
-    }
-    if(component.getParent() != null) {
-      findTypeParent(component.getParent(), type);
-    }
-    return  null;
-  }
-
-  /**
-   * The view is created as needed
-   * @return true for lazy
-   */
-  public boolean isLazy() {
-    if(mLazy){
-      return true;
-    }
-    return mParent != null && mParent.isLazy();
-  }
-
-  protected final void addFocusChangeListener(OnFocusChangeListener l){
-    View view;
-    if(l != null && (view = getRealView()) != null) {
-      if( mFocusChangeListeners == null){
-        mFocusChangeListeners = new ArrayList<>();
-        view.setFocusable(true);
-        view.setOnFocusChangeListener(new View.OnFocusChangeListener() {
-          @Override
-          public void onFocusChange(View v, boolean hasFocus) {
-            for (OnFocusChangeListener listener : mFocusChangeListeners){
-              if(listener != null){
-                listener.onFocusChange(hasFocus);
-              }
-            }
-          }
-        });
-      }
-      mFocusChangeListeners.add(l);
-    }
-  }
-
-  protected final void addClickListener(OnClickListener l){
-    View view;
-    if(l != null && (view = getRealView()) != null) {
-      if(mHostClickListeners == null){
-        mHostClickListeners = new ArrayList<>();
-        view.setOnClickListener(new View.OnClickListener() {
-          @Override
-          public void onClick(View v) {
-            if(mGesture != null && mGesture.isTouchEventConsumedByAdvancedGesture()){
-              //event is already consumed by gesture
-              return;
-            }
-            for (OnClickListener listener : mHostClickListeners){
-              if(listener != null) {
-                listener.onHostViewClick();
-              }
-            }
-          }
-        });
-      }
-      mHostClickListeners.add(l);
-
-    }
-  }
-
-  protected final void removeClickListener(OnClickListener l) {
-    mHostClickListeners.remove(l);
-  }
-
-  public void bindData(WXComponent component) {
-    if (!isLazy()) {
-      if (component == null) {
-        component = this;
-      }
-      bindComponent(component);
-      updateStyles(component);
-      updateAttrs(component);
-      updateExtra(component.getExtra());
-    }
-  }
-
-  public void applyLayoutAndEvent(WXComponent component) {
-    if (!isLazy()) {
-      if (component == null) {
-        component = this;
-      }
-      bindComponent(component);
-      setSafeLayout(component);
-      setPadding(component.getPadding(), component.getBorder());
-      applyEvents();
-    }
-  }
-
-  public void setDemission(GraphicSize size, GraphicPosition position) {
-    setLayoutPosition(position);
-    setLayoutSize(size);
-  }
-
-  public void updateDemission(float top, float bottom, float left, float right, float height, float width) {
-    getLayoutPosition().update(top, bottom, left, right);
-    getLayoutSize().update(width, height);
-  }
-
-
-  public void applyLayoutOnly(){
-    if(!isLazy()) {
-      setSafeLayout(this);
-      setPadding(this.getPadding(), this.getBorder());
-    }
-  }
-
-
-  public void refreshData(WXComponent component) {
-
-  }
-
-  @Deprecated
-  public void updateProperties(Map<String, Object> props) {
-    if (props == null || (mHost == null && !isVirtualComponent())) {
-      return;
-    }
-
-    for (Map.Entry<String, Object> entry : props.entrySet()) {
-      Object key_obj = entry.getKey();
-      String key = WXUtils.getString(key_obj, null);
-      if ((key != null) && !(key_obj instanceof String)) {
-        Map<String, String> map = new HashMap<>();
-        map.put("componentType", getComponentType());
-        map.put("actual key", key == null ? "" : key);
-        WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),
-            WXErrorCode.WX_RENDER_ERR_COMPONENT_ATTR_KEY,
-            "WXComponent.updateProperties",
-            WXErrorCode.WX_RENDER_ERR_COMPONENT_ATTR_KEY.getErrorMsg(),
-            map);
-      }
-
-      Object param = entry.getValue();
-      String value = WXUtils.getString(param, null);
-
-      if (key == null) {
-        WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),
-                WXErrorCode.WX_RENDER_ERR_NULL_KEY, "updateProperties",
-                WXErrorCode.WX_RENDER_ERR_NULL_KEY.getErrorMsg(), null);
-      } else {
-        if (TextUtils.isEmpty(value)) {
-          param = convertEmptyProperty(key, value);
-        }
-        if (!setProperty(key, param)) {
-          if (mHolder == null) {
-            return;
-          }
-          Invoker invoker = mHolder.getPropertyInvoker(key);
-          if (invoker != null) {
-            try {
-              Type[] paramClazzs = invoker.getParameterTypes();
-              if (paramClazzs.length != 1) {
-                WXLogUtils.e("[WXComponent] setX method only one parameter：" + invoker);
-                return;
-              }
-              param = WXReflectionUtils.parseArgument(paramClazzs[0], param);
-              invoker.invoke(this, param);
-            } catch (Exception e) {
-              WXLogUtils.e("[WXComponent] updateProperties :" + "class:" + getClass() + "method:" + invoker.toString() + " function " + WXLogUtils.getStackTrace(e));
-            }
-          }
-        }
-      }
-    }
-    readyToRender();
-    if (this instanceof FlatComponent && mBackgroundDrawable != null) {
-      FlatComponent flatComponent = (FlatComponent) this;
-      if (!flatComponent.promoteToView(true) && !(flatComponent
-              .getOrCreateFlatWidget() instanceof AndroidViewWidget)) {
-        flatComponent.getOrCreateFlatWidget().setBackgroundAndBorder(mBackgroundDrawable);
-      }
-    }
-  }
-
-  /**
-   * Apply styles and attributes.
-   *
-   * @param key   name of argument
-   * @param param value of argument
-   * @return true means that the property is consumed
-   */
-  protected boolean setProperty(String key, Object param) {
-    if(key == null){
-      return true;
-    }
-    switch (key) {
-      case Constants.Name.PREVENT_MOVE_EVENT:
-        if (mGesture != null) {
-          mGesture.setPreventMoveEvent(WXUtils.getBoolean(param, false));
-        }
-        return true;
-      case Constants.Name.DISABLED:
-        Boolean disabled = WXUtils.getBoolean(param, null);
-        if (disabled != null) {
-          setDisabled(disabled);
-          setPseudoClassStatus(Constants.PSEUDO.DISABLED, disabled);
-        }
-        return true;
-      case Constants.Name.POSITION:
-        String position = WXUtils.getString(param, null);
-        if (position != null)
-          setSticky(position);
-        return true;
-      case Constants.Name.BACKGROUND_COLOR:
-        String bgColor = WXUtils.getString(param, null);
-        if (bgColor != null)
-          setBackgroundColor(bgColor);
-        return true;
-      case Constants.Name.BACKGROUND_IMAGE:
-        String bgImage = WXUtils.getString(param, null);
-        if (bgImage != null && mHost != null) {
-          setBackgroundImage(bgImage);
-        }
-        return true;
-      case Constants.Name.OPACITY:
-        Float opacity = WXUtils.getFloat(param, null);
-        if (opacity != null)
-          setOpacity(opacity);
-        return true;
-      case Constants.Name.BORDER_RADIUS:
-      case Constants.Name.BORDER_TOP_LEFT_RADIUS:
-      case Constants.Name.BORDER_TOP_RIGHT_RADIUS:
-      case Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS:
-      case Constants.Name.BORDER_BOTTOM_LEFT_RADIUS:
-        Float radius = WXUtils.getFloat(param, null);
-        if (radius != null)
-          setBorderRadius(key, radius);
-        return true;
-      case Constants.Name.BORDER_STYLE:
-      case Constants.Name.BORDER_RIGHT_STYLE:
-      case Constants.Name.BORDER_BOTTOM_STYLE:
-      case Constants.Name.BORDER_LEFT_STYLE:
-      case Constants.Name.BORDER_TOP_STYLE:
-        String border_style = WXUtils.getString(param, null);
-        if (border_style != null)
-          setBorderStyle(key, border_style);
-        return true;
-      case Constants.Name.BORDER_COLOR:
-      case Constants.Name.BORDER_TOP_COLOR:
-      case Constants.Name.BORDER_RIGHT_COLOR:
-      case Constants.Name.BORDER_BOTTOM_COLOR:
-      case Constants.Name.BORDER_LEFT_COLOR:
-        String border_color = WXUtils.getString(param, null);
-        if (border_color != null)
-          setBorderColor(key, border_color);
-        return true;
-      case Constants.Name.VISIBILITY:
-        String visibility = WXUtils.getString(param, null);
-        if (visibility != null)
-          setVisibility(visibility);
-        return true;
-      case Constants.Name.ELEVATION:
-        if (param != null) {
-          updateElevation();
-        }
-        return true;
-      case PROP_FIXED_SIZE:
-        String fixedSize = WXUtils.getString(param, PROP_FS_MATCH_PARENT);
-        setFixedSize(fixedSize);
-        return true;
-      case Constants.Name.ARIA_LABEL:
-        String label = WXUtils.getString(param, "");
-        setAriaLabel(label);
-        return true;
-      case Constants.Name.ARIA_HIDDEN:
-        boolean isHidden = WXUtils.getBoolean(param, false);
-        setAriaHidden(isHidden);
-        return true;
-      case Constants.Name.WIDTH:
-      case Constants.Name.MIN_WIDTH:
-      case Constants.Name.MAX_WIDTH:
-      case Constants.Name.HEIGHT:
-      case Constants.Name.MIN_HEIGHT:
-      case Constants.Name.MAX_HEIGHT:
-      case Constants.Name.ALIGN_ITEMS:
-      case Constants.Name.ALIGN_SELF:
-      case Constants.Name.FLEX:
-      case Constants.Name.FLEX_DIRECTION:
-      case Constants.Name.JUSTIFY_CONTENT:
-      case Constants.Name.FLEX_WRAP:
-      case Constants.Name.MARGIN:
-      case Constants.Name.MARGIN_TOP:
-      case Constants.Name.MARGIN_LEFT:
-      case Constants.Name.MARGIN_RIGHT:
-      case Constants.Name.MARGIN_BOTTOM:
-      case Constants.Name.PADDING:
-      case Constants.Name.PADDING_TOP:
-      case Constants.Name.PADDING_LEFT:
-      case Constants.Name.PADDING_RIGHT:
-      case Constants.Name.PADDING_BOTTOM:
-      case Constants.Name.BORDER_WIDTH:
-      case Constants.Name.BORDER_TOP_WIDTH:
-      case Constants.Name.BORDER_RIGHT_WIDTH:
-      case Constants.Name.BORDER_BOTTOM_WIDTH:
-      case Constants.Name.BORDER_LEFT_WIDTH:
-      case Constants.Name.LEFT:
-      case Constants.Name.TOP:
-      case Constants.Name.RIGHT:
-      case Constants.Name.BOTTOM:
-        return true;
-      case Constants.Name.BOX_SHADOW:
-        try {
-          updateBoxShadow();
-        } catch (Throwable t) {
-          t.printStackTrace();
-        }
-        return true;
-      case Constants.Name.ROLE:
-        setRole(WXUtils.getString(param, ""));
-        return true;
-      default:
-        return false;
-    }
-  }
-
-  protected BorderDrawable getOrCreateBorder() {
-    if (mBackgroundDrawable == null) {
-      mBackgroundDrawable = new BorderDrawable();
-      if (mHost != null) {
-        WXViewUtils.setBackGround(mHost, null, this);
-        if (mRippleBackground == null) {
-          WXViewUtils.setBackGround(mHost, mBackgroundDrawable, this);
-        } else {
-          //TODO Not strictly clip according to background-clip:border-box
-          WXViewUtils.setBackGround(mHost, new LayerDrawable(new Drawable[]{
-                  mRippleBackground, mBackgroundDrawable}), this);
-        }
-      }
-    }
-    return mBackgroundDrawable;
-  }
-
-  /**
-   * layout view
-   */
-  public void setSafeLayout(WXComponent component) {
-    if (TextUtils.isEmpty(component.getComponentType())
-            || TextUtils.isEmpty(component.getRef()) || component.getLayoutPosition() == null
-            || component.getLayoutSize() == null) {
-      return;
-    }
-    setLayout(component);
-  }
-
-  /**
-   * layout view
-   */
-  public void setLayout(WXComponent component) {
-    setLayoutSize(component.getLayoutSize());
-    setLayoutPosition(component.getLayoutPosition());
-    setPaddings(component.getPadding());
-    setMargins(component.getMargin());
-    setBorders(component.getBorder());
-
-    boolean isRTL = component.isLayoutRTL();
-    setIsLayoutRTL(isRTL);
-    if (isRTL != component.isLastLayoutDirectionRTL) {
-      component.isLastLayoutDirectionRTL = isRTL;
-      layoutDirectionDidChanged(isRTL);
-    }
-
-    parseAnimation();
-
-    boolean nullParent = mParent == null;//parent is nullable
-
-    //offset by sibling
-    int siblingOffset = nullParent ? 0 : mParent.getChildrenLayoutTopOffset();
-
-    CSSShorthand parentPadding = (nullParent ? new CSSShorthand() : mParent.getPadding());
-    CSSShorthand parentBorder = (nullParent ? new CSSShorthand() : mParent.getBorder());
-
-    int realWidth = (int) getLayoutSize().getWidth();
-    int realHeight = (int) getLayoutSize().getHeight();
-
-    int realLeft = 0;
-    int realTop = 0;
-    int realRight = 0;
-
-    if (isFixed()) {
-      realLeft = (int) (getLayoutPosition().getLeft() - getInstance().getRenderContainerPaddingLeft());
-      realTop = (int) (getLayoutPosition().getTop() - getInstance().getRenderContainerPaddingTop()) + siblingOffset;
-    } else {
-      realLeft = (int) (getLayoutPosition().getLeft() -
-              parentPadding.get(CSSShorthand.EDGE.LEFT) - parentBorder.get(CSSShorthand.EDGE.LEFT));
-      realTop = (int) (getLayoutPosition().getTop() -
-              parentPadding.get(CSSShorthand.EDGE.TOP) - parentBorder.get(CSSShorthand.EDGE.TOP)) + siblingOffset;
-    }
-
-    realRight = (int) getMargin().get(CSSShorthand.EDGE.RIGHT);
-    int realBottom = (int) getMargin().get(CSSShorthand.EDGE.BOTTOM);
-
-    Point rawOffset = new Point(
-            (int) getLayoutPosition().getLeft(),
-            (int) getLayoutPosition().getTop());
-
-    if (mPreRealWidth == realWidth && mPreRealHeight == realHeight && mPreRealLeft == realLeft && mPreRealRight == realRight && mPreRealTop == realTop) {
-      return;
-    }
-
-    if (this instanceof WXCell && realHeight >= WXPerformance.VIEW_LIMIT_HEIGHT && realWidth>=WXPerformance.VIEW_LIMIT_WIDTH){
-      mInstance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_CELL_EXCEED_NUM,1);
-      mInstance.getWXPerformance().cellExceedNum++;
-      if (WXAnalyzerDataTransfer.isOpenPerformance){
-        WXAnalyzerDataTransfer.transferPerformance(getInstanceId(),"details",WXInstanceApm.KEY_PAGE_STATS_CELL_EXCEED_NUM,
-            String.format(Locale.ROOT, "cell:ref:%s,[w:%d,h:%d],attrs:%s,styles:%s",getRef(),realWidth,realHeight,getAttrs(),getStyles())
-        );
-      }
-
-    }
-
-    mAbsoluteY = (int) (nullParent ? 0 : mParent.getAbsoluteY() + getCSSLayoutTop());
-    mAbsoluteX = (int) (nullParent ? 0 : mParent.getAbsoluteX() + getCSSLayoutLeft());
-
-    if (mHost == null) {
-      return;
-    }
-
-    //calculate first screen time
-    if (!(mHost instanceof ViewGroup) && mAbsoluteY + realHeight > mInstance.getWeexHeight() + 1) {
-      if (!mInstance.mEnd){
-        mInstance.onOldFsRenderTimeLogic();
-      }
-      if (!mInstance.isNewFsEnd){
-        mInstance.isNewFsEnd = true;
-        mInstance.getApmForInstance().arriveNewFsRenderTime();
-      }
-    }
-
-    MeasureOutput measureOutput = measure(realWidth, realHeight);
-    realWidth = measureOutput.width;
-    realHeight = measureOutput.height;
-
-    setComponentLayoutParams(realWidth, realHeight, realLeft, realTop, realRight, realBottom, rawOffset);
-  }
-
-  private void setComponentLayoutParams(int realWidth, int realHeight, int realLeft, int realTop,
-                                        int realRight, int realBottom, Point rawOffset) {
-    if(getInstance() == null || getInstance().isDestroy()){
-      return;
-    }
-
-    FlatGUIContext UIImp = getInstance().getFlatUIContext();
-    WidgetContainer ancestor;
-    Widget widget;
-    if (UIImp != null && (ancestor = UIImp.getFlatComponentAncestor(this)) != null) {
-      if (this instanceof FlatComponent && !((FlatComponent) this).promoteToView(true)) {
-        widget = ((FlatComponent) this).getOrCreateFlatWidget();
-      } else {
-        widget = UIImp.getAndroidViewWidget(this);
-      }
-      setWidgetParams(widget, UIImp, rawOffset, realWidth, realHeight, realLeft, realRight, realTop,
-              realBottom);
-    } else if (mHost != null) {
-      // clear box shadow before host's size changed
-      clearBoxShadow();
-      if (isFixed()) {
-        setFixedHostLayoutParams(mHost, realWidth, realHeight, realLeft, realRight, realTop,
-                realBottom);
-      } else {
-        setHostLayoutParams(mHost, realWidth, realHeight, realLeft, realRight, realTop, realBottom);
-      }
-      recordInteraction(realWidth,realHeight);
-      mPreRealWidth = realWidth;
-      mPreRealHeight = realHeight;
-      mPreRealLeft = realLeft;
-      mPreRealRight = realRight;
-      mPreRealTop = realTop;
-      onFinishLayout();
-      // restore box shadow
-      updateBoxShadow();
-    }
-  }
-
-  /**
-   * layout direction is changed
-   * basic class is a empty implementation
-   * subclass can override this method do some RTL necessary things
-   * such as WXText
-   */
-  protected void layoutDirectionDidChanged(boolean isRTL) {
-
-  }
-
-  private void recordInteraction(int realWidth,int realHeight){
-    if (!mIsAddElementToTree){
-      return;
-    }
-    mIsAddElementToTree = false;
-    if (null == mParent){
-      interactionAbsoluteX = 0;
-      interactionAbsoluteY = 0;
-    }else {
-      float cssTop = getCSSLayoutTop();
-      float cssLeft = getCSSLayoutLeft();
-      interactionAbsoluteX = (int)(this.isFixed() ? cssLeft : mParent.interactionAbsoluteX + mParent.mChildrensWidth + cssLeft);
-      interactionAbsoluteY = (int)(this.isFixed() ? cssTop  : mParent.interactionAbsoluteY + cssTop);
-      //fix for slider impl ,and interactionTime calculate if component is out screen
-      if (WXBasicComponentType.SLIDER.equalsIgnoreCase(mParent.getComponentType()) || WXBasicComponentType.CYCLE_SLIDER.equalsIgnoreCase(mParent.getComponentType())){
-        if (!WXBasicComponentType.INDICATOR.equalsIgnoreCase(getComponentType())){
-          mParent.mChildrensWidth += (int)(realWidth + cssLeft);
-        }
-      }
-    }
-
-    if (null == getInstance().getApmForInstance().instanceRect){
-      getInstance().getApmForInstance().instanceRect = new Rect();
-    }
-    Rect instanceRect = getInstance().getApmForInstance().instanceRect;
-    instanceRect.set(0,0,mInstance.getWeexWidth(),mInstance.getWeexHeight());
-    boolean inScreen =
-          instanceRect.contains(interactionAbsoluteX,interactionAbsoluteY) //leftTop
-              || instanceRect.contains(interactionAbsoluteX+realWidth,interactionAbsoluteY)//rightTop
-              || instanceRect.contains(interactionAbsoluteX,interactionAbsoluteY+realHeight)//leftBottom
-              || instanceRect.contains(interactionAbsoluteX+realWidth,interactionAbsoluteY+realHeight);//rightBottom
-    mInstance.onChangeElement(this,!inScreen);
-  }
-
-  private void setWidgetParams(Widget widget, FlatGUIContext UIImp, Point rawoffset,
-                               int width, int height, int left, int right, int top, int bottom) {
-    Point childOffset = new Point();
-    if (mParent != null) {
-      if (mParent instanceof FlatComponent &&
-              UIImp.getFlatComponentAncestor(mParent) != null &&
-              UIImp.getAndroidViewWidget(mParent) == null) {
-        childOffset.set(rawoffset.x, rawoffset.y);
-      }
-      else{
-        childOffset.set(left, top);
-      }
-
-      if (mParent instanceof FlatComponent &&
-              UIImp.getFlatComponentAncestor(mParent) != null &&
-              UIImp.getAndroidViewWidget(mParent) == null) {
-        Point parentLayoutOffset = ((FlatComponent) mParent).getOrCreateFlatWidget().getLocInFlatContainer();
-        childOffset.offset(parentLayoutOffset.x, parentLayoutOffset.y);
-      }
-      ViewGroup.LayoutParams lp = mParent
-              .getChildLayoutParams(this, mHost, width, height, left, right, top, bottom);
-      if (lp instanceof ViewGroup.MarginLayoutParams) {
-        width = lp.width;
-        height = lp.height;
-        left = ((ViewGroup.MarginLayoutParams) lp).leftMargin;
-        right = ((ViewGroup.MarginLayoutParams) lp).rightMargin;
-        top = ((ViewGroup.MarginLayoutParams) lp).topMargin;
-        bottom = ((ViewGroup.MarginLayoutParams) lp).bottomMargin;
-      }
-    }
-    widget.setLayout(width, height, left, right, top, bottom, childOffset);
-
-    if (widget instanceof AndroidViewWidget && ((AndroidViewWidget) widget).getView()!=null) {
-      //TODO generic method if ever possible
-      setHostLayoutParams((T) ((AndroidViewWidget) widget).getView(),
-              width, height, childOffset.x, right, childOffset.y, bottom);
-    }
-  }
-
-  public int getLayoutTopOffsetForSibling() {
-    return 0;
-  }
-
-  protected void setHostLayoutParams(T host, int width, int height, int left, int right, int top, int bottom) {
-    ViewGroup.LayoutParams lp;
-    if (mParent == null) {
-        FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(width, height);
-        this.setMarginsSupportRTL(params, left, top, right, bottom);
-        lp = params;
-    } else {
-        lp = mParent.getChildLayoutParams(this, host, width, height, left, right, top, bottom);
-    }
-    if (lp != null) {
-        host.setLayoutParams(lp);
-    }
-  }
-
-  private void setFixedHostLayoutParams(T host, int width, int height, int left, int right, int top, int bottom){
-    FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
-
-    params.width = width;
-    params.height = height;
-
-    this.setMarginsSupportRTL(params, left, top, right, bottom);
-
-    host.setLayoutParams(params);
-    mInstance.moveFixedView(host);
-
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("Weex_Fixed_Style", "WXComponent:setLayout :" + left + " " + top + " " + width + " " + height);
-      WXLogUtils.d("Weex_Fixed_Style", "WXComponent:setLayout Left:" + getStyles().getLeft() + " " + (int) getStyles().getTop());
-    }
-  }
-
-  protected void updateBoxShadow() {
-    if (!BoxShadowUtil.isBoxShadowEnabled()) {
-//      WXLogUtils.w("BoxShadow", "box-shadow disabled");
-      return;
-    }
-
-    if (getStyles() != null) {
-      Object boxShadow = getStyles().get(Constants.Name.BOX_SHADOW);
-      Object shadowQuality = getAttrs().get(Constants.Name.SHADOW_QUALITY);
-      if (boxShadow == null) {
-        return;
-      }
-
-      View target = mHost;
-      if (this instanceof WXVContainer) {
-        target = ((WXVContainer) this).getBoxShadowHost(false);
-      }
-
-      if (target == null) {
-        return;
-      }
-
-      float quality = WXUtils.getFloat(shadowQuality, 0.5f);
-      int viewPort = getInstance().getInstanceViewPortWidth();
-      String token = new StringBuilder(boxShadow.toString()).append(" / [")
-              .append(target.getMeasuredWidth()).append(",")
-              .append(target.getMeasuredHeight()).append("] / ")
-              .append(quality).toString();
-
-      if (mLastBoxShadowId != null && mLastBoxShadowId.equals(token)) {
-        WXLogUtils.d("BoxShadow", "box-shadow style was not modified. " + token);
-        return;
-      }
-
-      float[] radii = new float[]{0, 0, 0, 0, 0, 0, 0, 0};
-      WXStyle style = getStyles();
-      if (style != null) {
-        float tl = WXUtils.getFloat(style.get(Constants.Name.BORDER_TOP_LEFT_RADIUS), 0f);
-        radii[0] = tl;
-        radii[1] = tl;
-
-        float tr = WXUtils.getFloat(style.get(Constants.Name.BORDER_TOP_RIGHT_RADIUS), 0f);
-        radii[2] = tr;
-        radii[3] = tr;
-
-        float br = WXUtils.getFloat(style.get(Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS), 0f);
-        radii[4] = br;
-        radii[5] = br;
-
-        float bl = WXUtils.getFloat(style.get(Constants.Name.BORDER_BOTTOM_LEFT_RADIUS), 0f);
-        radii[6] = bl;
-        radii[7] = bl;
-
-        if (style.containsKey(Constants.Name.BORDER_RADIUS)) {
-          float radius = WXUtils.getFloat(style.get(Constants.Name.BORDER_RADIUS), 0f);
-          for (int i = 0; i < radii.length; i++) {
-            radii[i] = radius;
-          }
-        }
-      }
-
-      BoxShadowUtil.setBoxShadow(target, boxShadow.toString(), radii, viewPort, quality);
-      mLastBoxShadowId = token;
-    } else {
-      WXLogUtils.w("Can not resolve styles");
-    }
-  }
-
-  protected void clearBoxShadow() {
-    if (!BoxShadowUtil.isBoxShadowEnabled()) {
-//      WXLogUtils.w("BoxShadow", "box-shadow disabled");
-      return;
-    }
-
-    if (getStyles() != null) {
-      Object obj = getStyles().get(Constants.Name.BOX_SHADOW);
-      if (obj == null) {
-        return;
-      }
-    }
-
-    View target = mHost;
-    if (this instanceof WXVContainer) {
-      target = ((WXVContainer) this).getBoxShadowHost(true);
-    }
-
-    if (target != null && Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
-      ViewOverlay overlay = target.getOverlay();
-      if (overlay != null) {
-        overlay.clear();
-      }
-    }
-    mLastBoxShadowId = null;
-  }
-
-  /**
-   * After component's layout result is apply to view. May be invoke multiple times since
-   * DOM can be changed in js runtime.
-   */
-  protected void onFinishLayout() {
-    Object param = getStyles() != null ? getStyles().get(Constants.Name.BACKGROUND_IMAGE) : null;
-    if (param != null) {
-      setBackgroundImage(param.toString());
-    }
-  }
-
-  /**
-   * measure
-   */
-  protected MeasureOutput measure(int width, int height) {
-    MeasureOutput measureOutput = new MeasureOutput();
-
-    if (mFixedProp != 0) {
-      measureOutput.width = mFixedProp;
-      measureOutput.height = mFixedProp;
-    } else {
-      measureOutput.width = width;
-      measureOutput.height = height;
-    }
-    return measureOutput;
-  }
-
-  @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
-  protected void setAriaHidden(boolean isHidden) {
-    View host = getHostView();
-    if (host != null && Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
-      host.setImportantForAccessibility(isHidden ? View.IMPORTANT_FOR_ACCESSIBILITY_NO : View.IMPORTANT_FOR_ACCESSIBILITY_YES);
-    }
-  }
-
-  protected void setAriaLabel(String label) {
-    View host = getHostView();
-    if (host != null) {
-      host.setContentDescription(label);
-    }
-  }
-
-  protected void setRole(String roleKey) {
-    View host = getHostView();
-    String role = roleKey;
-    if (host != null && !TextUtils.isEmpty(roleKey)) {
-      IWXAccessibilityRoleAdapter roleAdapter = WXSDKManager.getInstance().getAccessibilityRoleAdapter();
-      if (roleAdapter != null) {
-        role = roleAdapter.getRole(roleKey);
-      }
-      final String finalRole = role;
-      AccessibilityDelegateCompat delegate = new AccessibilityDelegateCompat() {
-        @Override
-        public void onInitializeAccessibilityNodeInfo(View host, AccessibilityNodeInfoCompat info) {
-          try {
-            super.onInitializeAccessibilityNodeInfo(host, info);
-            info.setRoleDescription(finalRole);
-          } catch (Throwable e) {
-            WXLogUtils.e("SetRole failed!");
-          }
-        }
-      };
-      ViewCompat.setAccessibilityDelegate(host, delegate);
-    }
-  }
-
-  /**
-   * Avoid large size view fail in GPU-Animation.
-   *
-   * @param fixedSize
-   */
-  private void setFixedSize(String fixedSize) {
-    if (PROP_FS_MATCH_PARENT.equals(fixedSize)) {
-      mFixedProp = ViewGroup.LayoutParams.MATCH_PARENT;
-    } else if (PROP_FS_WRAP_CONTENT.equals(fixedSize)) {
-      mFixedProp = ViewGroup.LayoutParams.WRAP_CONTENT;
-    } else {
-      mFixedProp = 0;
-      return;
-    }
-    if (mHost != null) {
-      ViewGroup.LayoutParams layoutParams = mHost.getLayoutParams();
-      if (layoutParams != null) {
-        layoutParams.height = mFixedProp;
-        layoutParams.width = mFixedProp;
-        mHost.setLayoutParams(layoutParams);
-      }
-    }
-  }
-
-  /**
-   * Add new event to component,this will post a task to DOM thread to add event.
-   *
-   * @param type
-   */
-  protected void appendEventToDOM(String type) {
-//    WXSDKManager.getInstance().getWXDomManager().postAction(getInstanceId(), Actions.getAddEvent(getRef(), type), false);
-  }
-
-  public View getRealView() {
-    return mHost;
-  }
-
-  /**
-   * Judge whether need to set an onTouchListener.<br>
-   * As there is only one onTouchListener in each view, so all the gesture that use onTouchListener should put there.
-   *
-   * @param type eventType {@link com.taobao.weex.common.Constants.Event}
-   * @return true for set an onTouchListener, otherwise false
-   */
-  private boolean needGestureDetector(String type) {
-    if (mHost != null) {
-      for (WXGestureType gesture : WXGestureType.LowLevelGesture.values()) {
-        if (type.equals(gesture.toString())) {
-          return true;
-        }
-      }
-      for (WXGestureType gesture : WXGestureType.HighLevelGesture.values()) {
-        if (type.equals(gesture.toString())) {
-          return true;
-        }
-      }
-    }
-    if(WXGesture.isStopPropagation(type)){
-      return  true;
-    }
-    return false;
-  }
-
-  /**
-   * get Scroller components
-   */
-  public Scrollable getParentScroller() {
-    WXComponent component = this;
-    WXVContainer container;
-    Scrollable scroller;
-    for (; ; ) {
-      container = component.getParent();
-      if (container == null) {
-        return null;
-      }
-      if (container instanceof Scrollable) {
-        scroller = (Scrollable) container;
-        return scroller;
-      }
-      if (container.getRef().equals(ROOT)) {
-        return null;
-      }
-      component = container;
-    }
-  }
-
-  /**
-   * get Scroller components
-   */
-  @Nullable
-  public Scrollable getFirstScroller() {
-    if (this instanceof Scrollable) {
-      return (Scrollable) this;
-    }
-    return null;
-  }
-
-  public WXVContainer getParent() {
-    return mParent;
-  }
-
-  /**
-   * create view
-   */
-  public final void createView() {
-    if (!isLazy()) {
-      createViewImpl();
-    }
-  }
-
-  protected void createViewImpl() {
-    if (mContext != null) {
-      mHost = initComponentHostView(mContext);
-      if (mHost == null && !isVirtualComponent()) {
-        //compatible
-        initView();
-      }
-      if (mHost != null) {
-        if(mHost.getId() == View.NO_ID)
-          mHost.setId(WXViewUtils.generateViewId());
-        if(TextUtils.isEmpty(mHost.getContentDescription()) && WXEnvironment.isApkDebugable()){
-          mHost.setContentDescription(getRef());
-        }
-        ComponentObserver observer;
-        if ((observer = getInstance().getComponentObserver()) != null) {
-          observer.onViewCreated(this, mHost);
-        }
-      }
-      onHostViewInitialized(mHost);
-    } else {
-      WXLogUtils.e("createViewImpl", "Context is null");
-    }
-  }
-
-  /**
-   * Use {@link #initComponentHostView(Context context)} instead.
-   */
-  @Deprecated
-  protected void initView() {
-    if (mContext != null)
-      mHost = initComponentHostView(mContext);
-  }
-
-
-  /**
-   * Create corresponding view for this component.
-   *
-   * @param context
-   * @return
-   */
-  protected T initComponentHostView(@NonNull Context context) {
-    /**
-     * compatible old initView
-     */
-    return null;
-  }
-
-  /**
-   * Called after host view init. <br>
-   * Any overriding methods should invoke this method at the right time, to ensure the cached animation can be triggered correctly.
-   * (the animation will be cached when {@link #isLazy()} is true)
-   *
-   * @param host the host view
-   */
-  @CallSuper
-  protected void onHostViewInitialized(T host) {
-    if (mAnimationHolder != null) {
-//      Performs cached animation
-      mAnimationHolder.execute(mInstance, this);
-    }
-    setActiveTouchListener();
-  }
-
-  public T getHostView() {
-    return mHost;
-  }
-
-  /**
-   * use {@link #getHostView()} instead
-   *
-   * @return
-   */
-  @Deprecated
-  public View getView() {
-    return mHost;
-  }
-
-  public int getAbsoluteY() {
-    return mAbsoluteY;
-  }
-
-  public int getAbsoluteX() {
-    return mAbsoluteX;
-  }
-
-  public void removeEvent(String type) {
-    if (TextUtils.isEmpty(type)) {
-      return;
-    }
-
-    if (type.equals(Constants.Event.LAYEROVERFLOW))
-      removeLayerOverFlowListener(getRef());
-
-    if(getEvents() != null){
-      getEvents().remove(type);
-    }
-    if(mAppendEvents != null) {
-      mAppendEvents.remove(type);//only clean append events, not dom's events.
-    }
-    if(mGestureType != null){
-      mGestureType.remove(type);
-    }
-    removeEventFromView(type);
-  }
-
-  protected void removeEventFromView(String type) {
-    if (type.equals(Constants.Event.CLICK) && getRealView() != null && mHostClickListeners != null) {
-      if(mClickEventListener == null){
-        mClickEventListener = new OnClickListenerImp();
-      }
-      mHostClickListeners.remove(mClickEventListener);
-      //click event only remove from listener array
-    }
-    Scrollable scroller = getParentScroller();
-    if (type.equals(Constants.Event.APPEAR) && scroller != null) {
-      scroller.unbindAppearEvent(this);
-    }
-    if (type.equals(Constants.Event.DISAPPEAR) && scroller != null) {
-      scroller.unbindDisappearEvent(this);
-    }
-  }
-
-  public void removeAllEvent() {
-    if (getEvents().size() < 1) {
-      return;
-    }
-    WXEvent events = getEvents();
-    int size = events.size();
-    for (int i=0; i<size; i++) {
-      if(i >= events.size()){
-        break;
-      }
-      String event = events.get(i);
-      if (event == null) {
-        continue;
-      }
-      removeEventFromView(event);
-    }
-    if(mAppendEvents!=null) {
-      mAppendEvents.clear();//only clean append events, not dom's events.
-    }
-    if(mGestureType != null){
-      mGestureType.clear();
-    }
-    mGesture = null;
-    if (getRealView() != null &&
-            getRealView() instanceof WXGestureObservable) {
-      ((WXGestureObservable) getRealView()).registerGestureListener(null);
-    }
-    if (mHost != null) {
-      mHost.setOnFocusChangeListener(null);
-      if (mHostClickListeners != null && mHostClickListeners.size() > 0) {
-        mHostClickListeners.clear();
-        mHost.setOnClickListener(null);
-      }
-    }
-  }
-
-  public final void removeStickyStyle() {
-    if (isSticky()) {
-      Scrollable scroller = getParentScroller();
-      if (scroller != null) {
-        scroller.unbindStickStyle(this);
-      }
-    }
-  }
-
-  public boolean isSticky() {
-    return getStyles().isSticky();
-  }
-
-  public boolean isFixed() {
-    return getStyles().isFixed();
-  }
-
-  public void setDisabled(boolean disabled) {
-    mIsDisabled = disabled;
-    if (mHost == null) {
-      return;
-    }
-    mHost.setEnabled(!disabled);
-  }
-
-  public boolean isDisabled() {
-    return mIsDisabled;
-  }
-
-  public void setSticky(String sticky) {
-    if (!TextUtils.isEmpty(sticky) && sticky.equals(Constants.Value.STICKY)) {
-      Scrollable waScroller = getParentScroller();
-      if (waScroller != null) {
-        waScroller.bindStickStyle(this);
-      }
-    }
-  }
-
-  public void setBackgroundColor(String color) {
-    if (!TextUtils.isEmpty(color)) {
-      int colorInt = WXResourceUtils.getColor(color);
-      if (isRippleEnabled() && Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-        mRippleBackground = prepareBackgroundRipple();
-        if (mRippleBackground != null) {
-          if (mBackgroundDrawable == null) {
-            WXViewUtils.setBackGround(mHost, mRippleBackground, this);
-          } else {
-            LayerDrawable layerDrawable = new LayerDrawable(new Drawable[]{mRippleBackground, mBackgroundDrawable});
-            WXViewUtils.setBackGround(mHost, layerDrawable, this);
-          }
-          return;
-        }
-      }
-      if (!(colorInt == Color.TRANSPARENT && mBackgroundDrawable == null)) {
-        getOrCreateBorder().setColor(colorInt);
-      }
-    }
-  }
-
-  private Drawable prepareBackgroundRipple() {
-    try {
-      if (getStyles() != null && getStyles().getPesudoResetStyles() != null) {
-        Map<String, Object> resetStyles = getStyles().getPesudoResetStyles();
-
-        Object bgColor = resetStyles.get(Constants.Name.BACKGROUND_COLOR);
-        int colorInt = Color.TRANSPARENT;
-        if (bgColor != null) {
-          colorInt = WXResourceUtils.getColor(bgColor.toString(), Color.TRANSPARENT);
-          if (colorInt == Color.TRANSPARENT) {
-            return null;
-          }
-        }
-
-        Object bg = resetStyles.get(Constants.Name.BACKGROUND_COLOR + Constants.PSEUDO.ACTIVE);
-        if (bg == null) {
-          return null;
-        }
-        int rippleColor = WXResourceUtils.getColor(bg.toString(), colorInt);
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-          ColorStateList colorStateList = new ColorStateList(
-                  new int[][]{new int[]{}},
-                  new int[]{rippleColor});
-          return new RippleDrawable(colorStateList, new ColorDrawable(colorInt), null) {
-            @Override
-            @SuppressLint("CanvasSize")
-            public void draw(@NonNull Canvas canvas) {
-              if (mBackgroundDrawable != null) {
-                Path border = mBackgroundDrawable.getContentPath(new RectF(0, 0, canvas.getWidth(), canvas.getHeight()));
-                canvas.clipPath(border);
-              }
-              super.draw(canvas);
-            }
-          };
-        }
-      }
-    } catch (Throwable t) {
-      WXLogUtils.w("Exception on create ripple: ", t);
-    }
-    return null;
-  }
-
-  public void setBackgroundImage(@NonNull String bgImage) {
-    if ("".equals(bgImage.trim())) {
-      getOrCreateBorder().setImage(null);
-    } else {
-      Shader shader = WXResourceUtils.getShader(bgImage, getLayoutSize().getWidth(), getLayoutSize().getHeight());
-      getOrCreateBorder().setImage(shader);
-    }
-  }
-  private boolean shouldCancelHardwareAccelerate() {
-    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
-    boolean cancel_hardware_accelerate = true;
-    if (adapter != null) {
-      try {
-        cancel_hardware_accelerate = Boolean.parseBoolean(adapter
-                .getConfig("android_weex_test_gpu",
-                        "cancel_hardware_accelerate",
-                        "true"));
-      }catch (Exception e){
-        WXLogUtils.e(WXLogUtils.getStackTrace(e));
-      }
-      WXLogUtils.i("cancel_hardware_accelerate : " + cancel_hardware_accelerate);
-    }
-    return cancel_hardware_accelerate;
-  }
-
-  public void setOpacity(float opacity) {
-    if (opacity >= 0 && opacity <= 1 && mHost.getAlpha() != opacity) {
-      int limit = WXRenderManager.getOpenGLRenderLimitValue();
-      if (isLayerTypeEnabled()) {
-        mHost.setLayerType(View.LAYER_TYPE_HARDWARE, null);
-      }
-      if(isLayerTypeEnabled() && shouldCancelHardwareAccelerate() && limit > 0 && (getLayoutHeight() > limit ||
-              getLayoutWidth() > limit)){
-        mHost.setLayerType(View.LAYER_TYPE_NONE,null);
-      }
-      mHost.setAlpha(opacity);
-    }
-  }
-
-  public void setBorderRadius(String key, float borderRadius) {
-    if (borderRadius >= 0) {
-      switch (key) {
-        case Constants.Name.BORDER_RADIUS:
-          getOrCreateBorder().setBorderRadius(
-              CORNER.ALL, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
-          break;
-        case Constants.Name.BORDER_TOP_LEFT_RADIUS:
-          getOrCreateBorder().setBorderRadius(CORNER.BORDER_TOP_LEFT, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
-          break;
-        case Constants.Name.BORDER_TOP_RIGHT_RADIUS:
-          getOrCreateBorder().setBorderRadius(CORNER.BORDER_TOP_RIGHT, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
-          break;
-        case Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS:
-          getOrCreateBorder().setBorderRadius(CORNER.BORDER_BOTTOM_RIGHT, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
-          break;
-        case Constants.Name.BORDER_BOTTOM_LEFT_RADIUS:
-          getOrCreateBorder().setBorderRadius(CORNER.BORDER_BOTTOM_LEFT, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
-          break;
-      }
-    }
-  }
-
-  public void setBorderWidth(String key, float borderWidth) {
-    if (borderWidth >= 0) {
-      switch (key) {
-        case Constants.Name.BORDER_WIDTH:
-          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.ALL, borderWidth);
-          break;
-        case Constants.Name.BORDER_TOP_WIDTH:
-          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.TOP, borderWidth);
-          break;
-        case Constants.Name.BORDER_RIGHT_WIDTH:
-          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.RIGHT, borderWidth);
-          break;
-        case Constants.Name.BORDER_BOTTOM_WIDTH:
-          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.BOTTOM, borderWidth);
-          break;
-        case Constants.Name.BORDER_LEFT_WIDTH:
-          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.LEFT, borderWidth);
-          break;
-        default:
-          break;
-      }
-    }
-  }
-
-  public void setBorderStyle(String key, String borderStyle) {
-    if (!TextUtils.isEmpty(borderStyle)) {
-      switch (key) {
-        case Constants.Name.BORDER_STYLE:
-          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.ALL, borderStyle);
-          break;
-        case Constants.Name.BORDER_RIGHT_STYLE:
-          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.RIGHT, borderStyle);
-          break;
-        case Constants.Name.BORDER_BOTTOM_STYLE:
-          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.BOTTOM, borderStyle);
-          break;
-        case Constants.Name.BORDER_LEFT_STYLE:
-          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.LEFT, borderStyle);
-          break;
-        case Constants.Name.BORDER_TOP_STYLE:
-          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.TOP, borderStyle);
-          break;
-      }
-    }
-  }
-
-  public void setBorderColor(String key, String borderColor) {
-    if (!TextUtils.isEmpty(borderColor)) {
-      int colorInt = WXResourceUtils.getColor(borderColor);
-      if (colorInt != Integer.MIN_VALUE) {
-        switch (key) {
-          case Constants.Name.BORDER_COLOR:
-            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.ALL, colorInt);
-            break;
-          case Constants.Name.BORDER_TOP_COLOR:
-            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.TOP, colorInt);
-            break;
-          case Constants.Name.BORDER_RIGHT_COLOR:
-            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.RIGHT, colorInt);
-            break;
-          case Constants.Name.BORDER_BOTTOM_COLOR:
-            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.BOTTOM, colorInt);
-            break;
-          case Constants.Name.BORDER_LEFT_COLOR:
-            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.LEFT, colorInt);
-            break;
-        }
-      }
-    }
-  }
-
-  public
-  @Nullable
-  String getVisibility() {
-    try {
-      return (String) getStyles().get(Constants.Name.VISIBILITY);
-    } catch (Exception e) {
-      return Constants.Value.VISIBLE;
-    }
-  }
-
-  public void setVisibility(String visibility) {
-    View view;
-    if ((view = getRealView()) != null) {
-      if (TextUtils.equals(visibility, Constants.Value.VISIBLE)) {
-        view.setVisibility(View.VISIBLE);
-      } else if (TextUtils.equals(visibility, Constants.Value.HIDDEN)) {
-        view.setVisibility(View.GONE);
-      }
-    }
-  }
-
-  /**
-   * This is an experimental feature for elevation of material design.
-   */
-  private void updateElevation() {
-    float elevation = getAttrs().getElevation(getInstance().getInstanceViewPortWidth());
-    if (!Float.isNaN(elevation)) {
-      ViewCompat.setElevation(getHostView(), elevation);
-    }
-  }
-
-  @Deprecated
-  public void registerActivityStateListener() {
-
-  }
-
-
-  /********************************
-   *  begin hook Activity life cycle callback
-   ********************************************************/
-  public void onActivityCreate() {
-
-  }
-
-  public void onActivityStart() {
-
-  }
-
-  public void onActivityPause() {
-
-  }
-
-  public void onActivityResume() {
-
-  }
-
-  public void onActivityStop() {
-
-  }
-
-  public void onActivityDestroy() {
-
-  }
-
-  public boolean onActivityBack() {
-    return false;
-  }
-
-  public void onActivityResult(int requestCode, int resultCode, Intent data) {
-
-  }
-
-  public boolean onCreateOptionsMenu(Menu menu) {
-    return false;
-  }
-
-  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
-
-  }
-
-  /********************************
-   *  end hook Activity life cycle callback
-   ********************************************************/
-  public void recycled() {
-    if (isFixed())
-      return;
-    clearBoxShadow();
-  }
-
-  public void destroy() {
-    ComponentObserver observer;
-    if ((observer = getInstance().getComponentObserver()) != null) {
-      observer.onPreDestory(this);
-    }
-
-    if (WXEnvironment.isApkDebugable() && !WXUtils.isUiThread()) {
-      throw new WXRuntimeException("[WXComponent] destroy can only be called in main thread");
-    }
-    if (mHost != null && mHost.getLayerType() == View.LAYER_TYPE_HARDWARE && isLayerTypeEnabled()) {
-      mHost.setLayerType(View.LAYER_TYPE_NONE, null);
-    }
-    removeAllEvent();
-    removeStickyStyle();
-
-    View view;
-    if (isFixed() && (view = getHostView()) != null) {
-      getInstance().removeFixedView(view);
-    }
-
-    if(contentBoxMeasurement!=null){
-      contentBoxMeasurement.destroy();
-      contentBoxMeasurement = null;
-    }
-    mIsDestroyed = true;
-    if(animations!=null) {
-      animations.clear();
-    }
-  }
-
-  public boolean isDestoryed() {
-    return mIsDestroyed;
-  }
-
-  /**
-   * Detach view from its component. Components,
-   * which have difference between getHostView and getRealView or have temp calculation results,
-   * must<strong> override</strong>  this method with their own implementation.
-   *
-   * @return the original View
-   */
-  public View detachViewAndClearPreInfo() {
-    View original = mHost;
-    mPreRealLeft = 0;
-    mPreRealRight = 0;
-    mPreRealWidth = 0;
-    mPreRealHeight = 0;
-    mPreRealTop = 0;
-//    mHost = null;
-    return original;
-  }
-
-  public void clearPreLayout() {
-    mPreRealLeft = 0;
-    mPreRealRight = 0;
-    mPreRealWidth = 0;
-    mPreRealHeight = 0;
-    mPreRealTop = 0;
-  }
-
-  /**
-   * This method computes user visible left-top point in view's coordinate.
-   * The default implementation uses the scrollX and scrollY of the view as the result,
-   * and put the value in the parameter pointer.
-   * Components with different computation algorithm
-   * <strong> should override </strong> this method.
-   *
-   * @param pointF the user visible left-top point in view's coordinate.
-   */
-  public void computeVisiblePointInViewCoordinate(PointF pointF) {
-    View view = getRealView();
-    pointF.set(view.getScrollX(), view.getScrollY());
-  }
-
-  public boolean containsGesture(WXGestureType WXGestureType) {
-    return mGestureType != null && mGestureType.contains(WXGestureType.toString());
-  }
-
-  public boolean containsEvent(String event) {
-    return getEvents().contains(event) || (mAppendEvents!=null && mAppendEvents.contains(event));
-  }
-
-  public void notifyAppearStateChange(String wxEventType, String direction) {
-    if (containsEvent(Constants.Event.APPEAR) || containsEvent(Constants.Event.DISAPPEAR)) {
-      Map<String, Object> params = new HashMap<>();
-      params.put("direction", direction);
-      fireEvent(wxEventType, params);
-    }
-  }
-
-  public boolean isUsing() {
-    return isUsing;
-  }
-
-  public void setUsing(boolean using) {
-    isUsing = using;
-  }
-
-  public void readyToRender() {
-    if (mParent != null && getInstance().isTrackComponent()) {
-      mParent.readyToRender();
-    }
-  }
-
-  public static class MeasureOutput {
-    public int width;
-    public int height;
-  }
-
-  /**
-   * Determine whether the current component needs to be placed in the real View tree
-   *
-   * @return false component add subview
-   */
-  public boolean isVirtualComponent() {
-    return mType == TYPE_VIRTUAL;
-  }
-
-  public void removeVirtualComponent() {
-  }
-
-  public int getType() {
-    return mType;
-  }
-
-  public boolean hasScrollParent(WXComponent component) {
-    if (component.getParent() == null) {
-      return true;
-    } else if (component.getParent() instanceof WXScroller) {
-      return false;
-    } else {
-      return hasScrollParent(component.getParent());
-    }
-  }
-
-  /**
-   * Called when property has empty value
-   *
-   * @param propName
-   */
-  @CheckResult
-  protected Object convertEmptyProperty(String propName, Object originalValue) {
-    switch (propName) {
-      case Constants.Name.BACKGROUND_COLOR:
-        return "transparent";
-      case Constants.Name.BORDER_RADIUS:
-      case Constants.Name.BORDER_BOTTOM_LEFT_RADIUS:
-      case Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS:
-      case Constants.Name.BORDER_TOP_LEFT_RADIUS:
-      case Constants.Name.BORDER_TOP_RIGHT_RADIUS:
-        return 0;
-      case Constants.Name.BORDER_WIDTH:
-      case Constants.Name.BORDER_TOP_WIDTH:
-      case Constants.Name.BORDER_LEFT_WIDTH:
-      case Constants.Name.BORDER_RIGHT_WIDTH:
-      case Constants.Name.BORDER_BOTTOM_WIDTH:
-        return 0;
-      case Constants.Name.BORDER_COLOR:
-      case Constants.Name.BORDER_TOP_COLOR:
-      case Constants.Name.BORDER_LEFT_COLOR:
-      case Constants.Name.BORDER_RIGHT_COLOR:
-      case Constants.Name.BORDER_BOTTOM_COLOR:
-        return "black";
-    }
-    return originalValue;
-  }
-
-  private void setActiveTouchListener() {
-    boolean hasActivePesudo = getStyles().getPesudoStyles().containsKey(Constants.PSEUDO.ACTIVE);
-    View view;
-    if (hasActivePesudo && (view = getRealView()) != null) {
-      boolean hasTouchConsumer = isConsumeTouch();
-      view.setOnTouchListener(new TouchActivePseudoListener(this, !hasTouchConsumer));
-    }
-  }
-
-  protected boolean isConsumeTouch() {
-    return (mHostClickListeners != null && mHostClickListeners.size() > 0) || mGesture != null;
-  }
-
-  @Override
-  public void updateActivePseudo(boolean isSet) {
-    setPseudoClassStatus(Constants.PSEUDO.ACTIVE, isSet);
-  }
-
-  /**
-   * @param clzName like ':active' or ':active:enabled'
-   * @param status
-   */
-  protected void setPseudoClassStatus(String clzName, boolean status) {
-    WXStyle styles = getStyles();
-    Map<String, Map<String, Object>> pesudoStyles = styles.getPesudoStyles();
-
-    if (pesudoStyles == null || pesudoStyles.size() == 0) {
-      return;
-    }
-    if(mPesudoStatus == null){
-      mPesudoStatus = new PesudoStatus();
-    }
-    Map<String, Object> resultStyles = mPesudoStatus.updateStatusAndGetUpdateStyles(
-            clzName,
-            status,
-            pesudoStyles,
-            styles.getPesudoResetStyles());
-
-    if (null != resultStyles) {
-      if (status) {
-        mPseudoResetGraphicSize = new GraphicSize(getLayoutSize().getWidth(), getLayoutSize().getHeight());
-        if (resultStyles.keySet().contains(Constants.Name.WIDTH)) {
-          getLayoutSize().setWidth(WXViewUtils.getRealPxByWidth(WXUtils.parseFloat(styles.getPesudoResetStyles().get(Constants.Name.WIDTH + Constants.PSEUDO.ACTIVE)), getViewPortWidth()));
-        } else if (resultStyles.keySet().contains(Constants.Name.HEIGHT)){
-          getLayoutSize().setHeight(WXViewUtils.getRealPxByWidth(WXUtils.parseFloat(styles.getPesudoResetStyles().get(Constants.Name.HEIGHT + Constants.PSEUDO.ACTIVE)), getViewPortWidth()));
-        }
-      } else {
-        if (null != mPseudoResetGraphicSize) {
-          setLayoutSize(mPseudoResetGraphicSize);
-        }
-      }
-    }
-
-    updateStyleByPesudo(resultStyles);
-  }
-
-  private void updateStyleByPesudo(Map<String, Object> styles) {
-    new GraphicActionUpdateStyle(getInstance(), getRef(), styles, getPadding(), getMargin(), getBorder(), true)
-            .executeActionOnRender();
-    if (getLayoutWidth() == 0 && getLayoutWidth() == 0) {
-    } else {
-      WXBridgeManager.getInstance().setStyleWidth(getInstanceId(), getRef(), getLayoutWidth());
-      WXBridgeManager.getInstance().setStyleHeight(getInstanceId(), getRef(), getLayoutHeight());
-//      WXBridgeManager.getInstance().calculateLayout(getInstanceId(), getRef(), false);
-    }
-  }
-
-  public int getStickyOffset() {
-    return mStickyOffset;
-  }
-
-  public boolean canRecycled() {
-    return (!isFixed() || !isSticky()) && getAttrs().canRecycled();
-  }
-
-  /**
-   * Sets the offset for the sticky
-   *
-   * @param stickyOffset child[y]-parent[y]
-   */
-  public void setStickyOffset(int stickyOffset) {
-    mStickyOffset = stickyOffset;
-  }
-
-  /**
-   * For now, this method respect the result of {@link WXSDKInstance#isLayerTypeEnabled()}
-   *
-   * @return Refer {@link WXSDKInstance#isLayerTypeEnabled()}
-   */
-  public boolean isLayerTypeEnabled() {
-    return getInstance().isLayerTypeEnabled();
-  }
-
-  /**
-   * Sets whether or not to relayout page during animation, default is false
-   */
-  public void setNeedLayoutOnAnimation(boolean need) {
-    this.mNeedLayoutOnAnimation = need;
-  }
-
-  /**
-   * Trigger a updateStyles invoke to relayout current page
-   */
-  public void notifyNativeSizeChanged(int w, int h) {
-    if (!mNeedLayoutOnAnimation) {
-      return;
-    }
-
-    final WXBridgeManager manager = WXBridgeManager.getInstance();
-    manager.setStyleWidth(getInstanceId(), getRef(), w);
-    manager.setStyleHeight(getInstanceId(), getRef(), h);
-  }
-
-  public static final int STATE_DOM_FINISH = 0;
-  public static final int STATE_UI_FINISH = 1;
-  public static final int STATE_ALL_FINISH = 2;
-  @IntDef({STATE_DOM_FINISH, STATE_UI_FINISH, STATE_ALL_FINISH})
-  @Retention(RetentionPolicy.SOURCE)
-  @Target(ElementType.PARAMETER)
-  public @interface RenderState {
-  }
-
-  @CallSuper
-  public void onRenderFinish(@RenderState int state) {
-    if (WXTracing.isAvailable()) {
-      double uiTime = Stopwatch.nanosToMillis(mTraceInfo.uiThreadNanos);
-      if (state == STATE_ALL_FINISH || state == STATE_DOM_FINISH) {
-        WXTracing.TraceEvent domEvent = WXTracing.newEvent("DomExecute", getInstanceId(), mTraceInfo.rootEventId);
-        domEvent.ph = "X";
-        domEvent.ts = mTraceInfo.domThreadStart;
-        domEvent.tname = "DOMThread";
-        domEvent.name = getComponentType();
-        domEvent.classname = getClass().getSimpleName();
-        if (getParent() != null) {
-          domEvent.parentRef = getParent().getRef();
-        }
-        domEvent.submit();
-      }
-
-      if (state == STATE_ALL_FINISH || state == STATE_UI_FINISH) {
-        if (mTraceInfo.uiThreadStart != -1) {
-          WXTracing.TraceEvent uiEvent = WXTracing.newEvent("UIExecute", getInstanceId(), mTraceInfo.rootEventId);
-          uiEvent.ph = "X";
-          uiEvent.duration = uiTime;
-          uiEvent.ts = mTraceInfo.uiThreadStart;
-          uiEvent.name = getComponentType();
-          uiEvent.classname = getClass().getSimpleName();
-          if (getParent() != null) {
-            uiEvent.parentRef = getParent().getRef();
-          }
-          uiEvent.submit();
-        } else {
-          if (WXEnvironment.isApkDebugable() && !isLazy()) {
-//            WXLogUtils.w("onRenderFinish", "createView() not called");
-          }
-        }
-      }
-    }
-  }
-
-  protected boolean isRippleEnabled() {
-    try {
-      Object obj = getAttrs().get(Constants.Name.RIPPLE_ENABLED);
-      return WXUtils.getBoolean(obj, false);
-    } catch (Throwable t) {
-      //ignore
-    }
-    return false;
-  }
-
-  public boolean isWaste() {
-    return waste;
-  }
-
-  /**
-   * mark node waste,
-   * if node is waster should hidden, and dom tree should allow not show
-   * */
-  public void setWaste(boolean waste) {
-    if(this.waste != waste){
-      this.waste = waste;
-      if(!WXBasicComponentType.RECYCLE_LIST.equals(getParent().getComponentType())){
-          NativeRenderObjectUtils.nativeRenderObjectChildWaste(getRenderObjectPtr(), waste);
-      }
-
-     if(waste){
-        //update dom not show, and put style to hidden
-        getStyles().put(Constants.Name.VISIBILITY, Constants.Value.HIDDEN);
-        //if component not init, mark lazy init when use, reduce view count
-        if(getHostView() == null){
-          if(!mLazy){
-            lazy(true);
-          }
-        }else{
-          getHostView().setVisibility(View.GONE);
-        }
-      }else{
-       getStyles().put(Constants.Name.VISIBILITY, Constants.Value.VISIBLE);
-        if(getHostView() == null){
-          if(mLazy) { // when parent is lazy just mark node lazy false
-            if(mParent != null && mParent.isLazy()){
-              lazy(false);
-            }else{
-              Statements.initLazyComponent(this, mParent);
-            }
-          }
-        }else{
-          getHostView().setVisibility(View.VISIBLE);
-        }
-      }
-    }
-  }
-
-
-  /** component uniquie key id in native for recycle-list,
-   *  should be unique for every native component differ with ref
-   *  */
-  public  String getViewTreeKey(){
-    if(mViewTreeKey == null){
-      if(getParent() == null){
-        mViewTreeKey = hashCode() + "_" + getRef();
-      }else{
-        mViewTreeKey = hashCode() + "_" + getRef() + "_" + getParent().indexOf(this);
-      }
-    }
-    return mViewTreeKey;
-  }
-
-  private String mViewTreeKey;
-
-  public WXTransition getTransition() {
-    return mTransition;
-  }
-
-  public void setTransition(WXTransition transition) {
-    this.mTransition = transition;
-  }
-
-  public void addAnimationForElement(Map<String, Object> animMap) {
-    if(animMap!=null && !animMap.isEmpty()){
-      if(animations == null){
-        animations = new ConcurrentLinkedQueue<>();
-      }
-      animations.add(new Pair<>(getRef(),animMap));
-    }
-  }
-
-  private void parseAnimation() {
-    if (null == animations) {
-      return;
-    }
-    for (final Pair<String, Map<String, Object>> pair : animations) {
-      if (!TextUtils.isEmpty(pair.first)) {
-        final WXAnimationBean animationBean = createAnimationBean(pair.first, pair.second);
-        if (animationBean != null) {
-          GraphicActionAnimation action = new GraphicActionAnimation(getInstance(), getRef(), animationBean);
-          action.executeAction();
-        }
-      }
-    }
-    animations.clear();
-  }
-
-
-  private WXAnimationBean createAnimationBean(String ref,Map<String, Object> style){
-    if (style != null) {
-      try {
-        Object transform = style.get(Constants.Name.TRANSFORM);
-        if (transform instanceof String && !TextUtils.isEmpty((String) transform)) {
-          String transformOrigin = (String) style.get(Constants.Name.TRANSFORM_ORIGIN);
-          WXAnimationBean animationBean = new WXAnimationBean();
-          int width = (int) getLayoutWidth();
-          int height = (int) getLayoutHeight();
-          animationBean.styles = new WXAnimationBean.Style();
-          animationBean.styles.init(transformOrigin, (String) transform, width, height,WXSDKManager.getInstanceViewPortWidth(getInstanceId()),
-                  getInstance());
-          return animationBean;
-        }
-      }catch (RuntimeException e){
-        WXLogUtils.e("", e);
-        return null;
-      }
-    }
-    return null;
-  }
-
-  /**
-   * node is lazy
-   * */
-  private boolean mLazy = false;
-
-  /***/
-  public void lazy(boolean lazy) {
-    mLazy = lazy;
-  }
-
-  public long getRenderObjectPtr(){
-    if(getBasicComponentData().isRenderPtrEmpty()){
-      getBasicComponentData().setRenderObjectPr(NativeRenderObjectUtils.nativeGetRenderObject(getInstanceId(), getRef()));
-    }
-    return getBasicComponentData().getRenderObjectPr();
-  }
-
-
-  public void updateNativeAttr(String key, Object value){
-    if(key == null){
-      return;
-    }
-    if(value == null){
-      value  = "";
-    }
-    getBasicComponentData().getAttrs().put(key, value);
-    NativeRenderObjectUtils.nativeUpdateRenderObjectAttr(getRenderObjectPtr(), key, value.toString());
-  }
-
-  public  void  nativeUpdateAttrs(Map<String, Object> dynamic){
-    Set<Map.Entry<String, Object>> entries = dynamic.entrySet();
-    /**
-     * diff attrs, see attrs has update, remove none update attrs
-     * */
-    Iterator<Map.Entry<String, Object>> iterator = entries.iterator();
-    while (iterator.hasNext()){
-      Map.Entry<String, Object> objectEntry = iterator.next();
-      if(objectEntry.getKey() == null){
-        continue;
-      }
-      updateNativeAttr(objectEntry.getKey(), objectEntry.getValue());
-    }
-  }
-
-
-  public void updateNativeStyle(String key, Object value){
-    if(key == null){
-      return;
-    }
-    if(value == null){
-      value  = "";
-    }
-    getBasicComponentData().getStyles().put(key, value);
-    NativeRenderObjectUtils.nativeUpdateRenderObjectStyle(getRenderObjectPtr(), key, value.toString());
-  }
-
-  public  void  updateNativeStyles(Map<String, Object> dynamic){
-    Set<Map.Entry<String, Object>> entries = dynamic.entrySet();
-    /**
-     * diff attrs, see attrs has update, remove none update attrs
-     * */
-    Iterator<Map.Entry<String, Object>> iterator = entries.iterator();
-    while (iterator.hasNext()){
-      Map.Entry<String, Object> objectEntry = iterator.next();
-      if(objectEntry.getKey() == null){
-        continue;
-      }
-      updateNativeStyle(objectEntry.getKey(), objectEntry.getValue());
-    }
-  }
-
-  public void addLayerOverFlowListener(String ref) {
-    if (getInstance() != null)
-      getInstance().addLayerOverFlowListener(ref);
-  }
-
-  public void removeLayerOverFlowListener(String ref) {
-    if (getInstance() != null)
-      getInstance().removeLayerOverFlowListener(ref);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponentFactory.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponentFactory.java
deleted file mode 100644
index ce3b986..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponentFactory.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.text.TextUtils;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.ui.IFComponentHolder;
-import com.taobao.weex.ui.WXComponentRegistry;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Map;
-import java.util.Set;
-
-/**
- * Component factory
- */
-public class WXComponentFactory {
-
-  public static WXComponent newInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    if (instance == null || TextUtils.isEmpty(basicComponentData.mComponentType)) {
-      return null;
-    }
-
-    IFComponentHolder holder = WXComponentRegistry.getComponent(basicComponentData.mComponentType);
-    if (holder == null) {
-      if (WXEnvironment.isApkDebugable()) {
-        String tag = "WXComponentFactory error type:[" +
-                basicComponentData.mComponentType + "]" + " class not found";
-        WXLogUtils.e(tag);
-      }
-      //For compatible reason of JS framework, unregistered type will be treated as container.
-      holder = WXComponentRegistry.getComponent(WXBasicComponentType.CONTAINER);
-      if (holder == null) {
-        WXExceptionUtils.commitCriticalExceptionRT(instance.getInstanceId(),
-                WXErrorCode.WX_RENDER_ERR_COMPONENT_NOT_REGISTER, "createComponent",
-                basicComponentData.mComponentType + " not registered", null);
-        return null;
-      }
-    }
-
-    try {
-      return holder.createInstance(instance, parent, basicComponentData);
-    } catch (Throwable e) {
-      WXLogUtils.e("WXComponentFactory Exception type:[" + basicComponentData.mComponentType + "] ", e);
-    }
-
-    return null;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponentProp.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponentProp.java
deleted file mode 100644
index 65b9b51..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXComponentProp.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-
-@Retention(RetentionPolicy.RUNTIME)
-@Target(ElementType.METHOD)
-public @interface WXComponentProp {
-
-  String name();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXDiv.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXDiv.java
deleted file mode 100644
index c4fbbab..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXDiv.java
+++ /dev/null
@@ -1,126 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-import android.util.Log;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.flat.FlatComponent;
-import com.taobao.weex.ui.flat.WidgetContainer;
-import com.taobao.weex.ui.flat.widget.WidgetGroup;
-import com.taobao.weex.ui.view.WXFrameLayout;
-import com.taobao.weex.utils.WXUtils;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.LinkedList;
-
-/**
- * div component
- */
-@Component(lazyload = false)
-public class WXDiv extends WidgetContainer<WXFrameLayout> implements FlatComponent<WidgetGroup> {
-
-  private WidgetGroup mWidgetGroup;
-
-  public static class Ceator implements ComponentCreator {
-    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-      return new WXDiv(instance, parent, basicComponentData);
-    }
-  }
-
-  @Deprecated
-  public WXDiv(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, basicComponentData);
-  }
-
-  public WXDiv(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  @Override
-  protected WXFrameLayout initComponentHostView(@NonNull Context context) {
-    WXFrameLayout frameLayout = new WXFrameLayout(context);
-    frameLayout.holdComponent(this);
-    return frameLayout;
-  }
-
-  @Override
-  public boolean promoteToView(boolean checkAncestor) {
-    if (null != getInstance().getFlatUIContext()) {
-      return !intendToBeFlatContainer() ||
-            getInstance().getFlatUIContext().promoteToView(this, checkAncestor, WXDiv.class);
-    }
-    return false;
-  }
-
-  /**
-   * Create View tree there. Either this method or {@link #createViewImpl()} get called.
-   * If this object will be promoted to view, then getOrCreateFlatWidget() should never be called.
-   */
-  @Override
-  @NonNull
-  public WidgetGroup getOrCreateFlatWidget() {
-    if (mWidgetGroup == null) {
-      mWidgetGroup = new WidgetGroup(getInstance().getFlatUIContext());
-      for (int i = 0; i < getChildCount(); i++) {
-        createChildViewAt(i);
-      }
-      mountFlatGUI();
-    }
-    return mWidgetGroup;
-  }
-
-  @Override
-  protected void mountFlatGUI() {
-    if(widgets == null){
-      widgets = new LinkedList<>();
-    }
-    if (promoteToView(true)) {
-      if(getHostView()!=null) {
-        getHostView().mountFlatGUI(widgets);
-      }
-    } else {
-      mWidgetGroup.replaceAll(widgets);
-    }
-  }
-
-  @Override
-  public void unmountFlatGUI() {
-    if (getHostView() != null) {
-      getHostView().unmountFlatGUI();
-    }
-  }
-
-  @Override
-  public boolean intendToBeFlatContainer() {
-    return getInstance().getFlatUIContext().isFlatUIEnabled(this) && WXDiv.class.equals(getClass());
-  }
-
-  @Override
-  public boolean isVirtualComponent() {
-    return !promoteToView(true);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXEmbed.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXEmbed.java
deleted file mode 100644
index b95c8a0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXEmbed.java
+++ /dev/null
@@ -1,644 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.annotation.SuppressLint;
-import android.text.TextUtils;
-import android.view.Gravity;
-import android.view.View;
-import android.view.ViewGroup;
-import android.webkit.WebView;
-import android.widget.FrameLayout;
-import android.widget.ImageView;
-
-import com.taobao.weex.R;
-import com.taobao.weex.IWXRenderListener;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.OnWXScrollListener;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.instance.InstanceOnFireEventInterceptor;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.ArrayDeque;
-import java.util.Comparator;
-import java.util.Map;
-import java.util.PriorityQueue;
-import java.util.Queue;
-
-@Component(lazyload = false)
-public class WXEmbed extends WXDiv implements WXSDKInstance.OnInstanceVisibleListener,NestedContainer {
-
-  public static final  String STRATEGY_NONE =  "none";
-  public static final  String STRATEGY_NORMAL =  "normal";
-  public static final  String STRATEGY_HIGH =  "high";
-
-
-  public static final  String PRIORITY_LOW =  "low";
-  public static final  String PRIORITY_NORMAL =  "normal";
-  public static final  String PRIORITY_HIGH =  "high";
-
-  public static final String ITEM_ID = "itemId";
-
-  private String src;
-  protected WXSDKInstance mNestedInstance;
-  private static int ERROR_IMG_WIDTH = (int) WXViewUtils.getRealPxByWidth(270,750);
-  private static int ERROR_IMG_HEIGHT = (int) WXViewUtils.getRealPxByWidth(260,750);
-
-  private boolean mIsVisible = true;
-  private EmbedRenderListener mListener;
-  private EmbedInstanceOnScrollFireEventInterceptor mInstanceOnScrollFireEventInterceptor;
-
-
-  private String priority = PRIORITY_NORMAL;
-
-  private String strategy = "normal";  //none, normal, high(ignore priority)
-
-  private long hiddenTime;
-
-
-
-  public interface EmbedManager {
-    WXEmbed getEmbed(String itemId);
-    void putEmbed(String itemId,WXEmbed comp);
-  }
-
-  public static class FailToH5Listener extends ClickToReloadListener {
-    @SuppressLint("SetJavaScriptEnabled")
-    @Override
-    public void onException(NestedContainer comp, String errCode, String msg) {
-      //downgrade embed
-      if( errCode != null && comp instanceof WXEmbed && errCode.startsWith("1|")) {
-        ViewGroup container = comp.getViewContainer();
-        WebView webView = new WebView(container.getContext());
-        ViewGroup.LayoutParams params = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
-        webView.setLayoutParams(params);
-        webView.getSettings().setJavaScriptEnabled(true);
-
-        //WebView Remote Code Execution Vulnerability
-        webView.removeJavascriptInterface("searchBoxJavaBridge_");
-        webView.removeJavascriptInterface("accessibility");
-        webView.removeJavascriptInterface("accessibilityTraversal");
-        webView.getSettings().setSavePassword(false);
-
-        container.removeAllViews();
-        container.addView(webView);
-        webView.loadUrl(((WXEmbed) comp).src);
-      }else{
-        super.onException(comp,errCode,msg);
-      }
-    }
-  }
-
-  /**
-   * Default event listener.
-   */
-  public static class ClickToReloadListener implements OnNestedInstanceEventListener {
-    @Override
-    public void onException(NestedContainer container, String errCode, String msg) {
-      if (TextUtils.equals(errCode, WXErrorCode.
-              WX_DEGRAD_ERR_NETWORK_BUNDLE_DOWNLOAD_FAILED.getErrorCode()) && container instanceof WXEmbed) {
-        final WXEmbed comp = ((WXEmbed)container);
-        final ImageView imageView = new ImageView(comp.getContext());
-        imageView.setImageResource(R.drawable.weex_error);
-        FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(ERROR_IMG_WIDTH, ERROR_IMG_HEIGHT);
-        layoutParams.gravity = Gravity.CENTER;
-        imageView.setLayoutParams(layoutParams);
-        imageView.setScaleType(ImageView.ScaleType.FIT_XY);
-        imageView.setAdjustViewBounds(true);
-        imageView.setOnClickListener(new View.OnClickListener() {
-          @Override
-          public void onClick(View v) {
-            imageView.setOnClickListener(null);
-            imageView.setEnabled(false);
-            comp.loadContent();
-          }
-        });
-        FrameLayout hostView = comp.getHostView();
-        hostView.removeAllViews();
-        hostView.addView(imageView);
-        WXLogUtils.e("WXEmbed", "NetWork failure :" + errCode + ",\n error message :" + msg);
-      }
-    }
-
-    @Override
-    public boolean onPreCreate(NestedContainer comp, String src) {
-      return true;
-    }
-
-    @Override
-    public String transformUrl(String origin) {
-      return origin;
-    }
-
-    @Override
-    public void onCreated(NestedContainer comp, WXSDKInstance nestedInstance) {
-
-    }
-  }
-
-  static class EmbedRenderListener implements IWXRenderListener {
-    WXEmbed mComponent;
-    OnNestedInstanceEventListener mEventListener;
-
-    EmbedRenderListener(WXEmbed comp) {
-      mComponent = comp;
-      mEventListener = new ClickToReloadListener();
-    }
-
-    @Override
-    public void onViewCreated(WXSDKInstance instance, View view) {
-      FrameLayout hostView = mComponent.getHostView();
-      hostView.removeAllViews();
-      hostView.addView(view);
-    }
-
-    @Override
-    public void onRenderSuccess(WXSDKInstance instance, int width, int height) {
-
-    }
-
-    @Override
-    public void onRefreshSuccess(WXSDKInstance instance, int width, int height) {
-
-    }
-
-    @Override
-    public void onException(WXSDKInstance instance, String errCode, String msg) {
-      if (mEventListener != null) {
-        mEventListener.onException(mComponent, errCode, msg);
-      }
-    }
-  }
-
-  @Deprecated
-  public WXEmbed(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, basicComponentData);
-  }
-
-  public WXEmbed(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-    mListener = new EmbedRenderListener(this);
-    mInstanceOnScrollFireEventInterceptor = new EmbedInstanceOnScrollFireEventInterceptor(this);
-
-    ERROR_IMG_WIDTH = (int) WXViewUtils.getRealPxByWidth(270, instance.getInstanceViewPortWidth());
-    ERROR_IMG_HEIGHT = (int) WXViewUtils.getRealPxByWidth(260, instance.getInstanceViewPortWidth());
-    if (instance instanceof EmbedManager) {
-      Object itemId = getAttrs().get(ITEM_ID);
-      if (itemId != null) {
-        ((EmbedManager) instance).putEmbed(itemId.toString(), this);
-      }
-    }
-    this.priority = WXUtils.getString(getAttrs().get(Constants.Name.PRIORITY), PRIORITY_NORMAL);
-    this.strategy = WXUtils.getString(getAttrs().get(Constants.Name.STRATEGY), STRATEGY_NONE);
-    instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_EMBED_COUNT,1);
-  }
-
-  @Override
-  public void setOnNestEventListener(OnNestedInstanceEventListener listener){
-    mListener.mEventListener = listener;
-  }
-
-  @Override
-  public ViewGroup getViewContainer() {
-    return getHostView();
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.SRC:
-        String src = WXUtils.getString(param, null);
-        if (src != null)
-          setSrc(src);
-        return true;
-      case Constants.Name.PRIORITY:
-        String priority = WXUtils.getString(param, null);
-        if (priority != null) {
-          setPriority(priority);
-        }
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @Override
-  public void renderNewURL(String url) {
-    src = url;
-    loadContent();
-  }
-
-  @Override
-  public void reload() {
-    if (!TextUtils.isEmpty(src)) {
-      loadContent();
-    }
-  }
-
-  public String getOriginUrl() {
-    return originUrl;
-  }
-
-  public void setOriginUrl(String originUrl) {
-    this.originUrl = originUrl;
-  }
-
-  private String originUrl;
-
-
-  @Override
-  public void addEvent(String type) {
-    super.addEvent(type);
-    if(Constants.Event.SCROLL_START.equals(type)){
-      mInstanceOnScrollFireEventInterceptor.addInterceptEvent(type);
-    }else if(Constants.Event.SCROLL_END.equals(type)){
-      mInstanceOnScrollFireEventInterceptor.addInterceptEvent(type);
-    }else if(Constants.Event.SCROLL.equals(type)){
-      mInstanceOnScrollFireEventInterceptor.addInterceptEvent(type);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.SRC)
-  public void setSrc(String src) {
-    originUrl=src;
-    this.src = src;
-    if (mNestedInstance != null) {
-      mNestedInstance.destroy();
-      mNestedInstance = null;
-    }
-    if (mIsVisible && !TextUtils.isEmpty(this.src)) {
-      loadContent();
-    }
-  }
-  public String getSrc() {
-    return src;
-  }
-
-
-  @WXComponentProp(name = Constants.Name.PRIORITY)
-  public void setPriority(String priority) {
-    if(TextUtils.isEmpty(priority)){
-      return;
-    }
-    this.priority = priority;
-  }
-
-  /**
-   * Load embed content, default behavior is create a nested instance.
-   */
-  protected void loadContent(){
-    if(mNestedInstance != null){
-      mNestedInstance.destroy();
-    }
-    mNestedInstance = createInstance();
-    if(mListener != null && mListener.mEventListener != null){
-      if(!mListener.mEventListener.onPreCreate(this,src)){
-        //cancel render
-        mListener.mEventListener.onCreated(this, mNestedInstance);
-      }
-    }
-  }
-
-  private static final int getLevel(WXEmbed embed){
-    String priority = embed.priority;
-    String strategy = embed.strategy;
-    int level  = 5;
-    if(!STRATEGY_HIGH.equals(strategy)) {
-      if (TextUtils.equals(priority, PRIORITY_LOW)) {
-        level = 0;
-      } else if (TextUtils.equals(priority, PRIORITY_HIGH)) {
-        level = 10;
-      }
-    }
-    return  level;
-  }
-
-  private WXSDKInstance createInstance() {
-    WXSDKInstance sdkInstance = getInstance().createNestedInstance(this);
-    sdkInstance.setParentInstance(getInstance());
-    boolean needsAdd = !getAttrs().containsKey("disableInstanceVisibleListener");
-    if(needsAdd){ //prevent switch off fire viewappear event twice
-        getInstance().addOnInstanceVisibleListener(this);
-    }
-    sdkInstance.registerRenderListener(mListener);
-    mInstanceOnScrollFireEventInterceptor.resetFirstLaterScroller();;
-    sdkInstance.addInstanceOnFireEventInterceptor(mInstanceOnScrollFireEventInterceptor);
-    sdkInstance.registerOnWXScrollListener(mInstanceOnScrollFireEventInterceptor);
-
-    String url=src;
-    if(mListener != null && mListener.mEventListener != null){
-      url=mListener.mEventListener.transformUrl(src);
-      if(!mListener.mEventListener.onPreCreate(this,src)){
-        //cancel render
-        return null;
-      }
-    }
-
-    if(TextUtils.isEmpty(url)){
-      mListener.mEventListener.onException(this,
-              WXErrorCode.WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR.getErrorCode(),
-              WXErrorCode.WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR.getErrorMsg() + "!!wx embed src url is null"
-      );
-      return sdkInstance;
-    }
-    sdkInstance.setContainerInfo(WXInstanceApm.KEY_PAGE_PROPERTIES_INSTANCE_TYPE,"embed");
-    sdkInstance.setContainerInfo(WXInstanceApm.KEY_PAGE_PROPERTIES_PARENT_PAGE,getInstance().getWXPerformance().pageName);
-    sdkInstance.renderByUrl(url,
-            url,
-            null, null,
-            WXRenderStrategy.APPEND_ASYNC);
-
-    return sdkInstance;
-  }
-
-  @Override
-  public void setVisibility(String visibility) {
-    super.setVisibility(visibility);
-    boolean visible = TextUtils.equals(visibility, Constants.Value.VISIBLE);
-    if(mIsVisible != visible){
-
-      if (!TextUtils.isEmpty(src) && visible) {
-        if (mNestedInstance == null) {
-          loadContent();
-        } else {
-          mNestedInstance.onViewAppear();
-        }
-      }
-
-      if (!visible) {
-        if (mNestedInstance != null) {
-          mNestedInstance.onViewDisappear();
-        }
-      }
-      mIsVisible = visible;
-      doAutoEmbedMemoryStrategy();
-    }
-  }
-
-  @Override
-  public void destroy() {
-    super.destroy();
-    destoryNestInstance();
-    src = null;
-    if (getInstance() != null) {
-      getInstance().removeOnInstanceVisibleListener(this);
-    }
-  }
-
-  private void  doAutoEmbedMemoryStrategy(){
-    /**
-     * auto manage embed amount in current instance, save memory
-     * */
-    if(!STRATEGY_NONE.equals(this.strategy)){
-      if(!mIsVisible && mNestedInstance != null){
-        if(PRIORITY_LOW.equals(this.priority)){
-          destoryNestInstance();
-        }else{
-          if(getInstance().hiddenEmbeds == null){ // low is in front, when priority is same, hidden time pre in first
-            getInstance().hiddenEmbeds = new PriorityQueue<>(8, new Comparator<WXEmbed>() {
-              @Override
-              public int compare(WXEmbed o1, WXEmbed o2) {
-                int level =  getLevel(o1) - getLevel(o2);
-                if(level != 0){
-                  return  level;
-                }
-                return (int) (o1.hiddenTime - o2.hiddenTime);
-              }
-            });
-          }
-          //getInstance().hiddenEmbeds.remove(this);
-          if(!getInstance().hiddenEmbeds.contains(this)) {
-            this.hiddenTime = System.currentTimeMillis();
-            getInstance().hiddenEmbeds.add(this);
-          }
-          if(getInstance().hiddenEmbeds != null && getInstance().getMaxHiddenEmbedsNum() >= 0){
-            while (getInstance().hiddenEmbeds.size() > getInstance().getMaxHiddenEmbedsNum()){
-              WXEmbed embed = getInstance().hiddenEmbeds.poll();
-              if(embed.mIsVisible){
-                continue;
-              }
-              if(embed != null) {
-                embed.destoryNestInstance();
-              }
-            }
-          }
-        }
-      }
-      if(mIsVisible && mNestedInstance != null){
-        if(getInstance().hiddenEmbeds != null && getInstance().hiddenEmbeds.contains(this)){
-          getInstance().hiddenEmbeds.remove(this);
-        }
-      }
-    }
-
-  }
-
-  @Override
-  public void onAppear() {
-    //appear event from root instance will not trigger visibility change
-    if(mIsVisible && mNestedInstance != null){
-      WXComponent comp = mNestedInstance.getRootComponent();
-      if(comp != null)
-        comp.fireEvent(Constants.Event.VIEWAPPEAR);
-    }
-  }
-
-  @Override
-  public void onDisappear() {
-    //appear event from root instance will not trigger visibility change
-    if(mIsVisible && mNestedInstance != null){
-      WXComponent comp = mNestedInstance.getRootComponent();
-      if(comp != null)
-        comp.fireEvent(Constants.Event.VIEWDISAPPEAR);
-    }
-  }
-
-  @Override
-  public void onActivityStart() {
-    super.onActivityStart();
-    if (mNestedInstance != null) {
-      mNestedInstance.onActivityStart();
-    }
-  }
-
-  @Override
-  public void onActivityResume() {
-    super.onActivityResume();
-    if (mNestedInstance != null) {
-      mNestedInstance.onActivityResume();
-    }
-  }
-
-  @Override
-  public void onActivityPause() {
-    super.onActivityPause();
-    if (mNestedInstance != null) {
-      mNestedInstance.onActivityPause();
-    }
-  }
-
-  @Override
-  public void onActivityStop() {
-    super.onActivityStop();
-    if (mNestedInstance != null) {
-      mNestedInstance.onActivityStop();
-    }
-  }
-
-  @Override
-  public void onActivityDestroy() {
-    super.onActivityDestroy();
-    if (mNestedInstance != null) {
-      mNestedInstance.onActivityDestroy();
-    }
-  }
-
-  public void setStrategy(String strategy) {
-    this.strategy = strategy;
-  }
-
-  private void destoryNestInstance(){
-    if(getInstance().hiddenEmbeds != null && getInstance().hiddenEmbeds.contains(this)){
-      getInstance().hiddenEmbeds.remove(this);
-    }
-    if (mNestedInstance != null) {
-      mNestedInstance.destroy();
-      mNestedInstance = null;
-    }
-    if(WXEnvironment.isApkDebugable()){
-      WXLogUtils.w("WXEmbed destoryNestInstance priority " + priority + " index " + getAttrs().get("index")
-              + "  " + hiddenTime  + " embeds size " + (getInstance().hiddenEmbeds == null ?  0 : getInstance().hiddenEmbeds.size())
-              + " strategy " + this.strategy);
-    }
-  }
-
-  @Override
-  public void addLayerOverFlowListener(String ref) {
-    if (mNestedInstance != null)
-      mNestedInstance.addLayerOverFlowListener(getRef());
-  }
-
-  @Override
-  public void removeLayerOverFlowListener(String ref) {
-    if (mNestedInstance != null)
-      mNestedInstance.removeLayerOverFlowListener(ref);
-  }
-
-  static class EmbedInstanceOnScrollFireEventInterceptor extends InstanceOnFireEventInterceptor implements OnWXScrollListener{
-
-    private WXEmbed mEmbed;
-    private WXComponent firstLayerScroller;
-
-    public EmbedInstanceOnScrollFireEventInterceptor(WXEmbed embed) {
-      this.mEmbed = embed;
-    }
-
-    public void resetFirstLaterScroller(){
-      firstLayerScroller = null;
-    }
-
-    @Override
-    public void onFireEvent(String instanceId, String elementRef, String type, Map<String, Object> params, Map<String, Object> domChanges) {
-      if(mEmbed == null
-              || mEmbed.mNestedInstance == null
-              || !mEmbed.mNestedInstance.getInstanceId().equals(instanceId)){
-        return;
-      }
-      if(firstLayerScroller == null){
-          initFirstLayerScroller();
-      }
-      if(firstLayerScroller == null){
-        return;
-      }
-      if(firstLayerScroller.getRef().equals(elementRef)){
-         mEmbed.getInstance().fireEvent(mEmbed.getRef(), type, params, domChanges);
-      }
-    }
-
-
-    private void initFirstLayerScroller(){
-      if(firstLayerScroller == null){
-          firstLayerScroller = findFirstLayerScroller();
-          if(firstLayerScroller != null){
-            for(String event : getListenEvents()){
-              if(!firstLayerScroller.containsEvent(event)){
-                  firstLayerScroller.getEvents().add(event);
-                  firstLayerScroller.addEvent(event);
-              }
-            }
-          }
-      }
-    }
-
-    /**
-     * get first layer scroller ref
-     * */
-    private WXComponent findFirstLayerScroller(){
-         if(mEmbed.mNestedInstance == null){
-           return null;
-         }
-         WXComponent rootComponent = mEmbed.mNestedInstance.getRootComponent();
-        if(rootComponent instanceof  Scrollable){
-          return rootComponent;
-        }
-        Queue<WXComponent> queues = new ArrayDeque<>();
-        queues.offer(rootComponent);
-        while (!queues.isEmpty()){
-             WXComponent component = queues.poll();
-             if(component == null){
-               break;
-             }
-             if(component instanceof  Scrollable){
-                return  component;
-             }
-             if(component instanceof WXVContainer){
-               WXVContainer container = (WXVContainer) component;
-               for(int i=0; i<container.getChildCount(); i++){
-                  queues.offer(container.getChild(i));
-               }
-             }
-        }
-        return null;
-    }
-
-
-    @Override
-    public void onScrolled(View view, int x, int y) {
-      if(firstLayerScroller != null){
-        return;
-      }
-      if(getListenEvents().size() > 0){
-        initFirstLayerScroller();
-      }
-    }
-
-    @Override
-    public void onScrollStateChanged(View view, int x, int y, int newState) {
-
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXHeader.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXHeader.java
deleted file mode 100644
index a07f628..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXHeader.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.list.WXCell;
-
-/**
- * The same as sticky cell
- */
-@Component(lazyload = false)
-public class WXHeader extends WXCell {
-
-  @Deprecated
-  public WXHeader(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-  public WXHeader(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
-    super(instance, parent, lazy, basicComponentData);
-    String parantType = parent.getComponentType();
-    if(WXBasicComponentType.LIST.equals(parantType)
-            || WXBasicComponentType.RECYCLE_LIST.equals(parantType)){
-      getStyles().put(Constants.Name.POSITION, Constants.Value.STICKY);
-      setSticky(Constants.Value.STICKY);
-    }
-  }
-
-  @Override
-  public boolean isLazy() {
-    return false;
-  }
-
-  @Override
-  public boolean canRecycled() {
-    return !isSticky();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXImage.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXImage.java
deleted file mode 100644
index f165e1c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXImage.java
+++ /dev/null
@@ -1,549 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import com.taobao.weex.dom.WXImageQuality;
-
-import java.lang.ref.WeakReference;
-import java.lang.reflect.InvocationTargetException;
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Locale;
-import java.util.Map;
-
-import android.Manifest;
-import android.app.Activity;
-import android.content.Context;
-import android.content.pm.PackageManager;
-import android.graphics.RectF;
-import android.graphics.drawable.Drawable;
-import android.net.Uri;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v4.app.ActivityCompat;
-import android.support.v4.content.ContextCompat;
-import android.text.TextUtils;
-import android.view.ViewGroup;
-import android.widget.ImageView;
-import android.widget.ImageView.ScaleType;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.adapter.IWXImgLoaderAdapter;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXImageSharpen;
-import com.taobao.weex.common.WXImageStrategy;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.performance.WXAnalyzerDataTransfer;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXImageView;
-import com.taobao.weex.ui.view.border.BorderDrawable;
-import com.taobao.weex.utils.ImageDrawable;
-import com.taobao.weex.utils.ImgURIUtil;
-import com.taobao.weex.utils.SingleFunctionParser;
-import com.taobao.weex.utils.WXDomUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewToImageUtil;
-import com.taobao.weex.utils.WXViewUtils;
-
-/**
- * Image component
- */
-@Component(lazyload = false)
-public class WXImage extends WXComponent<ImageView> {
-
-  public static final String SUCCEED = "success";
-  public static final String ERRORDESC = "errorDesc";
-  private static final int WRITE_EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE = 0x2;
-
-  private String mSrc;
-  private int mBlurRadius;
-  private boolean mAutoRecycle = true;
-
-  private static SingleFunctionParser.FlatMapper<Integer> BLUR_RADIUS_MAPPER = new SingleFunctionParser.FlatMapper<Integer>() {
-    @Override
-    public Integer map(String raw) {
-      return WXUtils.getInteger(raw,0);
-    }
-  };
-
-  public static class Creator implements ComponentCreator {
-    @Override
-    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-      return new WXImage(instance, parent, basicComponentData);
-    }
-  }
-
-  @Deprecated
-  public WXImage(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, basicComponentData);
-  }
-
-  public WXImage(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  @Override
-  protected ImageView initComponentHostView(@NonNull Context context) {
-    WXImageView view = new WXImageView(context);
-    view.setScaleType(ScaleType.FIT_XY);
-    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
-      view.setCropToPadding(true);
-    }
-    view.holdComponent(this);
-    return view;
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.RESIZE_MODE:
-        String resizeMode = WXUtils.getString(param, null);
-        if (resizeMode != null) { setResizeMode(resizeMode); }
-        return true;
-      case Constants.Name.RESIZE:
-        String resize = WXUtils.getString(param, null);
-        if (resize != null) { setResize(resize); }
-        return true;
-      case Constants.Name.SRC:
-        String src = WXUtils.getString(param, null);
-        if (src != null) { setSrc(src); }
-        return true;
-      case Constants.Name.IMAGE_QUALITY:
-        return true;
-      case Constants.Name.AUTO_RECYCLE:
-        mAutoRecycle = WXUtils.getBoolean(param, mAutoRecycle);
-        if (!mAutoRecycle && null != getInstance()){
-          getInstance().getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_IMG_UN_RECYCLE_NUM,1);
-        }
-        return true;
-      case Constants.Name.FILTER:
-        int blurRadius = 0;
-        if (param != null && param instanceof String) {
-          blurRadius = parseBlurRadius((String)param);
-        }
-        if (!TextUtils.isEmpty(this.mSrc)) {
-          setBlurRadius(this.mSrc, blurRadius);
-        }
-        return true;
-      default:
-        return super.setProperty(key, param);
-    }
-  }
-
-  @Override
-  public void refreshData(WXComponent component) {
-    super.refreshData(component);
-    if (component instanceof WXImage) {
-      setSrc(component.getAttrs().getImageSrc());
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.RESIZE_MODE)
-  public void setResizeMode(String resizeMode) {
-    (getHostView()).setScaleType(getResizeMode(resizeMode));
-    getHostView().setImageDrawable(getHostView().getDrawable());
-  }
-
-  @RestrictTo(Scope.LIBRARY_GROUP)
-  protected ScaleType getResizeMode(String resizeMode) {
-    ScaleType scaleType = ScaleType.FIT_XY;
-    if (TextUtils.isEmpty(resizeMode)) {
-      return scaleType;
-    }
-
-    switch (resizeMode) {
-      case "cover":
-        scaleType = ScaleType.CENTER_CROP;
-        break;
-      case "contain":
-        scaleType = ScaleType.FIT_CENTER;
-        break;
-      case "stretch":
-        scaleType = ScaleType.FIT_XY;
-        break;
-      default:
-        break;
-    }
-    return scaleType;
-  }
-
-  @WXComponentProp(name = Constants.Name.RESIZE)
-  public void setResize(String resize) {
-    setResizeMode(resize);
-  }
-
-  /**
-   * Process local scheme, load drawable.
-   * @param rewrited
-   */
-  private void setLocalSrc(Uri rewrited) {
-    ImageView imageView;
-    Drawable localDrawable = ImgURIUtil.getDrawableFromLoaclSrc(getContext(), rewrited);
-    if (localDrawable != null && (imageView = getHostView()) != null) {
-      imageView.setImageDrawable(localDrawable);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.SRC)
-  public void setSrc(String src) {
-
-    if (getInstance().getImageNetworkHandler() != null) {
-      String localUrl = getInstance().getImageNetworkHandler().fetchLocal(src);
-      if (!TextUtils.isEmpty(localUrl)) {
-        src = localUrl;
-      }
-    }
-
-    if (src == null) {
-      return;
-    }
-
-    ImageView image = getHostView();
-    if("".equals(src) && image != null){
-      image.setImageDrawable(null);
-      return;
-    }
-
-    if(image != null){
-      if(image.getDrawable() != null && !TextUtils.equals(mSrc, src)){
-        image.setImageDrawable(null);
-      }
-    }
-
-
-    this.mSrc = src;
-    WXSDKInstance instance = getInstance();
-    Uri rewrited = instance.rewriteUri(Uri.parse(src), URIAdapter.IMAGE);
-
-    if (Constants.Scheme.LOCAL.equals(rewrited.getScheme())) {
-      setLocalSrc(rewrited);
-    } else {
-      int blur = 0;
-      String blurStr = getStyles().getBlur();
-      blur = parseBlurRadius(blurStr);
-      setRemoteSrc(rewrited, blur);
-    }
-  }
-
-  private void setBlurRadius(@NonNull String src, int blurRadius) {
-    if(getInstance() != null && blurRadius != mBlurRadius) {
-      Uri parsedUri = getInstance().rewriteUri(Uri.parse(src), URIAdapter.IMAGE);
-      if(!Constants.Scheme.LOCAL.equals(parsedUri.getScheme())) {
-        setRemoteSrc(parsedUri,blurRadius);
-      }
-    }
-  }
-
-  private int parseBlurRadius(@Nullable String rawRadius) {
-    if(rawRadius == null) {
-      return 0;
-    }
-    SingleFunctionParser<Integer> parser = new SingleFunctionParser<Integer>(rawRadius,BLUR_RADIUS_MAPPER);
-    List<Integer> list = null;
-    try {
-      list = parser.parse("blur");
-    }catch (Exception e) {
-      return 0;
-    }
-    if(list == null || list.isEmpty()) {
-      return 0;
-    }
-    return list.get(0);
-  }
-
-  @Override
-  public void recycled() {
-    super.recycled();
-
-    if (getInstance().getImgLoaderAdapter() != null) {
-      getInstance().getImgLoaderAdapter().setImage(null, mHost,
-              null, null);
-    } else {
-      if (WXEnvironment.isApkDebugable()) {
-        throw new WXRuntimeException("getImgLoaderAdapter() == null");
-      }
-      WXLogUtils.e("Error getImgLoaderAdapter() == null");
-    }
-  }
-
-  public void autoReleaseImage(){
-    if(mAutoRecycle){
-      if(getHostView() != null){
-        if (getInstance().getImgLoaderAdapter() != null) {
-          getInstance().getImgLoaderAdapter().setImage(null, mHost, null, null);
-        }
-      }
-    }
-  }
-
-  public void autoRecoverImage() {
-    if(mAutoRecycle) {
-      setSrc(mSrc);
-    }
-  }
-
-  private void setRemoteSrc(Uri rewrited, int blurRadius) {
-
-    WXImageStrategy imageStrategy = new WXImageStrategy(getInstanceId());
-    imageStrategy.isClipping = true;
-
-    WXImageSharpen imageSharpen = getAttrs().getImageSharpen();
-    imageStrategy.isSharpen = imageSharpen == WXImageSharpen.SHARPEN;
-
-    imageStrategy.blurRadius = Math.max(0, blurRadius);
-    this.mBlurRadius = blurRadius;
-
-    final String rewritedStr = rewrited.toString();
-    imageStrategy.setImageListener(new MyImageListener(this,rewritedStr));
-
-    String placeholder=null;
-    if(getAttrs().containsKey(Constants.Name.PLACEHOLDER)){
-      placeholder= (String) getAttrs().get(Constants.Name.PLACEHOLDER);
-    }else if(getAttrs().containsKey(Constants.Name.PLACE_HOLDER)){
-      placeholder=(String)getAttrs().get(Constants.Name.PLACE_HOLDER);
-    }
-    if(placeholder!=null){
-      imageStrategy.placeHolder = getInstance().rewriteUri(Uri.parse(placeholder),URIAdapter.IMAGE).toString();
-    }
-
-    imageStrategy.instanceId = getInstanceId();
-    IWXImgLoaderAdapter imgLoaderAdapter = getInstance().getImgLoaderAdapter();
-    if (imgLoaderAdapter != null) {
-      imgLoaderAdapter.setImage(rewritedStr, getHostView(),
-          getImageQuality(), imageStrategy);
-    }
-  }
-
-  @RestrictTo(Scope.LIBRARY_GROUP)
-  protected WXImageQuality getImageQuality(){
-    return getAttrs().getImageQuality();
-  }
-
-  @Override
-  protected void onFinishLayout() {
-    super.onFinishLayout();
-    updateBorderRadius();
-  }
-
-  @Override
-  public void updateProperties(Map<String, Object> props) {
-    super.updateProperties(props);
-    updateBorderRadius();
-  }
-
-  private void updateBorderRadius() {
-    if (getHostView() instanceof WXImageView) {
-      final WXImageView imageView = (WXImageView)getHostView();
-      BorderDrawable borderDrawable = WXViewUtils.getBorderDrawable(getHostView());
-      float[] borderRadius;
-      if (borderDrawable != null) {
-        RectF borderBox = new RectF(0, 0, WXDomUtils.getContentWidth(this), WXDomUtils.getContentHeight(this));
-        borderRadius = borderDrawable.getBorderInnerRadius(borderBox);
-      } else {
-        borderRadius = new float[] {0, 0, 0, 0, 0, 0, 0, 0};
-      }
-      imageView.setBorderRadius(borderRadius);
-
-      if (imageView.getDrawable() instanceof ImageDrawable) {
-        ImageDrawable imageDrawable = (ImageDrawable)imageView.getDrawable();
-        float[] previousRadius = imageDrawable.getCornerRadii();
-        if (!Arrays.equals(previousRadius, borderRadius)) {
-          imageDrawable.setCornerRadii(borderRadius);
-        }
-      }
-    }
-  }
-
-  /**
-   * Need permission {android.permission.WRITE_EXTERNAL_STORAGE}
-   */
-  @JSMethod(uiThread = false)
-  public void save(final JSCallback saveStatuCallback) {
-
-    if (ContextCompat.checkSelfPermission(getContext(), Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
-      if (getContext() instanceof Activity) {
-        ActivityCompat.requestPermissions((Activity) getContext(),
-                new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, WRITE_EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE);
-      }
-    }
-
-    if (ContextCompat.checkSelfPermission(getContext(), Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
-      if (saveStatuCallback != null) {
-        Map<String, Object> result = new HashMap<>();
-        result.put(SUCCEED, false);
-        result.put(ERRORDESC,"Permission denied: android.permission.WRITE_EXTERNAL_STORAGE");
-        saveStatuCallback.invoke(result);
-      }
-      return;
-    }
-
-    if (mHost == null) {
-      if (saveStatuCallback != null) {
-        Map<String, Object> result = new HashMap<>();
-        result.put(SUCCEED, false);
-        result.put(ERRORDESC,"Image component not initialized");
-        saveStatuCallback.invoke(result);
-      }
-      return;
-    }
-
-    if (mSrc == null || mSrc.equals("")) {
-      if (saveStatuCallback != null) {
-        Map<String, Object> result = new HashMap<>();
-        result.put(SUCCEED, false);
-        result.put(ERRORDESC,"Image does not have the correct src");
-        saveStatuCallback.invoke(result);
-      }
-      return;
-    }
-
-    WXViewToImageUtil.generateImage(mHost, 0, 0xfff8f8f8, new WXViewToImageUtil.OnImageSavedCallback() {
-      @Override
-      public void onSaveSucceed(String path) {
-        if (saveStatuCallback != null) {
-          Map<String, Object> result = new HashMap<>();
-          result.put(SUCCEED, true);
-          saveStatuCallback.invoke(result);
-        }
-      }
-
-      @Override
-      public void onSaveFailed(String errorDesc) {
-        if (saveStatuCallback != null) {
-          Map<String, Object> result = new HashMap<>();
-          result.put(SUCCEED, false);
-          result.put(ERRORDESC,errorDesc);
-          saveStatuCallback.invoke(result);
-        }
-      }
-    });
-  }
-
-  private String preImgUrlStr = "";
-  private void monitorImgSize(ImageView imageView,String currentImgUrlStr){
-    if (null == imageView){
-      return;
-    }
-    WXSDKInstance instance = getInstance();
-    if (null == instance){
-      return;
-    }
-    ViewGroup.LayoutParams params =imageView.getLayoutParams();
-    Drawable img = imageView.getDrawable();
-    if (null == params || null ==img){
-      return;
-    }
-    int imgHeight = img.getIntrinsicHeight();
-    int imgWidth = img.getIntrinsicWidth();
-    if (!preImgUrlStr.equals(currentImgUrlStr)){
-      preImgUrlStr = currentImgUrlStr;
-      if (imgHeight > 1081 && imgWidth > 721){
-        instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_LARGE_IMG_COUNT,1);
-        if (WXAnalyzerDataTransfer.isOpenPerformance){
-          WXAnalyzerDataTransfer.transferPerformance(getInstanceId(),"details",WXInstanceApm.KEY_PAGE_STATS_LARGE_IMG_COUNT,
-              imgWidth+"*"+imgHeight+","+currentImgUrlStr
-              );
-        }
-      }
-      long imgSize = imgHeight * imgWidth;
-      long viewSize = imageView.getMeasuredHeight() * imageView.getMeasuredWidth();
-      if (viewSize == 0){
-          return;
-      }
-      double scaleSize =  imgSize/(double)viewSize;
-      //max diff 40*40
-      if (scaleSize >1.2 && imgSize-viewSize > 1600){
-        instance.getWXPerformance().wrongImgSizeCount++;
-        instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_WRONG_IMG_SIZE_COUNT,1);
-
-        if (WXAnalyzerDataTransfer.isOpenPerformance){
-          WXAnalyzerDataTransfer.transferPerformance(getInstanceId(),"details",WXInstanceApm.KEY_PAGE_STATS_WRONG_IMG_SIZE_COUNT,
-              String.format(Locale.ROOT, "imgSize:[%d,%d],viewSize:[%d,%d],urL:%s",imgWidth,imgHeight,imageView.getMeasuredWidth(),imageView.getMeasuredHeight()
-              ,currentImgUrlStr)
-          );
-        }
-      }
-    }
-
-  }
-
-  @Override
-  public void destroy() {
-    if(getHostView() instanceof WXImageView){
-      if (getInstance().getImgLoaderAdapter() != null) {
-        getInstance().getImgLoaderAdapter().setImage(null, mHost, null, null);
-      }
-    }
-    super.destroy();
-  }
-
-  public interface Measurable {
-    int getNaturalWidth();
-    int getNaturalHeight();
-  }
-
-  public  static class MyImageListener implements WXImageStrategy.ImageListener {
-
-    private WeakReference<WXImage> wxImageWeakReference;
-
-    private String rewritedStr;
-
-    MyImageListener(WXImage image,String rewritedStr) {
-      this.wxImageWeakReference = new WeakReference<WXImage>(image);
-      this.rewritedStr = rewritedStr;
-    }
-
-    @Override
-    public void onImageFinish(String url, ImageView imageView, boolean result, Map extra) {
-      WXImage image = wxImageWeakReference.get();
-
-      if(image == null)
-        return;
-
-      if (image.getEvents().contains(Constants.Event.ONLOAD)) {
-        Map<String, Object> params = new HashMap<String, Object>();
-        Map<String, Object> size = new HashMap<>(2);
-        if (imageView != null && imageView instanceof Measurable) {
-          size.put("naturalWidth", ((Measurable) imageView).getNaturalWidth());
-          size.put("naturalHeight", ((Measurable) imageView).getNaturalHeight());
-        } else {
-          size.put("naturalWidth", 0);
-          size.put("naturalHeight", 0);
-        }
-        if (image.containsEvent(Constants.Event.ONLOAD)) {
-          params.put("success", result);
-          params.put("size", size);
-          image.fireEvent(Constants.Event.ONLOAD, params);
-        }
-      }
-      image.monitorImgSize(imageView,rewritedStr);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXIndicator.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXIndicator.java
deleted file mode 100644
index 449c12e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXIndicator.java
+++ /dev/null
@@ -1,167 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-import android.view.View;
-import android.widget.FrameLayout;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXCircleIndicator;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-/**
- *
- * Slider indicator
- */
-@Component(lazyload = false)
-public class WXIndicator extends WXComponent<WXCircleIndicator> {
-
-  @Deprecated
-  public WXIndicator(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-  public WXIndicator(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-    super(instance, parent, isLazy, basicComponentData);
-  }
-
-  @Override
-  protected void setHostLayoutParams(WXCircleIndicator host, int width, int height, int left, int right, int top, int bottom) {
-      FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(width, height);
-      this.setMarginsSupportRTL(params, left, top, right, bottom);
-      host.setLayoutParams(params);
-  }
-
-  @Override
-  protected WXCircleIndicator initComponentHostView(@NonNull Context context) {
-    WXCircleIndicator view = new WXCircleIndicator(context);
-    if (getParent() instanceof WXSlider) {
-      return view;
-    } else {
-      if (WXEnvironment.isApkDebugable()) {
-        throw new WXRuntimeException("WXIndicator initView error.");
-      }
-    }
-    return null;
-  }
-
-  @Override
-  protected void onHostViewInitialized(WXCircleIndicator host) {
-    super.onHostViewInitialized(host);
-    if (getParent() instanceof WXSlider) {
-      ((WXSlider) getParent()).addIndicator(this);
-    }
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.ITEM_COLOR:
-        String item_color = WXUtils.getString(param,null);
-        if (item_color != null)
-          setItemColor(item_color);
-        return true;
-      case Constants.Name.ITEM_SELECTED_COLOR:
-        String selected_color = WXUtils.getString(param,null);
-        if (selected_color != null)
-          setItemSelectedColor(selected_color);
-        return true;
-      case Constants.Name.ITEM_SIZE:
-        Integer item_size = WXUtils.getInteger(param,null);
-        if (item_size != null)
-          setItemSize(item_size);
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-
-  @WXComponentProp(name = Constants.Name.ITEM_COLOR)
-  public void setItemColor(String itemColor) {
-    if (!TextUtils.isEmpty(itemColor)) {
-      int colorInt = WXResourceUtils.getColor(itemColor);
-      if (colorInt != Integer.MIN_VALUE) {
-        getHostView().setPageColor(colorInt);
-        getHostView().forceLayout();
-        getHostView().requestLayout();
-      }
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.ITEM_SELECTED_COLOR)
-  public void setItemSelectedColor(String itemSelectedColor) {
-    if (!TextUtils.isEmpty(itemSelectedColor)) {
-      int colorInt = WXResourceUtils.getColor(itemSelectedColor);
-      if (colorInt != Integer.MIN_VALUE) {
-        getHostView().setFillColor(colorInt);
-        getHostView().forceLayout();
-        getHostView().requestLayout();
-      }
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.ITEM_SIZE)
-  public void setItemSize(int itemSize) {
-    if (itemSize < 0) {
-      return;
-    }
-    getHostView().setRadius(WXViewUtils.getRealPxByWidth(itemSize,getInstance().getInstanceViewPortWidth()) / 2.0f);
-    getHostView().forceLayout();
-    getHostView().requestLayout();
-  }
-
-  public void setShowIndicators(boolean show) {
-    if (getHostView() == null) {
-      return;
-    }
-    if (show) {
-      getHostView().setVisibility(View.VISIBLE);
-    } else {
-      getHostView().setVisibility(View.GONE);
-    }
-  }
-
-  // TODO
-//  public static class IndicatorDomNode extends WXDomObject{
-//    public IndicatorDomNode(){
-//      super();
-//    }
-//
-//    @Override
-//    protected Map<String, String> getDefaultStyle() {
-//      WXStyle pendingStyles = getStyles();
-//      Map<String,String> map = new HashMap<>();
-//      if(!pendingStyles.containsKey(Constants.Name.RIGHT))
-//        map.put(Constants.Name.LEFT,"0");
-//      if(!pendingStyles.containsKey(Constants.Name.BOTTOM))
-//        map.put(Constants.Name.TOP,"0");
-//      return map;
-//    }
-//  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXInput.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXInput.java
deleted file mode 100644
index d1a272d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXInput.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXEditText;
-
-/**
- *
- * Input component
- */
-@Component(lazyload = false)
-public class WXInput extends AbstractEditComponent{
-
-  @Deprecated
-  public WXInput(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-  public WXInput(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-    super(instance, parent, isLazy, basicComponentData);
-  }
-
-  @Override
-  protected void appleStyleAfterCreated(WXEditText editText) {
-    super.appleStyleAfterCreated(editText);
-    editText.setSingleLine();//default use single line , same to ios
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXLoading.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXLoading.java
deleted file mode 100644
index 9ddd15a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXLoading.java
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.list.WXListComponent;
-import com.taobao.weex.ui.view.WXFrameLayout;
-import com.taobao.weex.ui.view.WXLoadingLayout;
-import com.taobao.weex.ui.view.refresh.core.WXSwipeLayout;
-import com.taobao.weex.ui.view.refresh.wrapper.BaseBounceView;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * div component
- */
-@Component(lazyload = false)
-public class WXLoading extends WXBaseRefresh implements WXSwipeLayout.WXOnLoadingListener {
-
-  public static final String HIDE = "hide";
-
-  public WXLoading(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
-    super(instance, parent, lazy, basicComponentData);
-  }
-
-  @Override
-  protected WXFrameLayout initComponentHostView(@NonNull Context context) {
-    return new WXLoadingLayout(context);
-  }
-
-  @Override
-  public void onLoading() {
-    if (getEvents().contains(Constants.Event.ONLOADING)) {
-      fireEvent(Constants.Event.ONLOADING);
-    }
-  }
-
-  @Override
-  protected void setHostLayoutParams(WXFrameLayout host, int width, int height,
-                                     int left, int right, int top, int bottom) {
-    // The view of WXLoading will always be wrapped by a WXRefreshView at some point
-    // which is unknowable for front-end so the margins should always be 0 in LayoutParams,
-    // otherwise it will bring visible layout errors. This means WXLoading do not
-    // support margin.
-    super.setHostLayoutParams(host, width, height, 0, 0, 0, 0);
-  }
-
-  @Override
-  public void onPullingUp(float dy, int pullOutDistance, float viewHeight) {
-    if (getEvents().contains(Constants.Event.ONPULLING_UP)) {
-      Map<String, Object> data = new HashMap<>();
-      data.put(Constants.Name.DISTANCE_Y, dy);
-      data.put(Constants.Name.PULLING_DISTANCE, pullOutDistance);
-      data.put(Constants.Name.VIEW_HEIGHT, viewHeight);
-      fireEvent(Constants.Event.ONPULLING_UP, data);
-    }
-  }
-
-  @Override
-  public boolean canRecycled() {
-    return false;
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.DISPLAY:
-        String display = WXUtils.getString(param,null);
-        if (display != null)
-          setDisplay(display);
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @WXComponentProp(name = Constants.Name.DISPLAY)
-  public void setDisplay(String display) {
-    if (!TextUtils.isEmpty(display)) {
-      if (display.equals(HIDE)) {
-        if (getParent() instanceof WXListComponent || getParent() instanceof WXScroller) {
-          if (((BaseBounceView)getParent().getHostView()).getSwipeLayout().isRefreshing()) {
-            ((BaseBounceView) getParent().getHostView()).finishPullLoad();
-            ((BaseBounceView) getParent().getHostView()).onLoadmoreComplete();
-          }
-        }
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXLoadingIndicator.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXLoadingIndicator.java
deleted file mode 100644
index be6bdd1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXLoadingIndicator.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.graphics.Color;
-
-import android.support.annotation.NonNull;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.refresh.circlebar.CircleProgressBar;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXUtils;
-
-@Component(lazyload = false)
-
-public class WXLoadingIndicator extends WXComponent<CircleProgressBar> {
-
-
-    public WXLoadingIndicator(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-        super(instance, parent, isLazy, basicComponentData);
-    }
-
-    @Override
-    protected CircleProgressBar initComponentHostView(@NonNull Context context) {
-        return new CircleProgressBar(context);
-    }
-
-    @Override
-    protected boolean setProperty(String key, Object param) {
-        switch (key) {
-            case Constants.Name.COLOR:
-                String color = WXUtils.getString(param,null);
-                if (color != null)
-                    setColor(color);
-                return true;
-            case Constants.Name.ANIMATING:
-                Boolean result = WXUtils.getBoolean(param, null);
-                if (result != null) {
-                    setAnimating(result);
-                }
-                return true;
-        }
-        return super.setProperty(key, param);
-    }
-
-    @WXComponentProp(name = Constants.Name.COLOR)
-    public void setColor(String color) {
-        if (color != null && !color.equals("")) {
-            int parseColor = WXResourceUtils.getColor(color, Color.RED);
-            getHostView().setColorSchemeColors(parseColor);
-        }
-    }
-
-    @WXComponentProp(name = Constants.Name.ANIMATING)
-    public void setAnimating(boolean animating) {
-        if (animating) {
-            getHostView().start();
-        } else {
-            getHostView().stop();
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXRefresh.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXRefresh.java
deleted file mode 100644
index bf8c99c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXRefresh.java
+++ /dev/null
@@ -1,119 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.list.WXListComponent;
-import com.taobao.weex.ui.view.WXFrameLayout;
-import com.taobao.weex.ui.view.WXRefreshLayout;
-import com.taobao.weex.ui.view.refresh.core.WXSwipeLayout;
-import com.taobao.weex.ui.view.refresh.wrapper.BaseBounceView;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * div component
- */
-@Component(lazyload = false)
-public class WXRefresh extends WXBaseRefresh implements WXSwipeLayout.WXOnRefreshListener{
-
-  public static final String HIDE = "hide";
-
-  @Deprecated
-  public WXRefresh(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-  public WXRefresh(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
-    super(instance, parent, lazy, basicComponentData);
-  }
-
-  @Override
-  protected WXFrameLayout initComponentHostView(@NonNull Context context) {
-    return new WXRefreshLayout(context);
-  }
-
-  @Override
-  public boolean canRecycled() {
-    return false;
-  }
-
-  @Override
-  public void onRefresh() {
-    if(isDestoryed()){
-      return;
-    }
-    
-    if (getEvents().contains(Constants.Event.ONREFRESH)) {
-      fireEvent(Constants.Event.ONREFRESH);
-    }
-  }
-
-  @Override
-  public int getLayoutTopOffsetForSibling() {
-    //offset siblings
-    return getParent() instanceof Scrollable ? -Math.round(getLayoutHeight()) : 0;
-  }
-
-  @Override
-  public void onPullingDown(float dy, int pullOutDistance, float viewHeight) {
-    if (getEvents() != null && getEvents().contains(Constants.Event.ONPULLING_DOWN)) {
-      Map<String, Object> data = new HashMap<>();
-      data.put(Constants.Name.DISTANCE_Y, dy);
-      data.put(Constants.Name.PULLING_DISTANCE, pullOutDistance);
-      data.put(Constants.Name.VIEW_HEIGHT, viewHeight);
-      fireEvent(Constants.Event.ONPULLING_DOWN, data);
-    }
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.DISPLAY:
-        String display = WXUtils.getString(param,null);
-        if (display != null)
-          setDisplay(display);
-        return true;
-    }
-    return super.setProperty(key,param);
-  }
-
-  @WXComponentProp(name = Constants.Name.DISPLAY)
-  public void setDisplay(String display) {
-    if (!TextUtils.isEmpty(display)) {
-      if (display.equals(HIDE)) {
-        if (getParent() instanceof WXListComponent || getParent() instanceof WXScroller) {
-          if (((BaseBounceView)getParent().getHostView()).getSwipeLayout().isRefreshing()) {
-            ((BaseBounceView) getParent().getHostView()).finishPullRefresh();
-            ((BaseBounceView) getParent().getHostView()).onRefreshingComplete();
-          }
-        }
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXScroller.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXScroller.java
deleted file mode 100644
index c460849..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXScroller.java
+++ /dev/null
@@ -1,1048 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.annotation.SuppressLint;
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.os.Build;
-import android.os.Handler;
-import android.os.Looper;
-import android.support.annotation.NonNull;
-import android.support.v4.view.ViewCompat;
-import android.text.TextUtils;
-import android.view.GestureDetector;
-import android.view.Gravity;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewTreeObserver;
-import android.widget.FrameLayout;
-import android.widget.FrameLayout.LayoutParams;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.ICheckBindingScroller;
-import com.taobao.weex.common.OnWXScrollListener;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.helper.ScrollStartEndHelper;
-import com.taobao.weex.ui.component.helper.WXStickyHelper;
-import com.taobao.weex.ui.view.IWXScroller;
-import com.taobao.weex.ui.view.WXBaseRefreshLayout;
-import com.taobao.weex.ui.view.WXHorizontalScrollView;
-import com.taobao.weex.ui.view.WXScrollView;
-import com.taobao.weex.ui.view.WXScrollView.WXScrollViewListener;
-import com.taobao.weex.ui.view.refresh.wrapper.BaseBounceView;
-import com.taobao.weex.ui.view.refresh.wrapper.BounceScrollerView;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import java.lang.reflect.InvocationTargetException;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Map.Entry;
-
-/**
- * Component for scroller. It also support features like
- * "appear", "disappear" and "sticky"
- */
-@Component(lazyload = false)
-
-public class WXScroller extends WXVContainer<ViewGroup> implements WXScrollViewListener,Scrollable {
-
-  public static final String DIRECTION = "direction";
-  protected int mOrientation = Constants.Orientation.VERTICAL;
-  private List<WXComponent> mRefreshs=new ArrayList<>();
-  /** Use for offset children layout */
-  private int mChildrenLayoutOffset = 0;
-  private boolean mForceLoadmoreNextTime = false;
-  private int mOffsetAccuracy = 10;
-  private Point mLastReport = new Point(-1, -1);
-  private boolean mHasAddScrollEvent = false;
-  private Boolean mIslastDirectionRTL;
-
-  private static final int SWIPE_MIN_DISTANCE = 5;
-  private static final int SWIPE_THRESHOLD_VELOCITY = 300;
-  private int mActiveFeature = 0;
-  /**
-   * scroll start and scroll end event
-   * */
-  private ScrollStartEndHelper mScrollStartEndHelper;
-
-  private GestureDetector mGestureDetector;
-
-  private int pageSize = 0;
-  private boolean pageEnable = false;
-  private boolean mIsHostAttachedToWindow = false;
-  private View.OnAttachStateChangeListener mOnAttachStateChangeListener;
-
-  private boolean mlastDirectionRTL = false;
-
-  public static class Creator implements ComponentCreator {
-    @Override
-    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-      // For performance message collection
-      instance.setUseScroller(true);
-      return new WXScroller(instance, parent, basicComponentData);
-    }
-  }
-  /**
-   * Map for storing appear information
-   **/
-  private Map<String,AppearanceHelper> mAppearanceComponents = new HashMap<>();
-
-  /**
-   * Map for storing component that is sticky.
-   **/
-  private Map<String, Map<String, WXComponent>> mStickyMap = new HashMap<>();
-  private FrameLayout mRealView;
-  private FrameLayout mScrollerView;
-
-  private int mContentHeight = 0;
-
-  private WXStickyHelper stickyHelper;
-  private Handler handler=new Handler(Looper.getMainLooper());
-
-  private boolean isScrollable = true;
-
-  @Deprecated
-  public WXScroller(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, basicComponentData);
-  }
-
-  public WXScroller(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-    stickyHelper = new WXStickyHelper(this);
-    instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_SCROLLER_NUM,1);
-  }
-
-  /**
-   * @return FrameLayout inner ScrollView
-   */
-  @Override
-  public ViewGroup getRealView() {
-    return mScrollerView;
-  }
-
-
-  @Override
-  public void createViewImpl() {
-    super.createViewImpl();
-    for (int i = 0; i < mRefreshs.size(); i++) {
-      WXComponent component = mRefreshs.get(i);
-      component.createViewImpl();
-      checkRefreshOrLoading(component);
-    }
-  }
-
-  /**
-   * @return ScrollView
-   */
-  public ViewGroup getInnerView() {
-    if(getHostView() == null) {
-      return null;
-    }
-    if (getHostView() instanceof BounceScrollerView) {
-      return ((BounceScrollerView) getHostView()).getInnerView();
-    } else {
-      return getHostView();
-    }
-  }
-
-  @Override
-  public void addEvent(String type) {
-    super.addEvent(type);
-    if (ScrollStartEndHelper.isScrollEvent(type)
-            && getInnerView() != null && !mHasAddScrollEvent) {
-      mHasAddScrollEvent = true;
-      if (getInnerView() instanceof WXScrollView) {
-        ((WXScrollView) getInnerView()).addScrollViewListener(new WXScrollViewListener() {
-          @Override
-          public void onScrollChanged(WXScrollView scrollView, int x, int y, int oldx, int oldy) {
-            getScrollStartEndHelper().onScrolled(x, y);
-            if(!getEvents().contains(Constants.Event.SCROLL)){
-              return;
-            }
-            if (shouldReport(x, y)) {
-              fireScrollEvent(scrollView.getContentFrame(), x, y, oldx, oldy);
-            }
-          }
-
-          @Override
-          public void onScrollToBottom(WXScrollView scrollView, int x, int y) {
-            //ignore
-          }
-
-          @Override
-          public void onScrollStopped(WXScrollView scrollView, int x, int y) {
-            //ignore
-          }
-
-          @Override
-          public void onScroll(WXScrollView scrollView, int x, int y) {
-            //ignore
-          }
-        });
-      } else if (getInnerView() instanceof WXHorizontalScrollView) {
-        ((WXHorizontalScrollView) getInnerView()).addScrollViewListener(new WXHorizontalScrollView.ScrollViewListener() {
-          @Override
-          public void onScrollChanged(WXHorizontalScrollView scrollView, int x, int y, int oldx, int oldy) {
-            getScrollStartEndHelper().onScrolled(x, y);
-            if(!getEvents().contains(Constants.Event.SCROLL)){
-              return;
-            }
-            if (shouldReport(x, y)) {
-              fireScrollEvent(scrollView.getContentFrame(), x, y, oldx, oldy);
-            }
-          }
-        });
-      }
-    }
-  }
-
-  private void fireScrollEvent(Rect contentFrame, int x, int y, int oldx, int oldy) {
-    fireEvent(Constants.Event.SCROLL, getScrollEvent(x, y));
-  }
-
-  public Map<String, Object> getScrollEvent(int x, int y){
-    Rect contentFrame =  new Rect();
-    if (getInnerView() instanceof WXScrollView) {
-      contentFrame = ((WXScrollView) getInnerView()).getContentFrame();
-    }else if (getInnerView() instanceof WXHorizontalScrollView) {
-      contentFrame = ((WXHorizontalScrollView) getInnerView()).getContentFrame();
-    }
-    Map<String, Object> event = new HashMap<>(2);
-    Map<String, Object> contentSize = new HashMap<>(2);
-    Map<String, Object> contentOffset = new HashMap<>(2);
-
-    int viewport = getInstance().getInstanceViewPortWidth();
-
-    contentSize.put(Constants.Name.WIDTH, WXViewUtils.getWebPxByWidth(contentFrame.width(), viewport));
-    contentSize.put(Constants.Name.HEIGHT, WXViewUtils.getWebPxByWidth(contentFrame.height(), viewport));
-
-    contentOffset.put(Constants.Name.X, -WXViewUtils.getWebPxByWidth(x, viewport));
-    contentOffset.put(Constants.Name.Y, -WXViewUtils.getWebPxByWidth(y, viewport));
-
-    event.put(Constants.Name.CONTENT_SIZE, contentSize);
-    event.put(Constants.Name.CONTENT_OFFSET, contentOffset);
-    return  event;
-  }
-
-  private boolean shouldReport(int x, int y) {
-    if (mLastReport.x == -1 && mLastReport.y == -1) {
-      mLastReport.x = x;
-      mLastReport.y = y;
-      return true;
-    }
-
-    if (mOrientation == Constants.Orientation.HORIZONTAL
-            && Math.abs(x - mLastReport.x) >= mOffsetAccuracy) {
-      mLastReport.x = x;
-      mLastReport.y = y;
-      return true;
-    }
-
-    if (mOrientation == Constants.Orientation.VERTICAL
-            && Math.abs(y - mLastReport.y) >= mOffsetAccuracy) {
-      mLastReport.x = x;
-      mLastReport.y = y;
-      return true;
-    }
-
-    return false;
-  }
-
-  /**
-   * Intercept refresh view and loading view
-   */
-  @Override
-  public void addSubView(View child, int index) {
-    if (child == null || mRealView == null) {
-      return;
-    }
-
-    if (child instanceof WXBaseRefreshLayout) {
-      return;
-    }
-
-    int count = mRealView.getChildCount();
-    index = index >= count ? -1 : index;
-    if (index == -1) {
-      mRealView.addView(child);
-    } else {
-      mRealView.addView(child, index);
-    }
-  }
-
-  @Override
-  protected int getChildrenLayoutTopOffset() {
-    if (mChildrenLayoutOffset == 0) {
-      // Child LayoutSize data set after call Layout. So init mChildrenLayoutOffset here
-      final int listSize = mRefreshs.size();
-      if (listSize > 0) {
-        for (int i = 0; i < listSize; i++) {
-          WXComponent child = mRefreshs.get(i);
-          mChildrenLayoutOffset += child.getLayoutTopOffsetForSibling();
-        }
-      }
-    }
-    return mChildrenLayoutOffset;
-  }
-
-  /**
-   * Intercept refresh view and loading view
-   */
-  @Override
-  public void addChild(WXComponent child, int index) {
-    if (child instanceof WXBaseRefresh) {
-      if (checkRefreshOrLoading(child)) {
-        mRefreshs.add(child);
-      }
-    }
-    super.addChild(child, index);
-  }
-
-  /**
-   * Setting refresh view and loading view
-   * @param child the refresh_view or loading_view
-   */
-
-  private boolean checkRefreshOrLoading(final WXComponent child) {
-    boolean result = false;
-    if (child instanceof WXRefresh && getHostView() != null) {
-      ((BaseBounceView) getHostView()).setOnRefreshListener((WXRefresh) child);
-      Runnable runnable = WXThread.secure(new Runnable(){
-        @Override
-        public void run() {
-          ((BaseBounceView) getHostView()).setHeaderView(child);
-        }
-      });
-      handler.postDelayed(runnable,100);
-      result = true;
-    }
-
-    if (child instanceof WXLoading && getHostView() !=null) {
-      ((BaseBounceView) getHostView()).setOnLoadingListener((WXLoading)child);
-      Runnable runnable= WXThread.secure(new Runnable(){
-        @Override
-        public void run() {
-          ((BaseBounceView) getHostView()).setFooterView(child);
-        }
-      });
-      handler.postDelayed(runnable, 100);
-      result = true;
-    }
-    return result;
-  }
-
-  @Override
-  public void remove(WXComponent child,boolean destory) {
-    super.remove(child,destory);
-    if(child instanceof WXLoading){
-      ((BaseBounceView)getHostView()).removeFooterView(child);
-    }else if(child instanceof WXRefresh){
-      ((BaseBounceView)getHostView()).removeHeaderView(child);
-    }
-  }
-
-  @Override
-  public void destroy() {
-    super.destroy();
-    if (mAppearanceComponents != null) {
-      mAppearanceComponents.clear();
-    }
-    if (mStickyMap != null) {
-      mStickyMap.clear();
-    }
-    if (mOnAttachStateChangeListener != null && getInnerView() != null) {
-      getInnerView().removeOnAttachStateChangeListener(mOnAttachStateChangeListener);
-    }
-    if (getInnerView() != null && getInnerView() instanceof IWXScroller) {
-      ((IWXScroller) getInnerView()).destroy();
-    }
-  }
-
-  @SuppressLint("RtlHardcoded")
-  @Override
-  public void setMarginsSupportRTL(ViewGroup.MarginLayoutParams lp, int left, int top, int right, int bottom) {
-    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR1) {
-      lp.setMargins(left, top, right, bottom);
-      lp.setMarginStart(left);
-      lp.setMarginEnd(right);
-    } else {
-      if (lp instanceof FrameLayout.LayoutParams) {
-        FrameLayout.LayoutParams lp_frameLayout = (FrameLayout.LayoutParams) lp;
-        if (isLayoutRTL()) {
-          lp_frameLayout.gravity = Gravity.RIGHT | Gravity.TOP;
-          lp.setMargins(right, top, left, bottom);
-        } else {
-          lp_frameLayout.gravity = Gravity.LEFT | Gravity.TOP;
-          lp.setMargins(left, top, right, bottom);
-        }
-      } else {
-        lp.setMargins(left, top, right, bottom);
-      }
-    }
-  }
-
-  @Override
-  public void setLayout(WXComponent component) {
-    if (TextUtils.isEmpty(component.getComponentType())
-            || TextUtils.isEmpty(component.getRef()) || component.getLayoutPosition() == null
-            || component.getLayoutSize() == null) {
-      return;
-    }
-    if (component.getHostView() != null) {
-      int layoutDirection = component.isLayoutRTL() ? ViewCompat.LAYOUT_DIRECTION_RTL : ViewCompat.LAYOUT_DIRECTION_LTR;
-      ViewCompat.setLayoutDirection(component.getHostView(), layoutDirection);
-    }
-    super.setLayout(component);
-  }
-
-  @Override
-  protected MeasureOutput measure(int width, int height) {
-    MeasureOutput measureOutput = new MeasureOutput();
-    if (this.mOrientation == Constants.Orientation.HORIZONTAL) {
-      int screenW = WXViewUtils.getScreenWidth(WXEnvironment.sApplication);
-      int weexW = WXViewUtils.getWeexWidth(getInstanceId());
-      measureOutput.width = width > (weexW >= screenW ? screenW : weexW) ? FrameLayout.LayoutParams.MATCH_PARENT
-              : width;
-      measureOutput.height = height;
-    } else {
-      int screenH = WXViewUtils.getScreenHeight(WXEnvironment.sApplication);
-      int weexH = WXViewUtils.getWeexHeight(getInstanceId());
-      measureOutput.height = height > (weexH >= screenH ? screenH : weexH) ? FrameLayout.LayoutParams.MATCH_PARENT
-              : height;
-      measureOutput.width = width;
-    }
-    return measureOutput;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  protected ViewGroup initComponentHostView(@NonNull Context context) {
-    String scroll;
-    if (getAttrs().isEmpty()) {
-      scroll = "vertical";
-    } else {
-      scroll = getAttrs().getScrollDirection();
-
-      Object o = getAttrs().get(Constants.Name.PAGE_ENABLED);
-
-      pageEnable = o != null && Boolean.parseBoolean(o.toString());
-
-      Object pageSize = getAttrs().get(Constants.Name.PAGE_SIZE);
-      if (pageSize != null) {
-        float aFloat = WXUtils.getFloat(pageSize);
-
-
-        float realPxByWidth = WXViewUtils.getRealPxByWidth(aFloat, getInstance().getInstanceViewPortWidth());
-        if (realPxByWidth != 0) {
-          this.pageSize = (int) realPxByWidth;
-        }
-      }
-
-    }
-
-    ViewGroup host;
-    if(("horizontal").equals(scroll)){
-      mOrientation = Constants.Orientation.HORIZONTAL;
-      final WXHorizontalScrollView scrollView = new WXHorizontalScrollView(context);
-      mRealView = new FrameLayout(context);
-      scrollView.setScrollViewListener(new WXHorizontalScrollView.ScrollViewListener() {
-        @Override
-        public void onScrollChanged(WXHorizontalScrollView scrollView, int x, int y, int oldx, int oldy) {
-          procAppear(x,y,oldx,oldy);
-        }
-      });
-      FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(
-              LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
-      scrollView.addView(mRealView, layoutParams);
-      scrollView.setHorizontalScrollBarEnabled(false);
-      mScrollerView = scrollView;
-      final WXScroller component = this;
-      final View.OnLayoutChangeListener listener = new View.OnLayoutChangeListener() {
-        @Override
-        public void onLayoutChange(View view, final int left, int top, final int right, int bottom, final int oldLeft, int oldTop, final int oldRight, int oldBottom) {
-          final View frameLayout = view;
-          scrollView.post(new Runnable() {
-            @Override
-            public void run() {
-              if (mIslastDirectionRTL != null && isLayoutRTL() != mIslastDirectionRTL) {
-                // when layout direction changed we need convert x to RTL x for scroll to the same item
-                int currentX = getScrollX();
-                int totalWidth = getInnerView().getChildAt(0).getWidth();
-                int displayWidth = getInnerView().getMeasuredWidth();
-                scrollView.scrollTo(totalWidth - currentX - displayWidth, component.getScrollY());
-              } else if (isLayoutRTL()) {
-                // if layout direction not changed, but width changede, we need keep RTL offset
-                int oldWidth = oldRight - oldLeft;
-                int width = right - left;
-                int changedWidth = width - oldWidth;
-                if (changedWidth != 0) {
-                  scrollView.scrollBy(changedWidth, component.getScrollY());
-                }
-              }
-              mIslastDirectionRTL = isLayoutRTL();
-            }
-          });
-        }
-      };
-      mRealView.addOnAttachStateChangeListener(new View.OnAttachStateChangeListener() {
-        @Override
-        public void onViewAttachedToWindow(View view) {
-          view.addOnLayoutChangeListener(listener);
-        }
-
-        @Override
-        public void onViewDetachedFromWindow(View view) {
-          view.removeOnLayoutChangeListener(listener);
-        }
-      });
-
-
-      if(pageEnable) {
-        mGestureDetector = new GestureDetector(new MyGestureDetector(scrollView));
-        scrollView.setOnTouchListener(new View.OnTouchListener() {
-          @Override
-          public boolean onTouch(View v, MotionEvent event) {
-            if (pageSize == 0)  {
-              pageSize = v.getMeasuredWidth();
-            }
-
-            if (mGestureDetector.onTouchEvent(event)) {
-              return true;
-            }
-            else if(event.getAction() == MotionEvent.ACTION_UP || event.getAction() == MotionEvent.ACTION_CANCEL ){
-              int scrollX = getScrollX();
-              int featureWidth = pageSize;
-              mActiveFeature = ((scrollX + (featureWidth/2))/featureWidth);
-              int scrollTo = mActiveFeature*featureWidth;
-              scrollView.smoothScrollTo(scrollTo, 0);
-              return true;
-            }
-            else{
-              return false;
-            }
-          }
-        });
-      }
-
-
-      host = scrollView;
-    }else{
-      mOrientation = Constants.Orientation.VERTICAL;
-      BounceScrollerView scrollerView = new BounceScrollerView(context, mOrientation, this);
-      mRealView = new FrameLayout(context);
-      WXScrollView innerView = scrollerView.getInnerView();
-      innerView.addScrollViewListener(this);
-      FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(
-              LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
-      mScrollerView = innerView;
-      innerView.addView(mRealView, layoutParams);
-      innerView.setVerticalScrollBarEnabled(true);
-      innerView.setNestedScrollingEnabled(WXUtils.getBoolean(getAttrs().get(Constants.Name.NEST_SCROLLING_ENABLED), true));
-      innerView.addScrollViewListener(new WXScrollViewListener() {
-        @Override
-        public void onScrollChanged(WXScrollView scrollView, int x, int y, int oldx, int oldy) {
-
-        }
-
-        @Override
-        public void onScrollToBottom(WXScrollView scrollView, int x, int y) {
-
-        }
-
-        @Override
-        public void onScrollStopped(WXScrollView scrollView, int x, int y) {
-          List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
-          if(listeners!=null && listeners.size()>0){
-            for (OnWXScrollListener listener : listeners) {
-              if (listener != null) {
-                listener.onScrollStateChanged(scrollView,x,y,OnWXScrollListener.IDLE);
-              }
-            }
-          }
-          getScrollStartEndHelper().onScrollStateChanged(OnWXScrollListener.IDLE);
-        }
-
-        @Override
-        public void onScroll(WXScrollView scrollView, int x, int y) {
-          List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
-          if(listeners!=null && listeners.size()>0){
-            for (OnWXScrollListener listener : listeners) {
-              if (listener != null) {
-                if(listener instanceof ICheckBindingScroller){
-                  if(((ICheckBindingScroller) listener).isNeedScroller(getRef(),null)){
-                    listener.onScrolled(scrollView, x, y);
-                  }
-                }else {
-                  listener.onScrolled(scrollView, x, y);
-                }
-              }
-            }
-          }
-        }
-      });
-      host = scrollerView;
-    }
-
-    host.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
-      @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
-      @Override
-      public void onGlobalLayout() {
-        procAppear(0,0,0,0);
-        View view;
-        if( (view = getHostView()) == null){
-          return;
-        }
-        if(Build.VERSION.SDK_INT >=  Build.VERSION_CODES.JELLY_BEAN) {
-          view.getViewTreeObserver().removeOnGlobalLayoutListener(this);
-        }else{
-          view.getViewTreeObserver().removeGlobalOnLayoutListener(this);
-        }
-      }
-    });
-    mOnAttachStateChangeListener = new View.OnAttachStateChangeListener() {
-      @Override
-      public void onViewAttachedToWindow(View v) {
-        mIsHostAttachedToWindow = true;
-        procAppear(getScrollX(), getScrollY(), getScrollX(), getScrollY());
-      }
-
-      @Override
-      public void onViewDetachedFromWindow(View v) {
-        mIsHostAttachedToWindow = false;
-        dispatchDisappearEvent();
-      }
-    };
-    host.addOnAttachStateChangeListener(mOnAttachStateChangeListener);
-    return host;
-  }
-
-  @Override
-  public int getScrollY() {
-    return getInnerView() == null ? 0 : getInnerView().getScrollY();
-  }
-
-  @Override
-  public int getScrollX() {
-    return getInnerView() == null ? 0 : getInnerView().getScrollX();
-  }
-
-  @Override
-  public int getOrientation() {
-    return mOrientation;
-  }
-
-  public Map<String, Map<String, WXComponent>> getStickMap() {
-    return mStickyMap;
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.SHOW_SCROLLBAR:
-        Boolean result = WXUtils.getBoolean(param,null);
-        if (result != null) {
-          setShowScrollbar(result);
-        }
-        return true;
-      case Constants.Name.SCROLLABLE:
-        boolean scrollable = WXUtils.getBoolean(param, true);
-        setScrollable(scrollable);
-        return true;
-      case Constants.Name.OFFSET_ACCURACY:
-        int accuracy = WXUtils.getInteger(param, 10);
-        setOffsetAccuracy(accuracy);
-        return true;
-        default:
-          break;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @WXComponentProp(name = Constants.Name.SHOW_SCROLLBAR)
-  public void setShowScrollbar(boolean show) {
-    if(getInnerView()==null){
-      return;
-    }
-    if (mOrientation == Constants.Orientation.VERTICAL) {
-      getInnerView().setVerticalScrollBarEnabled(show);
-    } else {
-      getInnerView().setHorizontalScrollBarEnabled(show);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.SCROLLABLE)
-  public void setScrollable(boolean scrollable) {
-    this.isScrollable = scrollable;
-    View hostView = getInnerView();
-    if(hostView instanceof WXHorizontalScrollView) {
-      ((WXHorizontalScrollView)hostView).setScrollable(scrollable);
-    }else if(hostView instanceof WXScrollView) {
-      ((WXScrollView)hostView).setScrollable(scrollable);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.OFFSET_ACCURACY)
-  public void setOffsetAccuracy(int accuracy) {
-    float realPx = WXViewUtils.getRealPxByWidth(accuracy, getInstance().getInstanceViewPortWidth());
-    this.mOffsetAccuracy = (int) realPx;
-  }
-
-  @Override
-  public boolean isScrollable() {
-    return isScrollable;
-  }
-
-
-  @Override
-  public void bindStickStyle(WXComponent component) {
-    stickyHelper.bindStickStyle(component,mStickyMap);
-  }
-
-  @Override
-  public void unbindStickStyle(WXComponent component) {
-    stickyHelper.unbindStickStyle(component,mStickyMap);
-  }
-
-  /**
-   * Bind appear event
-   */
-  @Override
-  public void bindAppearEvent(WXComponent component) {
-    setWatch(AppearanceHelper.APPEAR,component,true);
-  }
-
-  private void setWatch(int event,WXComponent component,boolean isWatch){
-    AppearanceHelper item = mAppearanceComponents.get(component.getRef());
-    if (item == null) {
-      item = new AppearanceHelper(component);
-      mAppearanceComponents.put(component.getRef(),item);
-    }
-
-    item.setWatchEvent(event,isWatch);
-
-    //check current components appearance status.
-    procAppear(0,0,0,0);
-  }
-
-  /**
-   * Bind disappear event
-   */
-  @Override
-  public void bindDisappearEvent(WXComponent component) {
-    setWatch(AppearanceHelper.DISAPPEAR,component,true);
-  }
-
-  /**
-   * Remove appear event
-   */
-  @Override
-  public void unbindAppearEvent(WXComponent component) {
-    setWatch(AppearanceHelper.APPEAR,component,false);
-  }
-
-  /**
-   * Remove disappear event
-   */
-  @Override
-  public void unbindDisappearEvent(WXComponent component) {
-    setWatch(AppearanceHelper.DISAPPEAR,component,false);
-  }
-
-  @Override
-  public void scrollTo(WXComponent component, Map<String, Object> options) {
-    float offsetFloat = 0;
-    boolean smooth = true;
-
-    if (options != null) {
-      String offset = options.get(Constants.Name.OFFSET) == null ? "0" : options.get(Constants.Name.OFFSET).toString();
-      smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
-      if (offset != null) {
-        try {
-          offsetFloat = WXViewUtils.getRealPxByWidth(Float.parseFloat(offset), getInstance().getInstanceViewPortWidth());
-        }catch (Exception e ){
-          WXLogUtils.e("Float parseFloat error :"+e.getMessage());
-        }
-      }
-    }
-
-    if(pageEnable) {
-      mActiveFeature = mChildren.indexOf(component);
-    }
-
-    int viewYInScroller = component.getAbsoluteY() - getAbsoluteY();
-    int viewXInScroller = 0;
-    if (this.isLayoutRTL()) {
-      // if layout direction is rtl, we need calculate rtl scroll x;
-      if (component.getParent() != null && component.getParent() == this) {
-        if (getInnerView().getChildCount() > 0) {
-          int totalWidth = getInnerView().getChildAt(0).getWidth();
-          int displayWidth = getInnerView().getMeasuredWidth();
-          viewXInScroller = totalWidth - (component.getAbsoluteX() - getAbsoluteX()) - displayWidth;
-        } else {
-          viewXInScroller = component.getAbsoluteX() - getAbsoluteX();
-        }
-      } else {
-        int displayWidth = getInnerView().getMeasuredWidth();
-        viewXInScroller = component.getAbsoluteX() - getAbsoluteX() - displayWidth + (int)component.getLayoutWidth();
-      }
-      offsetFloat = -offsetFloat;
-    } else {
-      viewXInScroller = component.getAbsoluteX() - getAbsoluteX();
-    }
-    scrollBy(viewXInScroller - getScrollX() + (int) offsetFloat, viewYInScroller - getScrollY() + (int) offsetFloat, smooth);
-
-  }
-
-  /**
-   * Scroll by specified distance. Horizontal scroll is not supported now.
-   * @param x horizontal distance, not support
-   * @param y vertical distance. Negative for scroll to top
-   */
-  public void scrollBy(final int x, final int y) {
-    scrollBy(x, y, false);
-  }
-
-  public void scrollBy(final int x, final int y, final boolean smooth) {
-    if (getInnerView() == null) {
-      return;
-    }
-
-    getInnerView().postDelayed(new Runnable() {
-      @Override
-      public void run() {
-        if (mOrientation == Constants.Orientation.VERTICAL) {
-          if (smooth) {
-            ((WXScrollView) getInnerView()).smoothScrollBy(0, y);
-          } else {
-            ((WXScrollView) getInnerView()).scrollBy(0, y);
-          }
-        } else {
-          if (smooth) {
-            ((WXHorizontalScrollView) getInnerView()).smoothScrollBy(x, 0);
-          } else {
-            ((WXHorizontalScrollView) getInnerView()).scrollBy(x, 0);
-          }
-        }
-        getInnerView().invalidate();
-      }
-    }, 16);
-  }
-
-  @Override
-  public void onScrollChanged(WXScrollView scrollView, int x, int y,
-                              int oldx, int oldy) {
-    procAppear( x, y, oldx, oldy);
-  }
-
-  @Override
-  public void notifyAppearStateChange(String wxEventType, String direction) {
-    if (containsEvent(Constants.Event.APPEAR) || containsEvent(Constants.Event.DISAPPEAR)) {
-      Map<String, Object> params = new HashMap<>();
-      params.put("direction", direction);
-      fireEvent(wxEventType, params);
-    }
-    // No-op. The moment to notify children is decided by the time when scroller is attached
-    // or detached to window. Do not call super as scrollview has different disposal.
-  }
-
-  /**
-   * Process event like appear and disappear
-   *
-   * This method will be invoked in several situation below.
-   *    1. bind or unbind event
-   *    2. host view is attached to window
-   *    3. when scrollview is scrolling
-   */
-  private void procAppear(int x, int y, int oldx,
-                          int oldy) {
-    if (!mIsHostAttachedToWindow) return;
-    int moveY = y - oldy;
-    int moveX = x - oldx;
-    String direction = moveY > 0 ? Constants.Value.DIRECTION_UP :
-            moveY < 0 ? Constants.Value.DIRECTION_DOWN : null;
-    if (mOrientation == Constants.Orientation.HORIZONTAL && moveX != 0) {
-      direction = moveX > 0 ? Constants.Value.DIRECTION_RIGHT : Constants.Value.DIRECTION_LEFT;
-    }
-
-    for (Entry<String, AppearanceHelper> item : mAppearanceComponents.entrySet()) {
-      AppearanceHelper helper = item.getValue();
-
-      if (!helper.isWatch()) {
-        continue;
-      }
-      boolean visible = checkItemVisibleInScroller(helper.getAwareChild());
-
-      int result = helper.setAppearStatus(visible);
-      if (result != AppearanceHelper.RESULT_NO_CHANGE) {
-        helper.getAwareChild().notifyAppearStateChange(result == AppearanceHelper.RESULT_APPEAR ? Constants.Event.APPEAR : Constants.Event.DISAPPEAR, direction);
-      }
-    }
-  }
-
-  /**
-   * Check the view of given component is visible in scrollview.
-   *
-   * @param component ready to be check
-   * @return item is visible
-   */
-  private boolean checkItemVisibleInScroller(WXComponent component) {
-    boolean visible = false;
-    while (component != null && !(component instanceof WXScroller)) {
-      if (component.getParent() instanceof WXScroller) {
-        if (mOrientation == Constants.Orientation.HORIZONTAL) {
-          int offsetLeft = (int) component.getLayoutPosition().getLeft() - getScrollX();
-          visible = (offsetLeft > 0 - component.getLayoutWidth() && offsetLeft < getLayoutWidth());
-        } else {
-          int offsetTop = (int) component.getLayoutPosition().getTop() - getScrollY();
-          visible = (offsetTop > 0 - component.getLayoutHeight() && offsetTop < getLayoutHeight());
-        }
-      }
-      component = component.getParent();
-    }
-    return visible;
-  }
-
-  /**
-   * Dispatch disappear event to the child components in need.
-   */
-  private void dispatchDisappearEvent() {
-    for (Entry<String, AppearanceHelper> item : mAppearanceComponents.entrySet()) {
-      AppearanceHelper helper = item.getValue();
-      if (!helper.isWatch()) {
-        continue;
-      }
-      int result = helper.setAppearStatus(false);
-      if (result != AppearanceHelper.RESULT_NO_CHANGE) {
-        helper.getAwareChild().notifyAppearStateChange(result == AppearanceHelper.RESULT_APPEAR ?
-                Constants.Event.APPEAR : Constants.Event.DISAPPEAR, "");
-      }
-    }
-  }
-
-  @Override
-  public void onScrollToBottom(WXScrollView scrollView, int x, int y) {
-
-  }
-
-  @Override
-  public void onScrollStopped(WXScrollView scrollView, int x, int y) {
-  }
-
-  @Override
-  public void onScroll(WXScrollView scrollView, int x, int y) {
-
-    this.onLoadMore(scrollView, x, y);
-  }
-
-  /**
-   * Handle loadMore Event.when Scroller has bind loadMore Event and set the attr of loadMoreOffset
-   * it will tell the JS to handle the event of onLoadMore;
-   * @param scrollView  the WXScrollView
-   * @param x the X direction
-   * @param y the Y direction
-   */
-  protected void onLoadMore(WXScrollView scrollView, int x, int y) {
-    try {
-      String offset = getAttrs().getLoadMoreOffset();
-      if (TextUtils.isEmpty(offset)) {
-        return;
-      }
-      int offsetInt = (int)WXViewUtils.getRealPxByWidth(Float.parseFloat(offset), getInstance().getInstanceViewPortWidth());
-
-      int contentH = scrollView.getChildAt(0).getHeight();
-      int scrollerH = scrollView.getHeight();
-      int offScreenY = contentH - y - scrollerH;
-      if (offScreenY < offsetInt) {
-        if (WXEnvironment.isApkDebugable()) {
-          WXLogUtils.d("[WXScroller-onScroll] offScreenY :" + offScreenY);
-        }
-        if (mContentHeight != contentH || mForceLoadmoreNextTime) {
-          fireEvent(Constants.Event.LOADMORE);
-          mContentHeight = contentH;
-          mForceLoadmoreNextTime = false;
-        }
-      }
-    } catch (Exception e) {
-      WXLogUtils.d("[WXScroller-onScroll] ", e);
-    }
-
-  }
-
-  @JSMethod
-  public void resetLoadmore() {
-    mForceLoadmoreNextTime = true;
-  }
-
-  public ScrollStartEndHelper getScrollStartEndHelper() {
-    if(mScrollStartEndHelper == null){
-      mScrollStartEndHelper = new ScrollStartEndHelper(this);
-    }
-    return mScrollStartEndHelper;
-  }
-
-
-  class MyGestureDetector extends GestureDetector.SimpleOnGestureListener {
-    public WXHorizontalScrollView getScrollView() {
-      return scrollView;
-    }
-
-    private final WXHorizontalScrollView scrollView;
-
-    MyGestureDetector(WXHorizontalScrollView horizontalScrollView) {
-      scrollView = horizontalScrollView;
-    }
-
-    @Override
-    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
-      int mItems = mChildren.size();
-      try {
-        //right to left
-        if(e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) {
-          int featureWidth = pageSize;
-          mActiveFeature = (mActiveFeature < (mItems - 1))? mActiveFeature + 1:mItems -1;
-          scrollView.smoothScrollTo(mActiveFeature*featureWidth, 0);
-          return true;
-        }
-        //left to right
-        else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) {
-          int featureWidth = pageSize;
-          mActiveFeature = (mActiveFeature > 0)? mActiveFeature - 1:0;
-          scrollView.smoothScrollTo(mActiveFeature*featureWidth, 0);
-          return true;
-        }
-      } catch (Exception e) {
-        WXLogUtils.e("There was an error processing the Fling event:" + e.getMessage());
-      }
-      return false;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSlider.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSlider.java
deleted file mode 100644
index c2806fa..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSlider.java
+++ /dev/null
@@ -1,619 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.support.v4.view.ViewPager;
-import android.support.v4.view.ViewPager.OnPageChangeListener;
-import android.text.TextUtils;
-import android.view.GestureDetector;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewGroup.LayoutParams;
-import android.widget.FrameLayout;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.BaseFrameLayout;
-import com.taobao.weex.ui.view.WXCircleIndicator;
-import com.taobao.weex.ui.view.WXCirclePageAdapter;
-import com.taobao.weex.ui.view.WXCircleViewPager;
-import com.taobao.weex.ui.view.gesture.WXGestureType;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.lang.ref.WeakReference;
-import java.lang.reflect.InvocationTargetException;
-import java.util.HashMap;
-import java.util.Map;
-
-@Component(lazyload = false)
-
-public class WXSlider extends WXVContainer<FrameLayout> {
-
-  public static final String INDEX = "index";
-  public static final String INFINITE = "infinite";
-
-  private boolean isInfinite = true;
-
-  Map<String, Object> params = new HashMap<>();
-  private float offsetXAccuracy = 0.1f;
-  private int initIndex = -1;
-  private boolean keepIndex = false;
-  private Runnable initRunnable;
-
-
-  public static class Creator implements ComponentCreator {
-    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-      return new WXSlider(instance, parent, basicComponentData);
-    }
-  }
-
-  /**
-   * Scrollable sliderview
-   */
-  /**
-   * package
-   **/
-  WXCircleViewPager mViewPager;
-  /**
-   * Circle indicator
-   */
-  protected WXIndicator mIndicator;
-
-  /**
-   * Adapter for sliderview
-   */
-  protected WXCirclePageAdapter mAdapter;
-
-  protected boolean mShowIndicators = true;
-
-  protected OnPageChangeListener mPageChangeListener = new SliderPageChangeListener();
-
-  @Deprecated
-  public WXSlider(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, basicComponentData);
-  }
-
-  public WXSlider(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  @Override
-  protected BaseFrameLayout initComponentHostView(@NonNull Context context) {
-    BaseFrameLayout view = new BaseFrameLayout(context);
-    // init view pager
-    if (getAttrs() != null) {
-      Object obj = getAttrs().get(INFINITE);
-      isInfinite = WXUtils.getBoolean(obj, true);
-    }
-    FrameLayout.LayoutParams pagerParams = new FrameLayout.LayoutParams(
-        LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
-    mViewPager = new WXCircleViewPager(context);
-    mViewPager.setCircle(isInfinite);
-    mViewPager.setLayoutParams(pagerParams);
-
-    // init adapter
-    mAdapter = new WXCirclePageAdapter(isInfinite);
-    mViewPager.setAdapter(mAdapter);
-    // add to parent
-    view.addView(mViewPager);
-    mViewPager.addOnPageChangeListener(mPageChangeListener);
-
-    registerActivityStateListener();
-
-    return view;
-  }
-
-  /**
-   * Slider is not a regular container,top/left/right/bottom not apply to view,expect indicator.
-   */
-  @Override
-  public LayoutParams getChildLayoutParams(WXComponent child,View childView, int width, int height, int left, int right, int top, int bottom) {
-    ViewGroup.LayoutParams lp = childView.getLayoutParams();
-    if (lp == null) {
-      lp = new FrameLayout.LayoutParams(width, height);
-    } else {
-      lp.width = width;
-      lp.height = height;
-    }
-
-    if (lp instanceof ViewGroup.MarginLayoutParams) {
-      //expect indicator .
-      if (child instanceof WXIndicator) {
-        this.setMarginsSupportRTL((ViewGroup.MarginLayoutParams) lp, left, top, right, bottom);
-      } else {
-        this.setMarginsSupportRTL((ViewGroup.MarginLayoutParams) lp, 0, 0, 0, 0);
-      }
-    }
-    return lp;
-  }
-
-
-  @Override
-  public void addEvent(String type) {
-    super.addEvent(type);
-    if (Constants.Event.SCROLL.equals(type)) {
-      if (mViewPager == null) {
-        return;
-      }
-      mViewPager.addOnPageChangeListener(new SliderOnScrollListener(this));
-    }
-  }
-
-  @Override
-  public boolean containsGesture(WXGestureType WXGestureType) {
-    //Enable gesture for slider
-    return super.containsGesture(WXGestureType);
-  }
-
-  @Override
-  public ViewGroup getRealView() {
-    return mViewPager;
-  }
-
-  @Override
-  public void addSubView(View view, int index) {
-    if (view == null || mAdapter == null) {
-      return;
-    }
-
-    if (view instanceof WXCircleIndicator) {
-      return;
-    }
-    mAdapter.addPageView(view);
-    hackTwoItemsInfiniteScroll();
-    if (initIndex != -1 && mAdapter.getRealCount() > initIndex) {
-      if(initRunnable == null){
-        initRunnable = new Runnable() {
-          @Override
-          public void run() {
-            initIndex = getInitIndex();
-            mViewPager.setCurrentItem(getRealIndex(initIndex));
-            initIndex = -1;
-            initRunnable = null;
-          }
-        };
-      }
-      mViewPager.removeCallbacks(initRunnable);
-      mViewPager.postDelayed(initRunnable, 50);
-    } else {
-      if (!keepIndex) {
-        mViewPager.setCurrentItem(getRealIndex(0));
-      }
-    }
-    if (mIndicator != null) {
-      mIndicator.getHostView().forceLayout();
-      mIndicator.getHostView().requestLayout();
-    }
-  }
-
-  @Override
-  public void setLayout(WXComponent component) {
-    if (mAdapter != null) {
-      mAdapter.setLayoutDirectionRTL(this.isLayoutRTL());
-    }
-    super.setLayout(component);
-  }
-
-  @Override
-  public void remove(WXComponent child, boolean destroy) {
-    if (child == null || child.getHostView() == null || mAdapter == null) {
-      return;
-    }
-
-    mAdapter.removePageView(child.getHostView());
-    hackTwoItemsInfiniteScroll();
-    super.remove(child,destroy);
-  }
-
-  @Override
-  public void destroy() {
-    super.destroy();
-    if (mViewPager != null) {
-      mViewPager.stopAutoScroll();
-      mViewPager.removeAllViews();
-      mViewPager.destory();
-    }
-  }
-
-  @Override
-  public void onActivityResume() {
-    super.onActivityResume();
-    if (mViewPager != null && mViewPager.isAutoScroll()) {
-      mViewPager.startAutoScroll();
-    }
-  }
-
-  @Override
-  public void onActivityStop() {
-    super.onActivityStop();
-    if (mViewPager != null) {
-      mViewPager.pauseAutoScroll();
-    }
-  }
-
-  public void addIndicator(WXIndicator indicator) {
-    FrameLayout root = getHostView();
-    if (root == null) {
-      return;
-    }
-    mIndicator = indicator;
-    mIndicator.setShowIndicators(mShowIndicators);
-    WXCircleIndicator indicatorView = indicator.getHostView();
-    if (indicatorView != null) {
-      indicatorView.setCircleViewPager(mViewPager);
-      // indicatorView.setOnPageChangeListener(mPageChangeListener);  // commented for twice onChange() called when do slide.
-      root.addView(indicatorView);
-    }
-
-  }
-
-
-  private int getInitIndex(){
-    Object index = getAttrs().get(Constants.Name.INDEX);
-    int select = WXUtils.getInteger(index, initIndex);
-    if(mAdapter == null || mAdapter.getCount() == 0){
-      return  0;
-    }
-    if(select >= mAdapter.getRealCount()){
-      select = select%mAdapter.getRealCount();
-    }
-
-    return select;
-  }
-
-  private int getRealIndex(int idx) {
-    int retIdx = idx;
-
-    if (mAdapter.getRealCount() > 0) {
-      if(idx >= mAdapter.getRealCount()) retIdx = mAdapter.getRealCount() - 1;
-      if (isLayoutRTL()) {
-        retIdx = mAdapter.getRealCount() - 1 - retIdx;
-      }
-    }
-    retIdx = retIdx + 0;
-    return retIdx;
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.VALUE:
-        String value = WXUtils.getString(param, null);
-        if (value != null) {
-          setValue(value);
-        }
-        return true;
-      case Constants.Name.AUTO_PLAY:
-        String aotu_play = WXUtils.getString(param, null);
-        if (aotu_play != null) {
-          setAutoPlay(aotu_play);
-        }
-        return true;
-      case Constants.Name.SHOW_INDICATORS:
-        String indicators = WXUtils.getString(param, null);
-        if (indicators != null) {
-          setShowIndicators(indicators);
-        }
-        return true;
-      case Constants.Name.INTERVAL:
-        Integer interval = WXUtils.getInteger(param, null);
-        if (interval != null) {
-          setInterval(interval);
-        }
-        return true;
-      case Constants.Name.INDEX:
-        Integer index = WXUtils.getInteger(param, null);
-        if (index != null) {
-          setIndex(index);
-        }
-        return true;
-      case Constants.Name.OFFSET_X_ACCURACY:
-        Float accuracy = WXUtils.getFloat(param, 0.1f);
-        if (accuracy != 0) {
-          setOffsetXAccuracy(accuracy);
-        }
-        return true;
-      case Constants.Name.SCROLLABLE:
-        boolean scrollable = WXUtils.getBoolean(param, true);
-        setScrollable(scrollable);
-        return true;
-      case Constants.Name.KEEP_INDEX:
-        this.keepIndex = WXUtils.getBoolean(param, false);
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @Deprecated
-  @WXComponentProp(name = Constants.Name.VALUE)
-  public void setValue(String value) {
-    if (value == null || getHostView() == null) {
-      return;
-    }
-    int i;
-    try {
-      i = Integer.parseInt(value);
-    } catch (NumberFormatException e) {
-      WXLogUtils.e("", e);
-      return;
-    }
-
-    setIndex(i);
-  }
-
-  @WXComponentProp(name = Constants.Name.AUTO_PLAY)
-  public void setAutoPlay(String autoPlay) {
-    if (TextUtils.isEmpty(autoPlay) || autoPlay.equals("false")) {
-      mViewPager.stopAutoScroll();
-    } else {
-      mViewPager.stopAutoScroll();
-      mViewPager.startAutoScroll();
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.SHOW_INDICATORS)
-  public void setShowIndicators(String show) {
-    if (TextUtils.isEmpty(show) || show.equals("false")) {
-      mShowIndicators = false;
-    } else {
-      mShowIndicators = true;
-    }
-
-    if (mIndicator == null) {
-      return;
-    }
-    mIndicator.setShowIndicators(mShowIndicators);
-  }
-
-  @WXComponentProp(name = Constants.Name.INTERVAL)
-  public void setInterval(int intervalMS) {
-    if (mViewPager != null && intervalMS > 0) {
-      mViewPager.setIntervalTime(intervalMS);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.INDEX)
-  public void setIndex(int index) {
-    if (mViewPager != null && mAdapter != null) {
-      if (index >= mAdapter.getRealCount() || index < 0) {
-        initIndex = index;
-        return;
-      }
-
-      index = getRealIndex(index);
-      mViewPager.setCurrentItem(index);
-      if (mIndicator != null && mIndicator.getHostView() != null
-              && mIndicator.getHostView().getRealCurrentItem() != index) {
-        //OnPageChangeListener not triggered
-        WXLogUtils.d("setIndex >>>> correction indicator to " + index);
-        mIndicator.getHostView().setRealCurrentItem(index);
-        mIndicator.getHostView().invalidate();
-
-        if (mPageChangeListener != null && mAdapter != null) {
-          mPageChangeListener.onPageSelected(mAdapter.getFirst() + index);
-        }
-      }
-    }
-  }
-  @WXComponentProp(name = Constants.Name.SCROLLABLE)
-  public void setScrollable(boolean scrollable) {
-    if (mViewPager != null && mAdapter != null) {
-      mViewPager.setScrollable(scrollable);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.OFFSET_X_ACCURACY)
-  public void setOffsetXAccuracy(float accuracy) {
-    this.offsetXAccuracy = accuracy;
-  }
-
-  protected class SliderPageChangeListener implements OnPageChangeListener {
-
-    private int lastPos = -1;
-
-    @Override
-    public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
-
-    }
-
-    @Override
-    public void onPageSelected(int pos) {
-      if (mAdapter.getRealPosition(pos) == lastPos) {
-        return;
-      }
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.d("onPageSelected >>>>" + mAdapter.getRealPosition(pos) + " lastPos: " + lastPos);
-      }
-      if (mAdapter == null || mAdapter.getRealCount() == 0) {
-        return;
-      }
-
-      int realPosition = mAdapter.getRealPosition(pos);
-      if (mChildren == null || realPosition >= mChildren.size()) {
-        return;
-      }
-
-      if (getEvents().size() == 0) {
-        return;
-      }
-      WXEvent event = getEvents();
-      String ref = getRef();
-      if (event.contains(Constants.Event.CHANGE) && WXViewUtils.onScreenArea(getHostView())) {
-        params.put(INDEX, realPosition);
-
-        Map<String, Object> domChanges = new HashMap<>();
-        Map<String, Object> attrsChanges = new HashMap<>();
-        attrsChanges.put(INDEX, realPosition);
-        domChanges.put("attrs", attrsChanges);
-        WXSDKManager.getInstance().fireEvent(getInstanceId(), ref,
-            Constants.Event.CHANGE, params, domChanges);
-      }
-
-      mViewPager.requestLayout();
-      getHostView().invalidate();
-      lastPos = mAdapter.getRealPosition(pos);
-    }
-
-    @Override
-    public void onPageScrollStateChanged(int arg0) {
-      FrameLayout root = getHostView();
-      if (null != root) {
-        root.invalidate();
-      }
-    }
-  }
-
-  protected static class SliderOnScrollListener implements OnPageChangeListener {
-    private float lastPositionOffset = 99f;
-    private int selectedPosition;
-    private WXSlider target;
-
-    public SliderOnScrollListener(WXSlider target) {
-      this.target = target;
-      this.selectedPosition = target.mViewPager.superGetCurrentItem();
-    }
-
-    @Override
-    public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
-      if (lastPositionOffset == 99f) {
-        lastPositionOffset = positionOffset;
-        return;
-      }
-
-      float offset = positionOffset - lastPositionOffset;
-
-      if (Math.abs(offset) >= target.offsetXAccuracy) {
-        if (position == selectedPosition) {
-          //slide to left. positionOffset[0 -> 1]
-          Map<String,Object> event = new HashMap<>(1);
-          event.put(Constants.Name.OFFSET_X_RATIO, -positionOffset);
-          target.fireEvent(Constants.Event.SCROLL, event);
-        } else if (position < selectedPosition) {
-          //slide to right. positionOffset[1 -> 0]
-          Map<String,Object> event = new HashMap<>(1);
-          event.put(Constants.Name.OFFSET_X_RATIO, (1f - positionOffset));
-          target.fireEvent(Constants.Event.SCROLL, event);
-        }
-        lastPositionOffset = positionOffset;
-      }
-    }
-
-    @Override
-    public void onPageSelected(int position) {
-      selectedPosition = position;
-    }
-
-    @Override
-    public void onPageScrollStateChanged(int state) {
-
-      /**
-       * @homeblog@vip.qq.com
-       *
-       *  add scrollstart & scrollend event
-       *
-       */
-      switch (state) {
-        case ViewPager.SCROLL_STATE_IDLE:
-          lastPositionOffset = 99f;
-          target.fireEvent("scrollend");
-          break;
-        case ViewPager.SCROLL_STATE_DRAGGING:
-          target.fireEvent("scrollstart");
-          break;
-        case ViewPager.SCROLL_STATE_SETTLING:
-          break;
-
-      }
-    }
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  private void hackTwoItemsInfiniteScroll() {
-    if (mViewPager == null || mAdapter == null) {
-      return;
-    }
-    if (isInfinite) {
-      if (mAdapter.getRealCount() == 2) {
-        final GestureDetector gestureDetector = new GestureDetector(getContext(), new FlingGestureListener(mViewPager));
-        mViewPager.setOnTouchListener(new View.OnTouchListener() {
-          @Override
-          public boolean onTouch(View v, MotionEvent event) {
-            return gestureDetector.onTouchEvent(event);
-          }
-        });
-      } else {
-        mViewPager.setOnTouchListener(null);
-      }
-    }
-  }
-
-  private static class FlingGestureListener extends GestureDetector.SimpleOnGestureListener {
-    private static final int SWIPE_MIN_DISTANCE = WXViewUtils.dip2px(50);
-    private static final int SWIPE_MAX_OFF_PATH = WXViewUtils.dip2px(250);
-    private static final int SWIPE_THRESHOLD_VELOCITY = WXViewUtils.dip2px(200);
-    private WeakReference<WXCircleViewPager> pagerRef;
-
-    FlingGestureListener(WXCircleViewPager pager) {
-      this.pagerRef = new WeakReference<>(pager);
-    }
-
-    @Override
-    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
-      WXCircleViewPager mViewPager = pagerRef.get();
-      if (mViewPager == null) {
-        return false;
-      }
-
-      try {
-        if (Math.abs(e1.getY() - e2.getY()) > SWIPE_MAX_OFF_PATH) {
-          return false;
-        }
-
-        if(e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE
-                && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY
-                && mViewPager.superGetCurrentItem() == 1) {
-          // right to left swipe
-          mViewPager.setCurrentItem(0, false);
-          return true;
-        } else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE
-                && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY
-                && mViewPager.superGetCurrentItem() == 0) {
-          // left to right swipe
-          mViewPager.setCurrentItem(1, false);
-          return true;
-        }
-      } catch (Exception e) {
-        // ignore
-      }
-      return false;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSliderNeighbor.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSliderNeighbor.java
deleted file mode 100644
index bfcaa4b..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSliderNeighbor.java
+++ /dev/null
@@ -1,412 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.support.v4.view.ViewPager;
-import android.text.TextUtils;
-import android.view.Gravity;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.FrameLayout;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.BaseFrameLayout;
-import com.taobao.weex.ui.view.WXCircleIndicator;
-import com.taobao.weex.ui.view.WXCirclePageAdapter;
-import com.taobao.weex.ui.view.WXCircleViewPager;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.List;
-
-/**
- * Known Issus: In auto play mode, neighbor view not scaled or aplhaed rarely.
- *
- * Created by xingjiu on 16/8/18.
- */
-public class WXSliderNeighbor extends WXSlider {
-    public static final String NEIGHBOR_SCALE = "neighborScale"; // the init scale of neighbor page
-    public static final String NEIGHBOR_ALPHA = "neighborAlpha"; // the init alpha of neighbor page
-    public static final String NEIGHBOR_SPACE = "neighborSpace"; // the init space of neighbor page
-    public static final String CURRENT_ITEM_SCALE = "currentItemScale"; // the scale of middle item
-
-    private static final int DEFAULT_NEIGHBOR_SPACE = 25;
-    private static final float DEFAULT_NEIGHBOR_SCALE = 0.8F;
-    private static final float DEFAULT_NEIGHBOR_ALPHA = 0.6F;
-    private static final float DEFAULT_CURRENT_ITEM_SCALE = 0.9F;
-
-    private float mNeighborScale = DEFAULT_NEIGHBOR_SCALE;
-    private float mNeighborAlpha = DEFAULT_NEIGHBOR_ALPHA;
-    private float mNeighborSpace = DEFAULT_NEIGHBOR_SPACE;
-    private float mCurrentItemScale = DEFAULT_CURRENT_ITEM_SCALE;
-
-    private ZoomTransformer mCachedTransformer;
-
-    public WXSliderNeighbor(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-        super(instance, parent, basicComponentData);
-    }
-
-    public static class Creator implements ComponentCreator {
-        public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-            return new WXSliderNeighbor(instance, parent, basicComponentData);
-        }
-    }
-
-    @Override
-    public void bindData(WXComponent component) {
-        super.bindData(component);
-    }
-
-    @Override
-    protected BaseFrameLayout initComponentHostView(@NonNull Context context) {
-        BaseFrameLayout view = new BaseFrameLayout(context);
-
-        // init view pager
-        FrameLayout.LayoutParams pagerParams = new FrameLayout.LayoutParams(
-                FrameLayout.LayoutParams.MATCH_PARENT, FrameLayout.LayoutParams.MATCH_PARENT);
-        pagerParams.gravity = Gravity.CENTER;
-        mViewPager = new WXCircleViewPager(getContext());
-        mViewPager.setLayoutParams(pagerParams);
-
-        // init adapter
-        mAdapter = new WXCirclePageAdapter();
-        mViewPager.setAdapter(mAdapter);
-
-        // add to parent
-        view.addView(mViewPager);
-        mViewPager.addOnPageChangeListener(mPageChangeListener);
-
-        mViewPager.setOverScrollMode(View.OVER_SCROLL_NEVER);
-        registerActivityStateListener();
-
-        mViewPager.setPageTransformer(false, createTransformer());
-
-        return view;
-    }
-
-    ZoomTransformer createTransformer() {
-        if(mCachedTransformer == null) {
-            mCachedTransformer = new ZoomTransformer();
-        }
-        return mCachedTransformer;
-    }
-
-    @Override
-    public void addSubView(View view, final int index) {
-        if (view == null || mAdapter == null) {
-            return;
-        }
-
-        if (view instanceof WXCircleIndicator) {
-            return;
-        }
-
-        FrameLayout wrapper = new FrameLayout(getContext());
-        FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
-        params.gravity = Gravity.CENTER;
-        view.setLayoutParams(params);
-        wrapper.addView(view);
-        super.addSubView(wrapper,index);
-
-        updateAdapterScaleAndAlpha(mNeighborAlpha, mNeighborScale); // we need to set neighbor view status when added.
-
-        mViewPager.postDelayed(WXThread.secure(new Runnable() {
-            @Override
-            public void run() {
-                try {
-                    if(mViewPager.getRealCount() > 0 && index > 2) { // index > 2 mean more than two times, then need a fake drag
-                        // prevent a bug of init status. ZoomTransformer no called as excepted.
-                        mViewPager.beginFakeDrag();
-                        mViewPager.fakeDragBy(1); // must be 1
-                    }
-                }catch (IndexOutOfBoundsException e){
-                    // do nothing
-                } finally {
-                    try {
-                        mViewPager.endFakeDrag();
-                    }catch (Exception e) {
-                        // do nothing
-                    }
-                }
-            }
-        }), 50);
-    }
-
-    private void updateScaleAndAlpha(View view, float alpha, float scale) {
-        if(null == view) {
-            return;
-        }
-        if(alpha >= 0 && view.getAlpha() != alpha) {
-            view.setAlpha(alpha);
-        }
-        if(scale >= 0 && view.getScaleX() != scale) {
-            view.setScaleX(scale);
-            view.setScaleY(scale);
-        }
-    }
-
-    private void updateAdapterScaleAndAlpha(final float alpha, final float scale) {
-        final List<View> pageViews = mAdapter.getViews();
-        final int curPos = mViewPager.getCurrentItem();
-
-        if(pageViews.size() > 0) {
-            final View currentPage = pageViews.get(curPos);
-            updateScaleAndAlpha(((ViewGroup)currentPage).getChildAt(0), 1.0F, mCurrentItemScale);
-
-            if(pageViews.size() < 2) {
-                return;
-            }
-            //make sure View's width & height are measured.
-            currentPage.postDelayed(WXThread.secure(new Runnable() {
-                @Override
-                public void run() {
-                    //change left and right page's translation
-                    updateNeighbor(currentPage, alpha, scale);
-
-                }
-            }), 17);
-
-            // make sure only display view current, left, right.
-            int left = (curPos == 0) ? pageViews.size()-1 : curPos-1;
-            int right = (curPos == pageViews.size()-1) ? 0 : curPos+1;
-            for(int i =0; i<mAdapter.getRealCount(); i++) {
-                if(i != left && i != curPos && i != right) {
-                    ((ViewGroup)pageViews.get(i)).getChildAt(0).setAlpha(0F);
-                }
-            }
-        }
-    }
-
-    private void updateNeighbor(View currentPage, final float alpha, final float scale) {
-        final List<View> pageViews = mAdapter.getViews();
-        final int curPos = mViewPager.getCurrentItem();
-
-        float translation = calculateTranslation(currentPage);
-        int left = (curPos == 0) ? pageViews.size()-1 : curPos-1;
-        View leftPage = pageViews.get(left);
-        int right = (curPos == pageViews.size()-1) ? 0 : curPos+1;
-        View rightPage = pageViews.get(right);
-
-        if(pageViews.size() == 2) {
-            if(curPos == 0) {
-                moveRight(rightPage, translation, alpha, scale);
-            }else if(curPos == 1) {
-                moveLeft(leftPage, translation, alpha, scale);
-            }
-        } else {
-            moveLeft(leftPage, translation, alpha, scale);
-            moveRight(rightPage, translation, alpha, scale);
-        }
-    }
-
-    private void moveLeft(View page, float translation, float alpha, float scale) {
-        updateScaleAndAlpha(((ViewGroup)page).getChildAt(0), alpha, scale);
-        page.setTranslationX(translation);
-        ((ViewGroup)page).getChildAt(0).setTranslationX(translation);
-    }
-    private void moveRight(View page, float translation, float alpha, float scale) {
-        moveLeft(page, -translation, alpha, scale);
-    }
-
-    @WXComponentProp(name = NEIGHBOR_SCALE)
-    public void setNeighborScale(String input) {
-        float neighborScale = DEFAULT_NEIGHBOR_SCALE;
-        if (!TextUtils.isEmpty(input)) {
-            try {
-                neighborScale = Float.parseFloat(input);
-            } catch (NumberFormatException e) {
-            }
-        }
-
-        // addSubView is called before setProperty, so we need to modify the neighbor view in mAdapter.
-        if(this.mNeighborScale != neighborScale) {
-            this.mNeighborScale = neighborScale;
-            updateAdapterScaleAndAlpha(-1, neighborScale);
-        }
-    }
-
-    @WXComponentProp(name = NEIGHBOR_ALPHA)
-    public void setNeighborAlpha(String input) {
-        float neighborAlpha = DEFAULT_NEIGHBOR_ALPHA;
-        if (!TextUtils.isEmpty(input)) {
-            try {
-                neighborAlpha = Float.parseFloat(input);
-            } catch (NumberFormatException e) {
-            }
-        }
-
-        // The same work as setNeighborScale()
-        if(this.mNeighborAlpha != neighborAlpha) {
-            this.mNeighborAlpha = neighborAlpha;
-            updateAdapterScaleAndAlpha(neighborAlpha, -1);
-        }
-    }
-
-    @WXComponentProp(name = NEIGHBOR_SPACE)
-    @SuppressWarnings("unused")
-    public void setNeighborSpace(String input) {
-        float neighborSpace = DEFAULT_NEIGHBOR_SPACE;
-        if (!TextUtils.isEmpty(input)) {
-            try {
-                neighborSpace = Float.parseFloat(input);
-            } catch (NumberFormatException e) {
-            }
-        }
-
-        if(this.mNeighborSpace != neighborSpace) {
-            this.mNeighborSpace = neighborSpace;
-        }
-    }
-
-    @WXComponentProp(name = CURRENT_ITEM_SCALE)
-    @SuppressWarnings("unused")
-    public void setCurrentItemScale(String input) {
-        float currentItemScale = DEFAULT_CURRENT_ITEM_SCALE;
-        if (!TextUtils.isEmpty(input)) {
-            try {
-                currentItemScale = Float.parseFloat(input);
-            } catch (NumberFormatException e) {
-            }
-        }
-
-        if(this.mCurrentItemScale != currentItemScale) {
-            this.mCurrentItemScale = currentItemScale;
-            updateAdapterScaleAndAlpha(-1, -1);
-        }
-    }
-
-    @Override
-    protected boolean setProperty(String key, Object param) {
-        String input;
-        switch (key) {
-            case NEIGHBOR_SCALE:
-                input = WXUtils.getString(param, null);
-                if (input != null) {
-                    setNeighborScale(input);
-                }
-                return true;
-            case NEIGHBOR_ALPHA:
-                input = WXUtils.getString(param, null);
-                if (input != null) {
-                    setNeighborAlpha(input);
-                }
-                return true;
-            case NEIGHBOR_SPACE:
-                input = WXUtils.getString(param, null);
-                if (input != null) {
-                    setNeighborSpace(input);
-                }
-                return true;
-            case CURRENT_ITEM_SCALE:
-                input = WXUtils.getString(param, null);
-                if (input != null) {
-                    setCurrentItemScale(input);
-                }
-                return true;
-        }
-        return super.setProperty(key, param);
-    }
-
-    /**
-     * we need add translation for left and right card view.
-     * */
-    private float calculateTranslation(@NonNull View hostPage) {
-        if(!(hostPage instanceof ViewGroup)) {
-            return 0;
-        }
-        View realView = ((ViewGroup)hostPage).getChildAt(0);
-        float translation = (hostPage.getMeasuredWidth()-realView.getMeasuredWidth()*mNeighborScale)/4;
-        translation += ((hostPage.getMeasuredWidth()-realView.getMeasuredWidth() * mCurrentItemScale)/2 - WXViewUtils.getRealPxByWidth(mNeighborSpace, getInstance().getInstanceViewPortWidth()))/2 ;
-        return translation;
-    }
-
-    // Here is the trick.
-     class ZoomTransformer implements ViewPager.PageTransformer {
-        @Override
-        public void transformPage(View page, float position) {
-            int pagePosition = mAdapter.getPagePosition(page);
-            int curPosition = mViewPager.getCurrentItem();
-
-            int realCount = mAdapter.getRealCount();
-
-            boolean ignore = false;
-            if(curPosition != 0 && curPosition != realCount - 1 && Math.abs(pagePosition - curPosition) > 1)  {
-                ignore = true;
-            }
-            if(curPosition == 0 && pagePosition < realCount - 1 && pagePosition > 1) {
-                ignore = true;
-            }
-            if(curPosition == realCount - 1 && pagePosition < realCount - 2 && pagePosition > 0) {
-                ignore = true;
-            }
-            // just transfer the neighbor(left & right) page.
-            if(ignore) {
-                return;
-            }
-
-            View realView = ((ViewGroup)page).getChildAt(0);
-            if(realView == null){
-                return;
-            }
-            float alpha, scale;
-
-            if(position <= (-realCount + 1)) {
-                position = position + realCount;
-            }
-            if(position >= realCount - 1) {
-                position = position - realCount;
-            }
-
-            if (position >= -1 && position <= 1) {
-                float factor = Math.abs(Math.abs(position) - 1);
-                scale = mNeighborScale + factor * (mCurrentItemScale - mNeighborScale);
-                alpha = (1- mNeighborAlpha) * factor + mNeighborAlpha;
-
-                float translation = calculateTranslation(page);
-                if(position > 0){
-                    translation = (position*translation);
-                    realView.setTranslationX(-translation);
-                    page.setTranslationX(-translation);
-                }else if(position == 0){
-                    page.setTranslationX(0);
-                    realView.setTranslationX(0);
-                    updateAdapterScaleAndAlpha(mNeighborAlpha, mNeighborScale);
-                }else{
-                    if(realCount == 2 && Math.abs(position) == 1) {
-                        return;
-                    }
-                    translation = (-position*translation);
-                    realView.setTranslationX(translation);
-                    page.setTranslationX(translation);
-                }
-                realView.setScaleX(scale);
-                realView.setScaleY(scale);
-                realView.setAlpha(alpha);
-            }
-
-        }
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSwitch.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSwitch.java
deleted file mode 100644
index 714986e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXSwitch.java
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.view.View;
-import android.widget.CompoundButton;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.layout.ContentBoxMeasurement;
-import com.taobao.weex.layout.MeasureSize;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXSwitchView;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.HashMap;
-import java.util.Map;
-
-@Component(lazyload = false)
-
-public class WXSwitch extends WXComponent<WXSwitchView> {
-
-  private CompoundButton.OnCheckedChangeListener mListener;
-
-  @Deprecated
-  public WXSwitch(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-  public WXSwitch(final WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-    super(instance, parent, isLazy, basicComponentData);
-    setContentBoxMeasurement(new ContentBoxMeasurement() {
-      /** uiThread = false **/
-      @Override
-      public void measureInternal(float width, float height, int widthMeasureMode, int heightMeasureMode) {
-        mMeasureWidth = 0;
-        mMeasureHeight = 0;
-        try {
-          WXSwitchView wxSwitchView = new WXSwitchView(instance.getContext());
-          int widthSpec, heightSpec;
-          heightSpec = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
-          if (Float.isNaN(width)) {
-            widthSpec = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
-          } else {
-            widthSpec = View.MeasureSpec.makeMeasureSpec((int) width, View.MeasureSpec.AT_MOST);
-          }
-
-          wxSwitchView.measure(widthSpec, heightSpec);
-          mMeasureWidth = wxSwitchView.getMeasuredWidth();
-          mMeasureHeight = wxSwitchView.getMeasuredHeight();
-        } catch (RuntimeException e) {
-          WXLogUtils.e(WXLogUtils.getStackTrace(e));
-        }
-      }
-
-      /** uiThread = false **/
-      @Override
-      public void layoutBefore() {
-      }
-
-      /** uiThread = false **/
-      @Override
-      public void layoutAfter(float computedWidth, float computedHeight) {
-      }
-    });
-  }
-
-  @Override
-  protected WXSwitchView initComponentHostView(@NonNull Context context) {
-    return new WXSwitchView(context);
-  }
-
-
-  @Override
-  public void addEvent(String type) {
-    super.addEvent(type);
-    if (type != null && type.equals(Constants.Event.CHANGE) && getHostView() != null) {
-      if (mListener == null) {
-        mListener = new CompoundButton.OnCheckedChangeListener() {
-          @Override
-          public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
-            Map<String, Object> params = new HashMap<>(2);
-            params.put("value", isChecked);
-
-            Map<String, Object> domChanges = new HashMap<>();
-            Map<String, Object> attrsChanges = new HashMap<>();
-            attrsChanges.put("checked",Boolean.toString(isChecked));
-            domChanges.put("attrs",attrsChanges);
-            fireEvent(Constants.Event.CHANGE, params,domChanges);
-          }
-        };
-      }
-      getHostView().setOnCheckedChangeListener(mListener);
-    }
-  }
-
-  @Override
-  protected void removeEventFromView(String type) {
-    super.removeEventFromView(type);
-    if (getHostView() != null && Constants.Event.CHANGE.equals(type)) {
-      getHostView().setOnCheckedChangeListener(null);
-    }
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.CHECKED:
-        Boolean result = WXUtils.getBoolean(param, null);
-        if (result != null) {
-          setChecked(result);
-        }
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @WXComponentProp(name = Constants.Name.CHECKED)
-  public void setChecked(boolean checked) {
-    getHostView().setOnCheckedChangeListener(null);
-    getHostView().setChecked(checked);
-    getHostView().setOnCheckedChangeListener(mListener);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXText.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXText.java
deleted file mode 100644
index 1236e37..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXText.java
+++ /dev/null
@@ -1,241 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.support.annotation.NonNull;
-import android.support.v4.content.LocalBroadcastManager;
-import android.text.Layout;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.layout.measurefunc.TextContentBoxMeasurement;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.flat.FlatComponent;
-import com.taobao.weex.ui.flat.widget.TextWidget;
-import com.taobao.weex.ui.view.WXTextView;
-import com.taobao.weex.utils.FontDO;
-import com.taobao.weex.utils.TypefaceUtil;
-import com.taobao.weex.utils.WXLogUtils;
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Text component
- */
-@Component(lazyload = false)
-public class WXText extends WXComponent<WXTextView> implements FlatComponent<TextWidget> {
-
-  private TextWidget mTextWidget;
-
-  /**
-   * The default text size
-   **/
-  public static final int sDEFAULT_SIZE = 32;
-  private BroadcastReceiver mTypefaceObserver;
-  private String mFontFamily;
-
-  @Override
-  public boolean promoteToView(boolean checkAncestor) {
-    if (null != getInstance().getFlatUIContext()) {
-      return getInstance().getFlatUIContext().promoteToView(this, checkAncestor, WXText.class);
-    }
-    return false;
-  }
-
-  @Override
-  @NonNull
-  public TextWidget getOrCreateFlatWidget() {
-    if (mTextWidget == null) {
-      mTextWidget = new TextWidget(getInstance().getFlatUIContext());
-    }
-    return mTextWidget;
-  }
-
-  @Override
-  public boolean isVirtualComponent() {
-    return !promoteToView(true);
-  }
-
-  public static class Creator implements ComponentCreator {
-    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-      return new WXText(instance, parent, basicComponentData);
-    }
-  }
-
-  @Deprecated
-  public WXText(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, basicComponentData);
-  }
-
-  public WXText(WXSDKInstance instance,
-                WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-    setContentBoxMeasurement(new TextContentBoxMeasurement(this));
-  }
-
-  @Override
-  protected WXTextView initComponentHostView(@NonNull Context context) {
-    WXTextView textView = new WXTextView(context);
-    textView.holdComponent(this);
-    return textView;
-  }
-
-  @Override
-  public void updateExtra(Object extra) {
-    super.updateExtra(extra);
-    if(extra instanceof Layout) {
-      final Layout layout = (Layout) extra;
-      if (!promoteToView(true)) {
-        getOrCreateFlatWidget().updateTextDrawable(layout);
-      } else if (getHostView() != null && !extra.equals(getHostView().getTextLayout())) {
-        getHostView().setTextLayout(layout);
-        getHostView().invalidate();
-      }
-    }
-  }
-
-  @Override
-  protected void setAriaLabel(String label) {
-    WXTextView text = getHostView();
-    if (text != null) {
-      text.setAriaLabel(label);
-    }
-  }
-
-  @Override
-  public void refreshData(WXComponent component) {
-    super.refreshData(component);
-    if (component instanceof WXText) {
-      updateExtra(component.getExtra());
-    }
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.LINES:
-      case Constants.Name.FONT_SIZE:
-      case Constants.Name.FONT_WEIGHT:
-      case Constants.Name.FONT_STYLE:
-      case Constants.Name.COLOR:
-      case Constants.Name.TEXT_DECORATION:
-      case Constants.Name.TEXT_ALIGN:
-      case Constants.Name.TEXT_OVERFLOW:
-      case Constants.Name.LINE_HEIGHT:
-      case Constants.Name.VALUE:
-        return true;
-      case Constants.Name.FONT_FAMILY:
-        if (param != null) {
-          registerTypefaceObserver(param.toString());
-        }
-        return true;
-      default:
-        return super.setProperty(key, param);
-    }
-  }
-
-  @Override
-  protected Object convertEmptyProperty(String propName, Object originalValue) {
-    switch (propName) {
-      case Constants.Name.FONT_SIZE:
-        return WXText.sDEFAULT_SIZE;
-      case Constants.Name.COLOR:
-        return "black";
-    }
-    return super.convertEmptyProperty(propName, originalValue);
-  }
-
-  @Override
-  protected void createViewImpl() {
-    if(promoteToView(true)) {
-      super.createViewImpl();
-    }
-  }
-
-  @Override
-  public void destroy() {
-    super.destroy();
-    if (WXEnvironment.getApplication() != null && mTypefaceObserver != null) {
-      WXLogUtils.d("WXText", "Unregister the typeface observer");
-      LocalBroadcastManager.getInstance(WXEnvironment.getApplication()).unregisterReceiver(mTypefaceObserver);
-      mTypefaceObserver = null;
-    }
-  }
-
-  private void registerTypefaceObserver(String desiredFontFamily) {
-    if (WXEnvironment.getApplication() == null) {
-      WXLogUtils.w("WXText", "ApplicationContent is null on register typeface observer");
-      return;
-    }
-    mFontFamily = desiredFontFamily;
-    if (mTypefaceObserver != null) {
-      return;
-    }
-
-    mTypefaceObserver = new BroadcastReceiver() {
-      @Override
-      public void onReceive(Context context, Intent intent) {
-        String fontFamily = intent.getStringExtra("fontFamily");
-        if (!mFontFamily.equals(fontFamily)) {
-          return;
-        }
-
-        FontDO fontDO = TypefaceUtil.getFontDO(fontFamily);
-        if (fontDO != null && fontDO.getTypeface() != null && getHostView() != null) {
-          WXTextView hostView = getHostView();
-          Layout layout = hostView.getTextLayout();
-          if (layout != null) {
-            layout.getPaint().setTypeface(fontDO.getTypeface());
-          } else {
-            WXLogUtils.d("WXText", "Layout not created");
-          }
-          WXBridgeManager
-              .getInstance().markDirty(getInstanceId(), getRef(), true);
-          forceRelayout();
-
-        }
-      }
-    };
-
-    LocalBroadcastManager.getInstance(WXEnvironment.getApplication()).registerReceiver(mTypefaceObserver, new IntentFilter(TypefaceUtil.ACTION_TYPE_FACE_AVAILABLE));
-  }
-
-
-  @Override
-  protected void layoutDirectionDidChanged(boolean isRTL) {
-    forceRelayout();
-  }
-
-  private void forceRelayout(){
-    WXBridgeManager.getInstance().post(new Runnable() {
-      @Override
-      public void run() {
-        if(contentBoxMeasurement instanceof TextContentBoxMeasurement){
-          ((TextContentBoxMeasurement) contentBoxMeasurement).forceRelayout();
-        }
-      }
-    });
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXTextDecoration.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXTextDecoration.java
deleted file mode 100644
index 44638ff..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXTextDecoration.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-public enum WXTextDecoration {
-  INVALID,
-  NONE,
-  UNDERLINE,
-  LINETHROUGH,
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXVContainer.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXVContainer.java
deleted file mode 100644
index 167eeb5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXVContainer.java
+++ /dev/null
@@ -1,629 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.content.Intent;
-import android.support.annotation.Nullable;
-import android.support.v4.view.ViewCompat;
-import android.util.Pair;
-import android.view.Menu;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewParent;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXImageView;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.ArrayList;
-
-/**
- * All container components must implement this class
- */
-public abstract class WXVContainer<T extends ViewGroup> extends WXComponent<T> {
-
-  private static final String TAG = "WXVContainer";
-  protected ArrayList<WXComponent> mChildren = new ArrayList<>();
-  private BoxShadowHost mBoxShadowHost;
-
-  @Deprecated
-  public WXVContainer(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-  @Deprecated
-  public WXVContainer(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  public WXVContainer(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  /**
-   * Container will get focus before any of its descendants.
-   */
-  public void interceptFocus() {
-    T host = getHostView();
-    if (host != null) {
-      host.setFocusable(true);
-      host.setFocusableInTouchMode(true);
-      host.setDescendantFocusability(ViewGroup.FOCUS_BEFORE_DESCENDANTS);
-      host.requestFocus();
-    }
-  }
-
-  /**
-   * Container will can not receive focus
-   */
-  public void ignoreFocus() {
-    T host = getHostView();
-    if (host != null) {
-      host.setFocusable(false);
-      host.setFocusableInTouchMode(false);
-      host.clearFocus();
-    }
-  }
-
-  /**
-   * Offset top for children layout.
-   */
-  protected int getChildrenLayoutTopOffset() {
-    return 0;
-  }
-
-  /**
-   * use {@link #getHostView()} instead
-   */
-  @Deprecated
-  public ViewGroup getView() {
-    return getHostView();
-  }
-
-  @Override
-  public void applyLayoutAndEvent(WXComponent component) {
-    if (!isLazy()) {
-      if (component == null) {
-        component = this;
-      }
-      super.applyLayoutAndEvent(component);
-      int count = childCount();
-      for (int i = 0; i < count; i++) {
-        WXComponent child = getChild(i);
-        child.applyLayoutAndEvent(((WXVContainer) component).getChild(i));
-      }
-    }
-  }
-
-  /**
-   * Get or generate new layout parameter for child view
-   */
-  public ViewGroup.LayoutParams getChildLayoutParams(WXComponent child, View childView, int width, int height, int left, int right, int top, int bottom) {
-    ViewGroup.LayoutParams lp = null;
-    if (childView != null) {
-      lp = childView.getLayoutParams();
-    }
-
-    if(lp == null) {
-      lp = new ViewGroup.LayoutParams(width,height);
-    }else{
-      lp.width = width;
-      lp.height = height;
-      if(lp instanceof ViewGroup.MarginLayoutParams){
-        this.setMarginsSupportRTL((ViewGroup.MarginLayoutParams) lp, left, top, right, bottom);
-      }
-    }
-    return lp;
-  }
-
-
-  public Scrollable getFirstScroller() {
-    if (this instanceof Scrollable) {
-      return (Scrollable) this;
-    } else {
-      for (int i = 0; i < getChildCount(); i++) {
-        Scrollable scrollable = getChild(i).getFirstScroller();
-        if (scrollable != null) {
-          return scrollable;
-        }
-      }
-    }
-    return null;
-  }
-
-  @Override
-  public void bindData(WXComponent component) {
-    if (!isLazy()) {
-      if (component == null) {
-        component = this;
-      }
-      super.bindData(component);
-      int count = childCount();
-      for (int i = 0; i < count; i++) {
-        getChild(i).bindData(((WXVContainer) component).getChild(i));
-      }
-    }
-  }
-
-  @Override
-  public void refreshData(WXComponent component) {
-    if (component == null) {
-      component = this;
-    }
-    super.refreshData(component);
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).refreshData(((WXVContainer) component).getChild(i));
-    }
-  }
-
-  /**
-   * return real View
-   */
-  @Override
-  public ViewGroup getRealView() {
-    return (ViewGroup) super.getRealView();
-  }
-
-  @Override
-  public void createViewImpl() {
-    super.createViewImpl();
-    int count = childCount();
-    for (int i = 0; i < count; ++i) {
-      createChildViewAt(i);
-    }
-    if (getHostView() != null) {
-      getHostView().setClipToPadding(false);
-    }
-  }
-
-  @Override
-  public void destroy() {
-    if (mChildren != null) {
-      int count = mChildren.size();
-      for (int i = 0; i < count; ++i) {
-        mChildren.get(i).destroy();
-      }
-      mChildren.clear();
-    }
-    super.destroy();
-  }
-
-  /**
-   * recycle component resources
-   */
-  public void recycled() {
-    if (mChildren != null && !isFixed() && getAttrs().canRecycled()) {
-      int count = mChildren.size();
-      for (int i = 0; i < count; ++i) {
-        mChildren.get(i).recycled();
-      }
-    }
-    super.recycled();
-
-  }
-
-  @Override
-  public View detachViewAndClearPreInfo() {
-    View original = super.detachViewAndClearPreInfo();
-    if (mChildren != null) {
-      int count = childCount();
-      for (int i = 0; i < count; ++i) {
-        mChildren.get(i).detachViewAndClearPreInfo();
-      }
-    }
-    return original;
-  }
-
-  public int childCount() {
-    return mChildren == null ? 0 : mChildren.size();
-  }
-
-  public WXComponent getChild(int index) {
-    if (mChildren == null || index < 0 || index >= mChildren.size()) {
-      //To avoid index out of bounds
-      return null;
-    }
-    return mChildren.get(index);
-  }
-
-  public int getChildCount() {
-    return childCount();
-  }
-
-  public void addChild(WXComponent child) {
-    addChild(child, -1);
-  }
-
-  public void addChild(WXComponent child, int index) {
-    if (child == null || index < -1) {
-      return;
-    }
-    child.mDeepInComponentTree = this.mDeepInComponentTree +1;
-    getInstance().setMaxDomDeep(child.mDeepInComponentTree);
-    int count = mChildren.size();
-    index = index >= count ? -1 : index;
-    if (index == -1) {
-      mChildren.add(child);
-    } else {
-      mChildren.add(index, child);
-    }
-  }
-
-  public final int indexOf(WXComponent comp) {
-    return mChildren.indexOf(comp);
-  }
-
-  public void createChildViewAt(int index) {
-    Pair<WXComponent, Integer> ret = rearrangeIndexAndGetChild(index);
-    if (ret.first != null) {
-      WXComponent child = ret.first;
-      child.createView();
-      if (!child.isVirtualComponent()) {
-        addSubView(child.getHostView(), ret.second);
-      }
-    }
-  }
-
-  protected Pair<WXComponent, Integer> rearrangeIndexAndGetChild(int index) {
-    int indexToCreate = index;
-    if (indexToCreate < 0) {
-      indexToCreate = childCount() - 1;
-    }
-
-    if (indexToCreate < 0) {
-      return new Pair<>(null, indexToCreate);
-    } else {
-      return new Pair<>(getChild(indexToCreate), indexToCreate);
-    }
-  }
-
-  public void addSubView(View child, int index) {
-    if (child == null || getRealView() == null) {
-      return;
-    }
-
-    int count = getRealView().getChildCount();
-    index = index >= count ? -1 : index;
-    if (index == -1) {
-      getRealView().addView(child);
-    } else {
-      getRealView().addView(child, index);
-    }
-    WXSDKInstance instance = getInstance();
-    if (null != instance){
-      instance.getApmForInstance().hasAddView = true;
-    }
-  }
-
-  public void remove(WXComponent child, boolean destroy) {
-    if (child == null || mChildren == null || mChildren.size() == 0) {
-      return;
-    }
-
-    mChildren.remove(child);
-    if (getInstance() != null
-            && getInstance().getRootView() != null
-            && child.isFixed()) {
-      getInstance().removeFixedView(child.getHostView());
-    } else if (getRealView() != null) {
-      if (!child.isVirtualComponent()) {
-        ViewParent parent = null;
-        if(child.getParent() instanceof  WXScroller){
-          if(child.getHostView() != null){
-            parent = child.getHostView().getParent();
-          }
-        }
-        if(parent != null && parent instanceof  ViewGroup){
-          ((ViewGroup) parent).removeView(child.getHostView());
-        }else{
-          getRealView().removeView(child.getHostView());
-        }
-      } else {
-        child.removeVirtualComponent();
-      }
-    }
-    if (destroy) {
-      child.destroy();
-    }
-  }
-
-  @Override
-  public void notifyAppearStateChange(String wxEventType, String direction) {
-    super.notifyAppearStateChange(wxEventType, direction);
-    if (getHostView() == null || mChildren == null) {
-      return;
-    }
-    for (WXComponent component : mChildren) {
-      if (component.getHostView() != null && !(component.getHostView().getVisibility() == View.VISIBLE)) {
-        wxEventType = Constants.Event.DISAPPEAR;
-      }
-      component.notifyAppearStateChange(wxEventType, direction);
-    }
-  }
-
-  /********************************************************
-   *  begin hook Activity life cycle callback             *
-   ********************************************************/
-  @Override
-  public void onActivityCreate() {
-    super.onActivityCreate();
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onActivityCreate();
-    }
-  }
-
-  @Override
-  public void onActivityStart() {
-    super.onActivityStart();
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onActivityStart();
-    }
-
-  }
-
-  @Override
-  public void onActivityPause() {
-    super.onActivityPause();
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onActivityPause();
-    }
-  }
-
-  @Override
-  public void onActivityResume() {
-    super.onActivityResume();
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onActivityResume();
-    }
-  }
-
-  @Override
-  public void onActivityStop() {
-    super.onActivityStop();
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onActivityStop();
-    }
-  }
-
-  @Override
-  public void onActivityDestroy() {
-    super.onActivityDestroy();
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onActivityDestroy();
-    }
-
-  }
-
-  @Override
-  public boolean onActivityBack() {
-    super.onActivityBack();
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onActivityBack();
-    }
-    return false;
-  }
-
-  @Override
-  public void onActivityResult(int requestCode, int resultCode, Intent data) {
-    super.onActivityResult(requestCode, resultCode, data);
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onActivityResult(requestCode, resultCode, data);
-    }
-
-  }
-
-  public boolean onCreateOptionsMenu(Menu menu) {
-    super.onCreateOptionsMenu(menu);
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onCreateOptionsMenu(menu);
-    }
-    return false;
-  }
-
-
-  @Override
-  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
-    super.onRequestPermissionsResult(requestCode, permissions, grantResults);
-
-    int count = childCount();
-    for (int i = 0; i < count; i++) {
-      getChild(i).onRequestPermissionsResult(requestCode, permissions, grantResults);
-    }
-  }
-
-  @Override
-  public void onRenderFinish(@RenderState int state) {
-    for (int i = 0; i < getChildCount(); i++) {
-      WXComponent child = getChild(i);
-      child.mTraceInfo.uiQueueTime = mTraceInfo.uiQueueTime;
-      child.onRenderFinish(state);
-    }
-    super.onRenderFinish(state);
-  }
-
-  @JSMethod
-  public void releaseImageList(String viewTreeRecycle){
-    if(getHostView() == null
-            || !ViewCompat.isAttachedToWindow(getHostView())
-            || !(getHostView() instanceof  ViewGroup)){
-      return;
-    }
-    boolean isViewTree = WXUtils.getBoolean(viewTreeRecycle, false);
-    if(isViewTree){
-      doViewTreeRecycleImageView(getHostView(), true);
-    }else{
-      int count = getChildCount();
-      for(int i=0; i<count; i++){
-        WXComponent component =  getChild(i);
-        if(component instanceof  WXImage && ((WXImage) component).getHostView() instanceof WXImageView){
-          WXImageView imageView = (WXImageView) component.getHostView();
-          if(imageView != null && ViewCompat.isAttachedToWindow(imageView)){
-            imageView.autoReleaseImage();
-          }
-        }else if(component instanceof  WXVContainer){
-          ((WXVContainer) component).releaseImageList(viewTreeRecycle);
-        }
-      }
-    }
-  }
-
-  @JSMethod
-  public void recoverImageList(String viewTreeRecycle){
-    if(getHostView() == null
-            || !ViewCompat.isAttachedToWindow(getHostView())
-            || !(getHostView() instanceof  ViewGroup)){
-      return;
-    }
-    boolean isViewTree = WXUtils.getBoolean(viewTreeRecycle, false);
-    if(isViewTree){
-      doViewTreeRecycleImageView(getHostView(), false);
-    }else{
-      int count = getChildCount();
-      for(int i=0; i<count; i++){
-        WXComponent component =  getChild(i);
-        if(component instanceof  WXImage && ((WXImage) component).getHostView() instanceof WXImageView){
-          WXImageView imageView = (WXImageView) component.getHostView();
-          if(imageView != null && ViewCompat.isAttachedToWindow(imageView)){
-            imageView.autoRecoverImage();
-          }
-        }else if(component instanceof  WXVContainer){
-          ((WXVContainer) component).recoverImageList(viewTreeRecycle);
-        }
-      }
-    }
-  }
-
-  /**
-   * transverse view tree, and recycle wximageview in container
-   * */
-  private void doViewTreeRecycleImageView(ViewGroup viewGroup, boolean isRelease){
-    int count = viewGroup.getChildCount();
-    for(int i=0; i<count; i++){
-      View view = viewGroup.getChildAt(i);
-      if(view instanceof  WXImageView){
-        if(isRelease){
-          ((WXImageView) view).autoReleaseImage();
-        }else{
-          ((WXImageView) view).autoRecoverImage();
-        }
-      }else if(view instanceof  ViewGroup){
-        doViewTreeRecycleImageView((ViewGroup) view, isRelease);
-      }
-    }
-  }
-
-
-  public void requestDisallowInterceptTouchEvent(boolean requestDisallowInterceptTouchEvent) {
-    if(mGesture != null){
-      if(mGesture.isRequestDisallowInterceptTouchEvent()){
-        return;
-      }
-      mGesture.setRequestDisallowInterceptTouchEvent(requestDisallowInterceptTouchEvent);
-    }
-    if(getParent() != null){
-      getParent().requestDisallowInterceptTouchEvent(requestDisallowInterceptTouchEvent);
-    }
-  }
-
-  /********************************
-   *  end hook Activity life cycle callback
-   ********************************************************/
-
-  public @Nullable
-  View getBoxShadowHost(boolean isClear) {
-    if (isClear) {
-      // Return existed host if want clear shadow
-      return mBoxShadowHost;
-    }
-
-    ViewGroup hostView = getHostView();
-    if (hostView == null) {
-      return null;
-    }
-
-    try {
-      String type = getComponentType();
-      if (WXBasicComponentType.DIV.equals(type)) {
-        WXLogUtils.d("BoxShadow", "Draw box-shadow with BoxShadowHost on div: " + toString());
-        if (mBoxShadowHost == null) {
-          mBoxShadowHost = new BoxShadowHost(getContext());
-          WXViewUtils.setBackGround(mBoxShadowHost, null, this);
-
-          hostView.addView(mBoxShadowHost);
-        }
-
-        CSSShorthand padding = this.getPadding();
-        CSSShorthand border = this.getBorder();
-
-        int left = (int) (padding.get(CSSShorthand.EDGE.LEFT) + border.get(CSSShorthand.EDGE.LEFT));
-        int top = (int) (padding.get(CSSShorthand.EDGE.TOP) + border.get(CSSShorthand.EDGE.TOP));
-        int right = (int) (padding.get(CSSShorthand.EDGE.RIGHT) + border.get(CSSShorthand.EDGE.RIGHT));
-        int bottom = (int) (padding.get(CSSShorthand.EDGE.BOTTOM) + border.get(CSSShorthand.EDGE.BOTTOM));
-
-        ViewGroup.MarginLayoutParams layoutParams = new ViewGroup.MarginLayoutParams(hostView.getLayoutParams()) ;
-        this.setMarginsSupportRTL(layoutParams, -left, -top, -right, -bottom);
-
-        mBoxShadowHost.setLayoutParams(layoutParams);
-        
-        hostView.removeView(mBoxShadowHost);
-        hostView.addView(mBoxShadowHost);
-        return mBoxShadowHost;
-      }
-    } catch (Throwable t) {
-      WXLogUtils.w("BoxShadow", t);
-    }
-    return hostView;
-  }
-
-  private class BoxShadowHost extends View {
-    public BoxShadowHost(Context context) {
-      super(context);
-    }
-  }
-
-  public void appendTreeCreateFinish() {
-    
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXVideo.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXVideo.java
deleted file mode 100644
index 0851825..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXVideo.java
+++ /dev/null
@@ -1,269 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.media.MediaPlayer;
-import android.net.Uri;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-import android.view.View;
-import android.widget.FrameLayout;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.WXVideoView;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.HashMap;
-import java.util.Map;
-@Component(lazyload = false)
-
-public class WXVideo extends WXComponent<FrameLayout> {
-
-  private boolean mAutoPlay;
-  private WXVideoView.Wrapper mWrapper;
-
-  /**
-   * package
-   **/
-  boolean mPrepared;
-  private boolean mError;
-
-  @Deprecated
-  public WXVideo(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-  public WXVideo(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-    super(instance, parent, isLazy, basicComponentData);
-  }
-
-  @Override
-  protected FrameLayout initComponentHostView(@NonNull Context context) {
-    final WXVideoView.Wrapper video = new WXVideoView.Wrapper(context);
-    video.setOnErrorListener(new MediaPlayer.OnErrorListener() {
-
-      @Override
-      public boolean onError(MediaPlayer mp, int what, int extra) {
-        if (WXEnvironment.isApkDebugable()) {
-          WXLogUtils.d("Video", "onError:" + what);
-        }
-        video.getProgressBar().setVisibility(View.GONE);
-        mPrepared = false;
-        mError = true;
-
-        if (getEvents().contains(Constants.Event.FAIL)) {
-          WXVideo.this.notify(Constants.Event.FAIL, Constants.Value.STOP);
-        }
-        return true;
-      }
-    });
-
-    video.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
-
-      @Override
-      public void onPrepared(MediaPlayer mediaPlayer) {
-        if (WXEnvironment.isApkDebugable()) {
-          WXLogUtils.d("Video", "onPrepared");
-        }
-        video.getProgressBar().setVisibility(View.GONE);
-        mPrepared = true;
-        if (mAutoPlay) {
-          video.start();
-        }
-
-        //callback from video view, so videoview should not null
-        WXVideoView videoView = video.getVideoView();
-        videoView.seekTo(5);
-
-        if (video.getMediaController() != null) {
-          if (!mStopped) {
-            video.getMediaController().show(3);
-          } else {
-            video.getMediaController().hide();
-          }
-        }
-
-        mStopped = false;
-      }
-    });
-
-    video.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
-
-      @Override
-      public void onCompletion(MediaPlayer mediaPlayer) {
-        if (WXEnvironment.isApkDebugable()) {
-          WXLogUtils.d("Video", "onCompletion");
-        }
-        if (getEvents().contains(Constants.Event.FINISH)) {
-          WXVideo.this.notify(Constants.Event.FINISH, Constants.Value.STOP);
-        }
-      }
-    });
-
-    video.setOnVideoPauseListener(new WXVideoView.VideoPlayListener() {
-
-      @Override
-      public void onPause() {
-        if (WXEnvironment.isApkDebugable()) {
-          WXLogUtils.d("Video", "onPause");
-        }
-        if (getEvents().contains(Constants.Event.PAUSE)) {
-          WXVideo.this.notify(Constants.Event.PAUSE, Constants.Value.PAUSE);
-        }
-      }
-
-      @Override
-      public void onStart() {
-        if (WXEnvironment.isApkDebugable()) {
-          WXLogUtils.d("Video", "onStart");
-        }
-
-        if (getEvents().contains(Constants.Event.START)) {
-          WXVideo.this.notify(Constants.Event.START, Constants.Value.PLAY);
-        }
-      }
-    });
-    mWrapper = video;
-    return video;
-  }
-
-  private void notify(String event, String newStatus) {
-    Map<String, Object> params = new HashMap<>(2);
-    params.put(Constants.Name.PLAY_STATUS, newStatus);
-    params.put("timeStamp", System.currentTimeMillis());
-
-    Map<String, Object> domChanges = new HashMap<>();
-    Map<String, Object> attrsChanges = new HashMap<>();
-    attrsChanges.put(Constants.Name.PLAY_STATUS, newStatus);
-    domChanges.put("attrs", attrsChanges);
-
-    WXSDKManager.getInstance().fireEvent(getInstanceId(), getRef(), event, params, domChanges);
-  }
-
-  @Override
-  public void bindData(WXComponent component) {
-    super.bindData(component);
-    addEvent(Constants.Event.APPEAR);
-  }
-
-  @Override
-  public void notifyAppearStateChange(String wxEventType, String direction) {
-    super.notifyAppearStateChange(wxEventType, direction);
-    mWrapper.createVideoViewIfVisible();
-  }
-
-  @Override
-  public void destroy() {
-    super.destroy();
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case Constants.Name.SRC:
-        String src = WXUtils.getString(param, null);
-        if (src != null) {
-          setSrc(src);
-        }
-        return true;
-      case Constants.Name.AUTO_PLAY:
-      case Constants.Name.AUTOPLAY:
-        Boolean result = WXUtils.getBoolean(param, null);
-        if (result != null) {
-          setAutoPlay(result);
-        }
-        return true;
-      case Constants.Name.ZORDERTOP:
-        Boolean zOrderTop = WXUtils.getBoolean(param, null);
-        if (zOrderTop != null) {
-            mWrapper.getVideoView().setZOrderOnTop(zOrderTop);
-        }
-        return true;
-      case Constants.Name.PLAY_STATUS:
-        String status = WXUtils.getString(param, null);
-        if (status != null) {
-          setPlaystatus(status);
-        }
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @WXComponentProp(name = Constants.Name.SRC)
-  public void setSrc(String src) {
-    if (TextUtils.isEmpty(src) || getHostView() == null) {
-      return;
-    }
-
-    if (!TextUtils.isEmpty(src)) {
-      WXSDKInstance instance = getInstance();
-      mWrapper.setVideoURI(instance.rewriteUri(Uri.parse(src), URIAdapter.VIDEO));
-      mWrapper.getProgressBar().setVisibility(View.VISIBLE);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.AUTO_PLAY)
-  public void setAutoPlay(boolean autoPlay) {
-    mAutoPlay = autoPlay;
-    if(autoPlay){
-      mWrapper.createIfNotExist();
-      mWrapper.start();
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.CONTROLS)
-  public void setControls(String controls) {
-    if (TextUtils.equals("controls", controls)) {
-      mWrapper.setControls(true);
-    } else if (TextUtils.equals("nocontrols", controls)) {
-      mWrapper.setControls(false);
-    }
-  }
-
-  private boolean mStopped;
-
-  @WXComponentProp(name = Constants.Name.PLAY_STATUS)
-  public void setPlaystatus(String playstatus) {
-
-    if (mPrepared && !mError && !mStopped) {
-      if (playstatus.equals(Constants.Value.PLAY)) {
-        mWrapper.start();
-      } else if (playstatus.equals(Constants.Value.PAUSE)) {
-        mWrapper.pause();
-      } else if (playstatus.equals(Constants.Value.STOP)) {
-        mWrapper.stopPlayback();
-        mStopped = true;
-      }
-    } else if ((mError || mStopped) && playstatus.equals(Constants.Value.PLAY)) {
-      mError = false;
-      mWrapper.resume();
-
-      mWrapper.getProgressBar().setVisibility(View.VISIBLE);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXWeb.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/WXWeb.java
deleted file mode 100644
index a536c46..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/WXWeb.java
+++ /dev/null
@@ -1,228 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.content.Context;
-import android.net.Uri;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-import android.view.View;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.view.IWebView;
-import com.taobao.weex.ui.view.WXWebView;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.HashMap;
-import java.util.Map;
-@Component(lazyload = false)
-
-public class WXWeb extends WXComponent {
-
-    public static final String GO_BACK = "goBack";
-    public static final String GO_FORWARD = "goForward";
-    public static final String RELOAD = "reload";
-    public static final String POST_MESSAGE = "postMessage";
-    protected IWebView mWebView;
-
-    @Deprecated
-    public WXWeb(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-        this(instance, parent, isLazy, basicComponentData);
-    }
-
-    public WXWeb(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-        super(instance, parent, isLazy, basicComponentData);
-        createWebView();
-    }
-
-    protected void createWebView(){
-        String origin = null;
-        try {
-            String bundleUrl = WXSDKManager.getInstance().getSDKInstance(getInstanceId()).getBundleUrl();
-            Uri uri = Uri.parse(bundleUrl);
-            String scheme = uri.getScheme();
-            String authority = uri.getAuthority();
-            if (!TextUtils.isEmpty(scheme) && !TextUtils.isEmpty(authority)) {
-                origin = scheme + "://" + authority;
-            }
-        } catch (Exception e) {
-            // do noting
-        }
-        mWebView = new WXWebView(getContext(), origin);
-    }
-
-    @Override
-    protected View initComponentHostView(@NonNull Context context) {
-        mWebView.setOnErrorListener(new IWebView.OnErrorListener() {
-            @Override
-            public void onError(String type, Object message) {
-                fireEvent(type, message);
-            }
-        });
-        mWebView.setOnPageListener(new IWebView.OnPageListener() {
-            @Override
-            public void onReceivedTitle(String title) {
-                if (getEvents().contains(Constants.Event.RECEIVEDTITLE)) {
-                    Map<String, Object> params = new HashMap<>();
-                    params.put("title", title);
-                    fireEvent(Constants.Event.RECEIVEDTITLE, params);
-                }
-            }
-
-            @Override
-            public void onPageStart(String url) {
-                if (getEvents().contains(Constants.Event.PAGESTART)) {
-                    Map<String, Object> params = new HashMap<>();
-                    params.put("url", url);
-                    fireEvent(Constants.Event.PAGESTART, params);
-                }
-            }
-
-            @Override
-            public void onPageFinish(String url, boolean canGoBack, boolean canGoForward) {
-                if (getEvents().contains(Constants.Event.PAGEFINISH)) {
-                    Map<String, Object> params = new HashMap<>();
-                    params.put("url", url);
-                    params.put("canGoBack", canGoBack);
-                    params.put("canGoForward", canGoForward);
-                    fireEvent(Constants.Event.PAGEFINISH, params);
-                }
-            }
-        });
-        mWebView.setOnMessageListener(new IWebView.OnMessageListener() {
-            @Override
-            public void onMessage(Map<String, Object> params) {
-                fireEvent(Constants.Event.ONMESSAGE, params);
-            }
-        });
-        return mWebView.getView();
-    }
-
-    @Override
-    public void destroy() {
-        super.destroy();
-        getWebView().destroy();
-    }
-
-    @Override
-    protected boolean setProperty(String key, Object param) {
-        switch (key) {
-            case Constants.Name.SHOW_LOADING:
-                Boolean result = WXUtils.getBoolean(param,null);
-                if (result != null)
-                    setShowLoading(result);
-                return true;
-            case Constants.Name.SRC:
-                String src = WXUtils.getString(param,null);
-                if (src != null)
-                    setUrl(src);
-                return true;
-            case Constants.Name.SOURCE:
-                String source = WXUtils.getString(param,null);
-                if (source != null)
-                    setSource(source);
-                return true;
-        }
-        return super.setProperty(key,param);
-    }
-
-    @WXComponentProp(name = Constants.Name.SHOW_LOADING)
-    public void setShowLoading(boolean showLoading) {
-        getWebView().setShowLoading(showLoading);
-    }
-
-    @WXComponentProp(name = Constants.Name.SRC)
-    public void setUrl(String url) {
-        if (TextUtils.isEmpty(url) || getHostView() == null) {
-            return;
-        }
-        if (!TextUtils.isEmpty(url)) {
-            loadUrl(getInstance().rewriteUri(Uri.parse(url), URIAdapter.WEB).toString());
-        }
-    }
-
-    @WXComponentProp(name = Constants.Name.SOURCE)
-    public void setSource(String source) {
-        if (!TextUtils.isEmpty(source) && getHostView() != null) {
-            loadDataWithBaseURL(source);
-        }
-    }
-
-    public void setAction(String action, Object data) {
-        if (!TextUtils.isEmpty(action)) {
-            if (action.equals(GO_BACK)) {
-                goBack();
-            } else if (action.equals(GO_FORWARD)) {
-                goForward();
-            } else if (action.equals(RELOAD)) {
-                reload();
-            } else if (action.equals(POST_MESSAGE)) {
-                postMessage(data);
-            }
-        }
-    }
-
-    private void fireEvent(String type, Object message) {
-        if (getEvents().contains(Constants.Event.ERROR)) {
-            Map<String, Object> params = new HashMap<>();
-            params.put("type", type);
-            params.put("errorMsg", message);
-            fireEvent(Constants.Event.ERROR, params);
-        }
-    }
-
-    private void loadUrl(String url) {
-        getWebView().loadUrl(url);
-    }
-
-    private void loadDataWithBaseURL(String source) {
-        getWebView().loadDataWithBaseURL(source);
-    }
-
-    @JSMethod
-    public void reload() {
-        getWebView().reload();
-    }
-
-    @JSMethod
-    public void goForward() {
-        getWebView().goForward();
-    }
-
-    @JSMethod
-    public void goBack() {
-        getWebView().goBack();
-    }
-
-    @JSMethod
-    public void postMessage(Object msg) {
-        getWebView().postMessage(msg);
-    }
-
-    private IWebView getWebView() {
-        return mWebView;
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/basic/WXBasicComponent.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/basic/WXBasicComponent.java
deleted file mode 100644
index 4164475..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/basic/WXBasicComponent.java
+++ /dev/null
@@ -1,232 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.basic;
-
-import android.support.annotation.NonNull;
-import android.view.View;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.action.GraphicPosition;
-import com.taobao.weex.ui.action.GraphicSize;
-import com.taobao.weex.ui.component.WXBasicComponentType;
-import com.taobao.weex.ui.component.WXComponent;
-import java.util.Map;
-import java.util.Set;
-
-public abstract class WXBasicComponent<T extends View> {
-
-  private Object mExtra;
-  private String mComponentType;
-  private String mRef;
-  private GraphicPosition mLayoutPosition;
-  private GraphicSize mLayoutSize;
-  private boolean mIsLayoutRTL;
-  private BasicComponentData mBasicComponentData;
-
-  private int mViewPortWidth = 750;
-
-  public WXBasicComponent(BasicComponentData basicComponentData) {
-    this.mBasicComponentData = basicComponentData;
-    this.mRef = basicComponentData.mRef;
-    this.mComponentType = basicComponentData.mComponentType;
-  }
-
-  public BasicComponentData getBasicComponentData() {
-    return mBasicComponentData;
-  }
-
-  protected void bindComponent(WXComponent component) {
-    mComponentType = component.getComponentType();
-    mRef = component.getRef();
-  }
-
-  public final @NonNull
-  WXStyle getStyles() {
-    return mBasicComponentData.getStyles();
-  }
-
-  public final @NonNull
-  WXAttr getAttrs() {
-    return mBasicComponentData.getAttrs();
-  }
-
-  public final @NonNull
-  WXEvent getEvents() {
-    return mBasicComponentData.getEvents();
-  }
-
-  /**
-   * Get this node's margin, as defined by cssstyle + default margin.
-   */
-  public final @NonNull
-  CSSShorthand getMargin() {
-    return mBasicComponentData.getMargin();
-  }
-
-  /**
-   * Get this node's padding, as defined by cssstyle + default padding.
-   */
-  public final @NonNull
-  CSSShorthand getPadding() {
-    return mBasicComponentData.getPadding();
-  }
-
-  /**
-   * Get this node's border, as defined by cssstyle.
-   */
-  public @NonNull
-  CSSShorthand getBorder() {
-    return mBasicComponentData.getBorder();
-  }
-
-  public final void setMargins(@NonNull CSSShorthand margins) {
-    mBasicComponentData.setMargins(margins);
-  }
-
-  public final void setPaddings(@NonNull CSSShorthand paddings) {
-    mBasicComponentData.setPaddings(paddings);
-  }
-
-  public final void setBorders(@NonNull CSSShorthand borders) {
-    mBasicComponentData.setBorders(borders);
-  }
-
-  public final void addAttr(Map<String, Object> attrs) {
-    if (attrs == null || attrs.isEmpty()) {
-      return;
-    }
-    mBasicComponentData.addAttr(attrs);
-  }
-
-  public final void addStyle(Map<String, Object> styles) {
-    if (styles == null || styles.isEmpty()) {
-      return;
-    }
-    mBasicComponentData.addStyle(styles);
-  }
-
-  public final void addStyle(Map<String, Object> styles, boolean byPesudo) {
-    if (styles == null || styles.isEmpty()) {
-      return;
-    }
-    mBasicComponentData.addStyle(styles, byPesudo);
-  }
-
-  public final void updateStyle(Map<String, Object> styles, boolean byPesudo){
-    if (styles == null || styles.isEmpty()) {
-      return;
-    }
-    mBasicComponentData.getStyles().updateStyle(styles, byPesudo);
-  }
-
-  public final void addEvent(Set<String> events) {
-    if (events == null || events.isEmpty()) {
-      return;
-    }
-
-    mBasicComponentData.addEvent(events);
-  }
-
-  public final void addShorthand(Map<String, String> shorthand) {
-    if (!shorthand.isEmpty() && mBasicComponentData != null) {
-      mBasicComponentData.addShorthand(shorthand);
-    }
-  }
-
-  public int getViewPortWidth() {
-    return mViewPortWidth;
-  }
-
-  public void setViewPortWidth(int mViewPortWidth) {
-    this.mViewPortWidth = mViewPortWidth;
-  }
-
-  public Object getExtra() {
-    return mExtra;
-  }
-
-  public void updateExtra(Object extra) {
-    this.mExtra = extra;
-  }
-
-  public String getComponentType() {
-    return mComponentType;
-  }
-
-  public String getRef() {
-    return mRef;
-  }
-
-  public void setIsLayoutRTL(boolean isRTL) {
-    mIsLayoutRTL = isRTL;
-  }
-
-  public boolean isLayoutRTL() {
-    return mIsLayoutRTL;
-  }
-
-  public GraphicPosition getLayoutPosition() {
-    if (mLayoutPosition == null) {
-      mLayoutPosition = new GraphicPosition(0, 0, 0, 0);
-    }
-    return mLayoutPosition;
-  }
-
-  protected void setLayoutPosition(GraphicPosition mLayoutPosition) {
-    this.mLayoutPosition = mLayoutPosition;
-  }
-
-  public GraphicSize getLayoutSize() {
-    if (mLayoutSize == null) {
-      mLayoutSize = new GraphicSize(0, 0);
-    }
-    return mLayoutSize;
-  }
-
-  protected void setLayoutSize(GraphicSize mLayoutSize) {
-    this.mLayoutSize = mLayoutSize;
-  }
-
-  public float getCSSLayoutTop() {
-    return mLayoutPosition == null ? 0 : mLayoutPosition.getTop();
-  }
-
-  public float getCSSLayoutBottom() {
-    return mLayoutPosition == null ? 0 : mLayoutPosition.getBottom();
-  }
-
-  public float getCSSLayoutLeft() {
-    return mLayoutPosition == null ? 0 : mLayoutPosition.getLeft();
-  }
-
-  public float getCSSLayoutRight() {
-    return mLayoutPosition == null ? 0 : mLayoutPosition.getRight();
-  }
-
-  public float getLayoutWidth() {
-    return mLayoutSize == null ? 0 : mLayoutSize.getWidth();
-  }
-
-  public float getLayoutHeight() {
-    return mLayoutSize == null ? 0 : mLayoutSize.getHeight();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/AsynLayoutTask.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/AsynLayoutTask.java
deleted file mode 100644
index 564c058..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/AsynLayoutTask.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.binding;
-
-import android.os.AsyncTask;
-
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.list.template.TemplateDom;
-import com.taobao.weex.ui.component.list.template.TemplateViewHolder;
-
-/**
- * Created by furture on 2018/5/11.
- */
-
-class AsynLayoutTask extends AsyncTask<Void, Void, Void> {
-
-    private final TemplateViewHolder templateViewHolder;
-    private final int position;
-    private final WXComponent component;
-
-    AsynLayoutTask(TemplateViewHolder templateViewHolder, int position, WXComponent component) {
-        this.templateViewHolder = templateViewHolder;
-        this.position = position;
-        this.component = component;
-    }
-
-    @Override
-    protected Void doInBackground(Void... params) {
-        if(templateViewHolder.getHolderPosition() == position){
-            if(component.getInstance() != null && !component.getInstance().isDestroy()) {
-                synchronized (templateViewHolder.getTemplateList()){
-                    if(templateViewHolder.getTemplateList().isDestoryed()){
-                        return null;
-                    }
-                    Layouts.doLayoutOnly(component, templateViewHolder);
-                }
-            }
-        }
-        return null;
-    }
-
-    @Override
-    protected void onPostExecute(Void aVoid) {
-        if(position == templateViewHolder.getHolderPosition()) {
-            if(component.getInstance() != null && !component.getInstance().isDestroy()) {
-                Layouts.setLayout(component, false);
-                if(templateViewHolder.getHolderPosition() >= 0){
-                    templateViewHolder.getTemplateList().fireEvent("_attach_slot", TemplateDom.findAllComponentRefs(templateViewHolder.getTemplateList().getRef(), position, component));
-                }
-            }
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/Layouts.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/Layouts.java
deleted file mode 100644
index 9320bce..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/Layouts.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.binding;
-
-
-
-import android.os.AsyncTask;
-import android.util.Log;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.ui.component.list.template.TemplateDom;
-import com.taobao.weex.ui.component.list.template.TemplateViewHolder;
-import com.taobao.weex.ui.component.list.template.WXRecyclerTemplateList;
-import com.taobao.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-
-/**
- * Created by furture on 2017/8/21.
- */
-public class Layouts {
-    /**
-     * do dom layout async or sync , and set layout to component on main.
-     * on first use do sync layout, when compontnet reuse do async layout
-     * */
-    public static void doLayoutAsync(final TemplateViewHolder templateViewHolder, boolean async){
-        final WXComponent component = templateViewHolder.getComponent();
-        final  int position = templateViewHolder.getHolderPosition();
-        if(templateViewHolder.asyncTask != null){
-            templateViewHolder.asyncTask.cancel(false);
-            templateViewHolder.asyncTask = null;
-        }
-        if(async){
-            AsyncTask<Void, Void, Void> asyncTask = new AsynLayoutTask(templateViewHolder, position, component);
-            templateViewHolder.asyncTask = asyncTask;
-            asyncTask.executeOnExecutor(AsyncTask.SERIAL_EXECUTOR); //serial executor is better
-        }else{
-            doLayoutOnly(component, templateViewHolder);
-            setLayout(component, false);
-            if(templateViewHolder.getHolderPosition() >= 0){
-                templateViewHolder.getTemplateList().fireEvent("_attach_slot", TemplateDom.findAllComponentRefs(templateViewHolder.getTemplateList().getRef(), position, component));
-            }
-        }
-
-    }
-    /**
-     * @param layoutHeight height
-     * @param layoutWidth width
-     * */
-    public static void doLayoutSync(WXCell component, float layoutWidth, float layoutHeight){
-        doSafeLayout(component, layoutWidth, layoutHeight);
-        setLayout(component, false);
-    }
-
-        /**
-         * safe layout
-         * */
-    public static void doLayoutOnly(WXComponent component, TemplateViewHolder holder){
-        doSafeLayout(component, holder.getTemplateList().getLayoutWidth(), holder.getTemplateList().getLayoutHeight());
-    }
-
-    private static void doSafeLayout(WXComponent component, float layoutWidth, float layoutHeight){
-        try{
-            long start = System.currentTimeMillis();
-            int height = NativeRenderObjectUtils.nativeLayoutRenderObject(component.getRenderObjectPtr(),
-                    layoutWidth,
-                    layoutHeight);
-            if(WXEnvironment.isOpenDebugLog() && WXRecyclerTemplateList.ENABLE_TRACE_LOG) {
-                WXLogUtils.d(WXRecyclerTemplateList.TAG, "WXTemplateList doSafeLayout " +
-                        component.getAttrs().get(Constants.Name.Recycler.SLOT_TEMPLATE_CASE) + " " + Thread.currentThread().getName() + " doSafeLayout  used " +
-                        (System.currentTimeMillis() - start));
-            }
-            if(!(height > 0)){
-                WXLogUtils.e(WXRecyclerTemplateList.TAG, " WXTemplateList doSafeLayout wrong template " +
-                        component.getAttrs().get(Constants.Name.Recycler.SLOT_TEMPLATE_CASE)  + " cell height " + height);
-            }
-        }catch (Exception e){
-            if(WXEnvironment.isApkDebugable()){
-                WXLogUtils.e(WXRecyclerTemplateList.TAG, e);
-            }
-        }
-    }
-
-
-    /**
-     * recursive set layout to component,
-     * dom extra will also be updated from dom object to component.
-     * if force is true, always set layout
-     * */
-    public static final void setLayout(WXComponent component, boolean force){
-        if(component.isWaste()){
-            return;
-        }
-        if(component.getAttrs().containsKey(TemplateDom.KEY_RESET_ANIMATION)){
-            if(WXUtils.getBoolean(component.getAttrs().get(TemplateDom.KEY_RESET_ANIMATION), true).booleanValue()){
-                TemplateDom.resetAnimaiton(component.getHostView());
-            }
-        }
-        long ptr = component.getRenderObjectPtr();
-        if(NativeRenderObjectUtils.nativeRenderObjectHasNewLayout(ptr)){
-            NativeRenderObjectUtils.nativeRenderObjectUpdateComponent(ptr, component);
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            int count = container.getChildCount();
-            for (int i = 0; i < count; ++i) {
-                WXComponent child = container.getChild(i);
-                if (child != null) {
-                    setLayout(child, force);
-                }
-            }
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/Statements.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/Statements.java
deleted file mode 100644
index e19ff8b..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/binding/Statements.java
+++ /dev/null
@@ -1,701 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.binding;
-
-import android.os.Looper;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.bridge.EventResult;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.dom.binding.ELUtils;
-import com.taobao.weex.dom.binding.JSONUtils;
-import com.taobao.weex.dom.binding.WXStatement;
-import com.taobao.weex.el.parse.ArrayStack;
-import com.taobao.weex.el.parse.Operators;
-import com.taobao.weex.el.parse.Token;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.action.GraphicPosition;
-import com.taobao.weex.ui.action.GraphicSize;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXComponentFactory;
-import com.taobao.weex.ui.component.WXImage;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.ui.component.list.template.CellDataManager;
-import com.taobao.weex.ui.component.list.template.CellRenderContext;
-import com.taobao.weex.ui.component.list.template.TemplateDom;
-import com.taobao.weex.ui.component.list.template.VirtualComponentLifecycle;
-import com.taobao.weex.ui.component.list.template.WXRecyclerTemplateList;
-import com.taobao.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-/**
- * Created by jianbai.gbj on 2017/8/17.
- * simple statement execute, render component for template list
- */
-public class Statements {
-
-
-    /**
-     * parse statements token from attrs and style and event
-     * */
-    public static void  parseStatementsToken(WXComponent component){
-        if(component.getBasicComponentData().isRenderPtrEmpty()){
-           component.getBasicComponentData().setRenderObjectPr(component.getRenderObjectPtr());
-        }
-        if(component.getBasicComponentData() != null){
-            BasicComponentData basicComponentData =  component.getBasicComponentData();
-            basicComponentData.getAttrs().parseStatements();
-            basicComponentData.getStyles().parseStatements();
-            basicComponentData.getEvents().parseStatements();
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            int count = container.getChildCount();
-            for (int i = 0; i < count; ++i) {
-                parseStatementsToken(container.getChild(i));
-            }
-        }
-    }
-
-
-
-    /**
-     * init component  if component is lazy,
-     * if component is not lazy, do nothing
-     * */
-    public static void initLazyComponent(WXComponent component, WXVContainer mParent){
-        if(component.isLazy() || component.getHostView() == null){
-            component.lazy(false);
-            if(mParent != null){
-                int index = mParent.indexOf(component);
-                mParent.createChildViewAt(index);
-            }else {
-                component.createView();
-            }
-            component.applyLayoutAndEvent(component);
-            component.bindData(component);
-        }
-    }
-
-
-
-    /**
-     * recursive copy component, none parent connect
-     * */
-    public static WXComponent copyComponentTree(WXComponent component){
-        WXComponent copy =  copyComponentTree(component, component.getParent());
-        return copy;
-    }
-
-    /**
-     * recursive copy component,
-     * */
-    private static final WXComponent copyComponentTree(WXComponent source, WXVContainer parent){
-        BasicComponentData basicComponentData = null;
-        try {
-            basicComponentData = source.getBasicComponentData().clone();
-        } catch (CloneNotSupportedException e) {
-            e.printStackTrace();
-        }
-        WXComponent component = WXComponentFactory.newInstance(source.getInstance(), parent, basicComponentData);
-        GraphicPosition graphicPosition = source.getLayoutPosition();
-        GraphicSize graphicSize = source.getLayoutSize();
-        component.updateDemission(graphicPosition.getTop(), graphicPosition.getBottom(), graphicPosition.getLeft(), graphicPosition.getRight(),
-                 graphicSize.getHeight(), graphicSize.getWidth());
-        component.updateExtra(source.getExtra());
-        if(source instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) source;
-            WXVContainer childParent = (WXVContainer) component;
-            int count = container.getChildCount();
-            for (int i = 0; i < count; ++i) {
-                WXComponent sourceChild = container.getChild(i);
-                if (sourceChild != null) {
-                    WXComponent targetChild = copyComponentTree(sourceChild,  childParent);childParent.addChild(targetChild);
-                    NativeRenderObjectUtils.nativeAddChildRenderObject(childParent.getRenderObjectPtr(),
-                            targetChild.getRenderObjectPtr());
-                }
-            }
-        }
-        //copy info need be sync
-        if(source.isWaste()){
-            component.setWaste(true);
-        }
-        return  component;
-    }
-
-    /**
-     *  @param component component with v-for statement, v-if statement and bind attrs
-     *  @param stack  execute context
-     *  render component in context, the function do the following  work.
-     *  execute component's v-for statement, v-if statement in context,
-     *  and rebuild component's tree with the statement, v-for reuse component execute by pre render.
-     *  if executed, component will be removed, don't remove, just mark it waste;
-     *  may be next render it can be used.
-     *  after statement has executed, render component's binding attrs in context and bind it to component.
-     * */
-    public static final List<WXComponent> doRender(WXComponent component, CellRenderContext stack){
-        List<WXComponent> updates = new ArrayList<>(4);
-        try{
-            doRenderComponent(component, stack, updates);
-        }catch (Exception e){
-            WXLogUtils.e("WeexStatementRender", e);
-        }
-        return updates;
-    }
-
-    public static final void doInitCompontent(List<WXComponent> updates) {
-        if(updates == null || updates.size() == 0){
-            return;
-        }
-        for(WXComponent renderNode : updates){
-            if(renderNode.getParent() == null){
-                throw new IllegalArgumentException("render node parent cann't find");
-            }
-            WXVContainer parent = renderNode.getParent();
-            int renderIndex = parent.indexOf(renderNode);
-            if(renderIndex < 0){
-                throw new IllegalArgumentException("render node cann't find");
-            }
-            parent.createChildViewAt(renderIndex);
-            renderNode.applyLayoutAndEvent(renderNode);
-            renderNode.bindData(renderNode);
-        }
-    }
-
-        /**
-         *  @param component component with v-for statement, v-if statement and bind attrs
-         *  @param context   execute context
-         *  render component in context, the function do the following  work.
-         *  execute component's v-for statement, v-if statement in context,
-         *  and rebuild component's tree with the statement, v-for reuse component execute by pre render.
-         *  if executed, component will be removed, don't remove, just mark it waste;
-         *  may be next render it can be used.
-         *  after statement has executed, render component's binding attrs in context and bind it to component.
-         * */
-    private static final int doRenderComponent(WXComponent component, CellRenderContext context,
-                                               List<WXComponent> updates){
-        WXVContainer parent = component.getParent();
-        WXAttr attrs = component.getAttrs();
-        WXStatement statement =  attrs.getStatement();
-        if(statement != null){
-            Token vif =  null;
-            JSONObject vfor = null;
-            if(statement.get(WXStatement.WX_IF) instanceof Token){
-                vif = (Token) statement.get(WXStatement.WX_IF);
-            }
-            if(statement.get(WXStatement.WX_FOR) instanceof  JSONObject){
-                vfor = (JSONObject) statement.get(WXStatement.WX_FOR);
-            }
-            // execute v-for content
-            if(vfor != null){
-                int    renderIndex = parent.indexOf(component);
-                if(vfor.get(WXStatement.WX_FOR_LIST) instanceof Token){
-                    Token listBlock = (Token) vfor.get(WXStatement.WX_FOR_LIST);
-                    String indexKey = vfor.getString(WXStatement.WX_FOR_INDEX);
-                    String itemKey = vfor.getString(WXStatement.WX_FOR_ITEM);
-                    Object data = null;
-                    if(listBlock != null) {
-                        data = listBlock.execute(context.stack);
-                    }
-                    if((data instanceof List || data instanceof  Map)){
-
-                        Collection collection = null;
-                        Map  map = null;
-                        if(data instanceof  List){
-                            collection = (List)data;
-                        }else{
-                            map = (Map)data;
-                            collection = map.keySet();
-                        }
-                        Map<String, Object> loop = new HashMap<>();
-                        int index = 0;
-                        for(Object item : collection){
-                            Object key = null;
-                            Object value = item;
-                            if(map == null){
-                                key = index;
-                                value = item;
-                                index ++;
-                            }else{
-                                key = item;
-                                value = map.get(item);
-                            }
-                            if(indexKey != null){
-                                loop.put(indexKey, key);
-                            }
-
-                            if(itemKey != null){
-                                loop.put(itemKey, value);
-                            }else{
-                                context.stack.push(value);
-                            }
-                            if(loop.size() > 0){
-                                context.stack.push(loop);
-                            }
-
-
-                            if(vif != null){
-                                if(!Operators.isTrue(vif.execute(context.stack))){
-                                    continue;
-                                }
-                            }
-                            //find resuable renderNode
-                            WXComponent renderNode = null;
-                            if(renderIndex < parent.getChildCount()){
-                                renderNode = parent.getChild(renderIndex);
-                                //check is same statment, if true, it is usabled.
-                                if(!isCreateFromNodeStatement(renderNode, component)){
-                                    renderNode = null;
-                                }
-                                if(renderNode != null){
-                                    if(renderNode.isWaste()){
-                                        renderNode.setWaste(false);
-                                    }
-                                }
-                            }
-                            //none resuable render node, create node, add to parent, but clear node's statement
-                            if(renderNode == null){
-                                long start = System.currentTimeMillis();
-                                renderNode = copyComponentTree(component, parent);
-                                renderNode.setWaste(false);
-                                if(renderNode.getAttrs().getStatement() != null) {
-                                    renderNode.getAttrs().getStatement().remove(WXStatement.WX_FOR);
-                                    renderNode.getAttrs().getStatement().remove(WXStatement.WX_IF); //clear node's statement
-                                }
-                                parent.addChild(renderNode, renderIndex);
-                                NativeRenderObjectUtils.nativeAddChildRenderObject(parent.getRenderObjectPtr(),
-                                        renderNode.getRenderObjectPtr());
-                                updates.add(renderNode);
-                                if(WXEnvironment.isApkDebugable()){
-                                    WXLogUtils.d(WXRecyclerTemplateList.TAG, Thread.currentThread().getName() +  renderNode.getRef() + renderNode.getComponentType() + "statements copy component tree used " + (System.currentTimeMillis() - start));
-                                }
-                            }
-                            doBindingAttrsEventAndRenderChildNode(renderNode, context, updates);
-                            renderIndex++;
-                            if(loop.size() > 0){
-                                context.stack.push(loop);
-                            }
-                            if(itemKey == null) {
-                                context.stack.pop();
-                            }
-                        }
-                    }
-                }else{
-                    WXLogUtils.e(WXRecyclerTemplateList.TAG,  vfor.toJSONString() + " not call vfor block, for pre compile");
-                }
-                //after v-for execute, remove component created pre v-for.
-                for(;renderIndex<parent.getChildCount(); renderIndex++){
-                    WXComponent wasteNode = parent.getChild(renderIndex);
-                    if(!isCreateFromNodeStatement(wasteNode, component)){
-                        break;
-                    }
-                    wasteNode.setWaste(true);
-                }
-                return renderIndex - parent.indexOf(component);
-            }
-
-            //execute v-if context
-            if(vif != null){
-                if(!Operators.isTrue(vif.execute(context.stack))){
-                    component.setWaste(true);
-                    return 1;
-                }else{
-                    component.setWaste(false);
-                }
-
-            }
-        }
-        doBindingAttrsEventAndRenderChildNode(component, context, updates);
-        return  1;
-    }
-
-
-    /**
-     * bind attrs and doRender component child
-     * */
-    private static void doBindingAttrsEventAndRenderChildNode(WXComponent component, CellRenderContext context,
-                                                              List<WXComponent> updates){
-        WXAttr attr = component.getAttrs();
-
-        /**
-         * sub component supported, sub component new stack
-         * */
-        ArrayStack stack = context.stack;
-
-
-        String virtualComponentId = null;
-        boolean callVirtualComponentAttach = false;
-        if(attr.get(ELUtils.IS_COMPONENT_ROOT) != null
-                && WXUtils.getBoolean(attr.get(ELUtils.IS_COMPONENT_ROOT), false)){
-            if(attr.get(ELUtils.COMPONENT_PROPS) != null
-                    && JSONUtils.isJSON(attr.get(ELUtils.COMPONENT_PROPS))){
-                 String compoentId = (String) attr.get(CellDataManager.SUB_COMPONENT_TEMPLATE_ID);
-                Object compoentData = null;
-                if(!TextUtils.isEmpty(compoentId)){
-                   virtualComponentId =  context.getRenderState().getVirtualComponentIds().get(component.getViewTreeKey());
-                   if(virtualComponentId == null){ //none virtualComponentId, create and do attach
-                        virtualComponentId =  CellDataManager.createVirtualComponentId(context.templateList.getRef(),
-                                component.getViewTreeKey(), context.templateList.getItemId(context.position));
-                        Map<String, Object>  props  = renderProps(JSONUtils.toJSON(attr.get(ELUtils.COMPONENT_PROPS)), context.stack);
-                        EventResult result = WXBridgeManager.getInstance().syncCallJSEventWithResult(WXBridgeManager.METHD_COMPONENT_HOOK_SYNC, component.getInstanceId(), null, compoentId, VirtualComponentLifecycle.LIFECYCLE, VirtualComponentLifecycle.CREATE,  new Object[]{
-                                virtualComponentId,
-                                props
-                        }, null);
-                        if(result != null
-                                && result.getResult() != null
-                                && result.getResult() instanceof Map){
-                            props.putAll((Map<? extends String, ?>) result.getResult());
-                        }
-                        compoentData  =  props;
-                        context.getRenderState().getVirtualComponentIds().put(component.getViewTreeKey(), virtualComponentId);
-                        context.templateList.getCellDataManager().createVirtualComponentData(context.position, virtualComponentId, compoentData);
-                         callVirtualComponentAttach = true; // when first create virtual compoent, call create
-                     }else{ // get virtual component data check has dirty's update
-                       compoentData = context.getRenderState().getVirtualComponentDatas().get(virtualComponentId);
-                       if(context.getRenderState().isHasDataUpdate()){
-                           Map<String, Object>  props  = renderProps((JSONObject) attr.get(ELUtils.COMPONENT_PROPS), context.stack);
-                           EventResult result = WXBridgeManager.getInstance().syncCallJSEventWithResult(WXBridgeManager.METHD_COMPONENT_HOOK_SYNC, component.getInstanceId(), null, virtualComponentId, VirtualComponentLifecycle.LIFECYCLE, VirtualComponentLifecycle.SYNSTATE,  new Object[]{
-                                   virtualComponentId,
-                                   props
-                           }, null);
-
-                           if(result != null
-                                   && result.getResult() != null
-                                   && result.getResult() instanceof Map){
-                               props.putAll((Map<? extends String, ?>) result.getResult());
-                               context.templateList.getCellDataManager().updateVirtualComponentData(virtualComponentId, props);
-                               compoentData = props;
-                           }
-                       }
-                    }
-                    component.getAttrs().put(CellDataManager.VIRTUAL_COMPONENT_ID, virtualComponentId);
-                }else{ //stateless component
-                    Map<String, Object>  props  = renderProps((JSONObject) attr.get(ELUtils.COMPONENT_PROPS), context.stack);
-                    compoentData = props;
-                }
-                //virtual component is new context
-                context.stack = new ArrayStack();
-                if(compoentData != null){
-                    context.stack.push(compoentData);
-                }
-            }
-        }
-
-        /**
-         * check node is render only once, if render once, and has rendered, just return
-         * */
-        Object vonce = null;
-        if(attr.getStatement() != null){
-            vonce = attr.getStatement().get(WXStatement.WX_ONCE);
-        }
-        if(vonce != null){
-            ArrayStack onceStack = context.getRenderState().getOnceComponentStates().get(component.getViewTreeKey());
-            if(onceStack == null){
-                onceStack = context.templateList.copyStack(context, stack);
-                context.getRenderState().getOnceComponentStates().put(component.getViewTreeKey(), onceStack);
-            }
-            context.stack = onceStack;
-        }
-
-        doRenderBindingAttrsAndEvent(component, context);
-        if(component instanceof WXVContainer){
-            if(component.isWaste()){
-                if(!(component instanceof WXCell)){
-                     return;
-                }
-            }
-            WXVContainer container = (WXVContainer) component;
-            for(int k=0; k<container.getChildCount();){
-                WXComponent next = container.getChild(k);
-                k += doRenderComponent(next, context, updates);
-            }
-        }
-        if(stack != context.stack){
-            context.stack = stack;
-        }
-        //create virtual componentId
-        if(callVirtualComponentAttach && virtualComponentId != null){
-            WXBridgeManager.getInstance().asyncCallJSEventVoidResult(WXBridgeManager.METHD_COMPONENT_HOOK_SYNC, component.getInstanceId(), null, virtualComponentId, VirtualComponentLifecycle.LIFECYCLE, VirtualComponentLifecycle.ATTACH, new Object[]{
-                    TemplateDom.findAllComponentRefs(context.templateList.getRef(),context.position, component)
-            });
-        }
-     }
-
-
-    /**
-     * check whether render node is create from component node statement.
-     * */
-    private static boolean isCreateFromNodeStatement(WXComponent renderNode, WXComponent component){
-        return (renderNode.getRef() != null && renderNode.getRef().equals(component.getRef()));
-    }
-
-
-    /**
-     * render dynamic binding attrs and bind them to component node.
-     * */
-    private static void doRenderBindingAttrsAndEvent(WXComponent component, CellRenderContext context){
-        ArrayStack stack  = context.stack;
-        component.setWaste(false);
-        WXAttr attr = component.getAttrs();
-        if(attr != null
-                && attr.getBindingAttrs() != null
-                && attr.getBindingAttrs().size() > 0){
-            ArrayMap<String, Object> bindAttrs = component.getAttrs().getBindingAttrs();
-            Map<String, Object> dynamic =  renderBindingAttrs(bindAttrs, stack);
-            Set<Map.Entry<String, Object>> entries = dynamic.entrySet();
-            /**
-             * diff attrs, see attrs has update, remove none update attrs
-             * */
-            Iterator<Map.Entry<String, Object>> iterator = entries.iterator();
-            while (iterator.hasNext()){
-                Map.Entry<String, Object> entry = iterator.next();
-                String key = entry.getKey();
-                Object value = entry.getValue();
-                Object oldValue = attr.get(key);
-                if(value == null){
-                    if(oldValue == null){
-                        iterator.remove();
-                        continue;
-                    }
-                }else{
-                    if(value.equals(oldValue)){
-                        iterator.remove();
-                    }
-                }
-            }
-
-            if(dynamic.size() > 0) {
-                if(dynamic.size() == 1
-                        && dynamic.get(Constants.Name.SRC) != null
-                        && component instanceof WXImage){
-                    //for image avoid dirty layout, only update src attrs
-                    component.getAttrs().put(Constants.Name.SRC, dynamic.get(Constants.Name.SRC));
-                }else {
-                    component.nativeUpdateAttrs(dynamic);
-                }
-                if(isMainThread()) {
-                    component.updateProperties(dynamic);
-                }
-                dynamic.clear();
-            }
-        }
-
-
-        WXStyle style = component.getStyles();
-        if(style != null && style.getBindingStyle() != null){
-            ArrayMap<String, Object> bindStyle = style.getBindingStyle();
-            Map<String, Object> dynamic =  renderBindingAttrs(bindStyle, stack);
-            Set<Map.Entry<String, Object>> entries = dynamic.entrySet();
-            /**
-             * diff attrs, see attrs has update, remove none update attrs
-             * */
-            Iterator<Map.Entry<String, Object>> iterator = entries.iterator();
-            while (iterator.hasNext()){
-                Map.Entry<String, Object> entry = iterator.next();
-                String key = entry.getKey();
-                Object value = entry.getValue();
-                Object oldValue = style.get(key);
-                if(value == null){
-                    if(oldValue == null){
-                        iterator.remove();
-                        continue;
-                    }
-                }else{
-                    if(value.equals(oldValue)){
-                        iterator.remove();
-                    }
-                }
-            }
-            if(dynamic.size() > 0) {
-                  component.updateNativeStyles(dynamic);
-                 if(isMainThread()) {
-                    component.updateProperties(dynamic);
-                 }
-            }
-        }
-
-        WXEvent event = component.getEvents();
-        if(event == null || event.getEventBindingArgs() == null){
-            return;
-        }
-        Set<Map.Entry<String, Object>> eventBindArgsEntrySet = event.getEventBindingArgs().entrySet();
-        for(Map.Entry<String, Object> eventBindArgsEntry : eventBindArgsEntrySet){
-             List<Object> values = getBindingEventArgs(stack, eventBindArgsEntry.getValue());
-             if(values != null){
-                 event.putEventBindingArgsValue(eventBindArgsEntry.getKey(), values);
-             }
-        }
-
-    }
-
-
-    /**
-     * @param  bindAttrs  none null,
-     * @param  context  context
-     * return binding attrs rended value in context
-     * */
-    private static final  ThreadLocal<Map<String, Object>> dynamicLocal = new ThreadLocal<>();
-    public static Map<String, Object> renderBindingAttrs(ArrayMap bindAttrs, ArrayStack stack){
-        Set<Map.Entry<String, Object>> entrySet = bindAttrs.entrySet();
-        Map<String, Object> dynamic = dynamicLocal.get();
-        if(dynamic == null) {
-            dynamic = new HashMap<>();
-            dynamicLocal.set(dynamic);
-        }
-        if(dynamic.size() > 0){
-            dynamic.clear();
-        }
-        for(Map.Entry<String, Object> entry : entrySet){
-            Object value = entry.getValue();
-            String key = entry.getKey();
-            if(value instanceof  JSONObject
-                    && (((JSONObject) value).get(ELUtils.BINDING)  instanceof Token)){
-                JSONObject binding = (JSONObject) value;
-                Token block = (Token) (binding.get(ELUtils.BINDING));
-                Object blockValue = block.execute(stack);
-                dynamic.put(key, blockValue);
-            }else if(value instanceof JSONArray){
-                JSONArray array = (JSONArray) value;
-                StringBuilder builder = new StringBuilder();
-                for(int i=0; i<array.size(); i++){
-                    Object element = array.get(i);
-                    if(element instanceof  CharSequence){
-                        builder.append(element);
-                        continue;
-                    }
-                    if(element instanceof JSONObject
-                            && (((JSONObject) element).get(ELUtils.BINDING) instanceof Token)){
-                        JSONObject binding = (JSONObject) element;
-                        Token block = (Token) (binding.get(ELUtils.BINDING));
-                        Object blockValue = block.execute(stack);
-                        if(blockValue == null){
-                            blockValue = "";
-                        }
-                        builder.append(blockValue);
-                    }
-                }
-                String builderString = builder.toString();
-                if(builderString.length() > 256){
-                    if(WXEnvironment.isApkDebugable()){
-                        WXLogUtils.w(WXRecyclerTemplateList.TAG, " warn too big string " + builderString);
-                    }
-                }
-                dynamic.put(key, builderString);
-            }
-        }
-        return  dynamic;
-    }
-
-
-    public static Map<String, Object> renderProps(JSONObject props, ArrayStack stack){
-        Set<Map.Entry<String, Object>> entrySet = props.entrySet();
-        Map<String, Object> renderProps = new ArrayMap<>(4);
-        for(Map.Entry<String, Object> entry : entrySet){
-            Object value = entry.getValue();
-            String key = entry.getKey();
-            if(value instanceof  JSONObject
-                    && (((JSONObject) value).get(ELUtils.BINDING)  instanceof Token)){
-                JSONObject binding = (JSONObject) value;
-                Token block = (Token) (binding.get(ELUtils.BINDING));
-                Object blockValue = block.execute(stack);
-                renderProps.put(key, blockValue);
-            }else{
-                renderProps.put(key, value);
-            }
-        }
-        return  renderProps;
-    }
-
-    public static List<Object> getBindingEventArgs(ArrayStack stack, Object bindings){
-          List<Object>  params = new ArrayList<>(4);
-          if(bindings instanceof  JSONArray){
-              JSONArray array = (JSONArray) bindings;
-              for(int i=0; i<array.size(); i++){
-                  Object value = array.get(i);
-                  if(value instanceof  JSONObject
-                          && (((JSONObject) value).get(ELUtils.BINDING) instanceof Token)){
-                      Token block = (Token)(((JSONObject) value).get(ELUtils.BINDING));
-                      Object blockValue = block.execute(stack);
-                      params.add(blockValue);
-                  }else{
-                      params.add(value);
-                  }
-              }
-          }else if(bindings instanceof  JSONObject){
-              JSONObject binding = (JSONObject) bindings;
-               if(binding.get(ELUtils.BINDING) instanceof Token){
-                   Token block = (Token) binding.get(ELUtils.BINDING);
-                   Object blockValue = block.execute(stack);
-                   params.add(blockValue);
-               }else{
-                   params.add(bindings.toString());
-               }
-          }else{
-              params.add(bindings.toString());
-          }
-          return  params;
-    }
-
-
-    private static boolean isMainThread(){
-        return  Thread.currentThread() == Looper.getMainLooper().getThread();
-    }
-
-
-
-    public static String getComponentId(WXComponent component){
-        if(component instanceof WXCell || component == null){
-            return  null;
-        }
-        WXAttr attr = component.getAttrs();
-        if(attr.get(ELUtils.IS_COMPONENT_ROOT) != null
-                && WXUtils.getBoolean(attr.get(ELUtils.IS_COMPONENT_ROOT), false)){
-            if(attr.get(ELUtils.COMPONENT_PROPS) != null
-                    && attr.get(ELUtils.COMPONENT_PROPS) instanceof  JSONObject){
-                Object componentId = attr.get(CellDataManager.VIRTUAL_COMPONENT_ID);
-                if(componentId == null){
-                    return null;
-                }
-                return componentId.toString();
-            }
-        }
-        return getComponentId(component.getParent());
-    }
-
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/ScrollStartEndHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/ScrollStartEndHelper.java
deleted file mode 100644
index 29eb775..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/ScrollStartEndHelper.java
+++ /dev/null
@@ -1,153 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.helper;
-
-import android.os.Handler;
-import android.os.Looper;
-
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.OnWXScrollListener;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXScroller;
-import com.taobao.weex.ui.component.list.BasicListComponent;
-import com.taobao.weex.ui.component.list.ListComponentView;
-import com.taobao.weex.ui.component.list.template.WXRecyclerTemplateList;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.Map;
-
-
-/**
- * Created by furture on 2017/11/13.
- */
-
-public class ScrollStartEndHelper implements Runnable{
-
-    private Handler handler;
-    private WXComponent component;
-    private boolean  hasStart;
-    private boolean  canStart = false;
-
-    private long  minInterval;
-    private int oldState = OnWXScrollListener.IDLE;
-
-    private int x;
-    private int y;
-    private boolean hasScrollEnd;
-
-
-    public ScrollStartEndHelper(WXComponent component) {
-        this.component = component;
-        this.handler = new Handler(Looper.getMainLooper());
-        this.minInterval = WXUtils.getNumberInt(component.getAttrs().get("minscrolldelayinterval"), 32);
-    }
-
-    /**
-     * @param  x scroll offset or dx, which is not accurate
-     * @param  y scroll offset or dy, which is not accurate
-     * */
-    public void  onScrolled(int x, int y){
-        if((component.getEvents().contains(Constants.Event.SCROLL_START)
-                || component.getEvents().contains(Constants.Event.SCROLL_END))){
-            this.x = x;
-            this.y = y;
-            if(!hasStart && canStart){
-                if(component.getEvents().contains(Constants.Event.SCROLL_START)){
-                    Map<String, Object> event = getScrollEvent(x,y);
-                    if (null !=event && !event.isEmpty()){
-                        component.fireEvent(Constants.Event.SCROLL_START,event);
-
-                    }
-                }
-                hasStart = true;
-                canStart = false;
-            }
-            handler.removeCallbacks(this);
-            handler.postDelayed(this, minInterval);
-        }
-    }
-
-
-    @Override
-    public void run() {
-        if(component.isDestoryed()){
-            return;
-        }
-        if(!hasScrollEnd){
-            return;
-        }
-        if(canStart){
-            component.fireEvent(Constants.Event.SCROLL_START, getScrollEvent(this.x, this.y));
-            canStart = false;
-        }
-        if(component.getEvents().contains(Constants.Event.SCROLL_END)){
-            component.fireEvent(Constants.Event.SCROLL_END, getScrollEvent(this.x, this.y));
-
-        }
-        hasStart = false;
-        hasScrollEnd = false;
-
-    }
-
-    private Map<String, Object> getScrollEvent(int offsetX, int offsetY){
-        if(component instanceof BasicListComponent){
-            BasicListComponent basicListComponent = (BasicListComponent) component;
-            if(basicListComponent.getHostView() instanceof ListComponentView){
-                ListComponentView componentView = (ListComponentView) basicListComponent.getHostView();
-                if(componentView != null){
-                    return basicListComponent.getScrollEvent(componentView.getInnerView(), offsetX, offsetY);
-                }
-            }
-        }else if(component instanceof WXRecyclerTemplateList){
-            WXRecyclerTemplateList templateList = (WXRecyclerTemplateList) component;
-            return templateList.getScrollEvent(templateList.getHostView().getInnerView(), offsetX, offsetY);
-        }else if(component instanceof WXScroller){
-            WXScroller scroller = (WXScroller) component;
-            return scroller.getScrollEvent(offsetX, offsetY);
-        }
-        return null;
-    }
-
-    public void onScrollStateChanged(int newState){
-
-        if(oldState == OnWXScrollListener.IDLE){
-            canStart = true;
-        }
-
-        if(newState == OnWXScrollListener.IDLE){
-            hasScrollEnd = true;
-            handler.removeCallbacks(this);
-            handler.postDelayed(this, minInterval);
-        }
-
-        oldState = newState;
-    }
-
-
-    public static boolean isScrollEvent(String type){
-        if(Constants.Event.SCROLL.equals(type)){
-            return  true;
-        }else if(Constants.Event.SCROLL_START.equals(type)){
-            return  true;
-        }else if(Constants.Event.SCROLL_END.equals(type)){
-            return  true;
-        }
-        return  false;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/SoftKeyboardDetector.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/SoftKeyboardDetector.java
deleted file mode 100644
index afbabd0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/SoftKeyboardDetector.java
+++ /dev/null
@@ -1,148 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.helper;
-
-import android.app.Activity;
-import android.graphics.Rect;
-import android.os.Build;
-import android.support.annotation.Nullable;
-import android.view.View;
-import android.view.ViewTreeObserver;
-import android.view.WindowManager;
-
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.lang.ref.WeakReference;
-
-/**
- * Created by moxun on 17/3/24.
- */
-
-public class SoftKeyboardDetector {
-
-    private static final int KEYBOARD_VISIBLE_THRESHOLD_DIP = 100;
-
-    public static Unregister registerKeyboardEventListener(Activity activity, final OnKeyboardEventListener listener) {
-        if (activity == null || listener == null) {
-            WXLogUtils.e("Activity or listener is null!");
-            return null;
-        }
-
-        if (activity.getWindow() != null) {
-            WindowManager.LayoutParams attributes = activity.getWindow().getAttributes();
-            if (attributes != null) {
-                int softInputMode = attributes.softInputMode;
-                if (softInputMode == WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING
-                        || softInputMode == WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN) {
-                    WXLogUtils.e("SoftKeyboard detector can't work with softInputMode is SOFT_INPUT_ADJUST_NOTHING or SOFT_INPUT_ADJUST_PAN");
-                    return null;
-                }
-            }
-        }
-
-        final View activityRoot = getActivityRoot(activity);
-
-        if (activityRoot == null) {
-            WXLogUtils.e("Activity root is null!");
-            return null;
-        }
-
-        final ViewTreeObserver.OnGlobalLayoutListener layoutListener = new ViewTreeObserver.OnGlobalLayoutListener() {
-
-            private final Rect visibleFrame = new Rect();
-            private final int threshold = WXViewUtils.dip2px(KEYBOARD_VISIBLE_THRESHOLD_DIP);
-            private boolean wasKeyboardOpened = false;
-
-            @Override
-            public void onGlobalLayout() {
-                activityRoot.getWindowVisibleDisplayFrame(visibleFrame);
-                int heightDiff = activityRoot.getRootView().getHeight() - visibleFrame.height();
-                boolean isOpen = heightDiff > threshold;
-                if (isOpen == wasKeyboardOpened) {
-                    return;
-                }
-
-                wasKeyboardOpened = isOpen;
-                listener.onKeyboardEvent(isOpen);
-            }
-        };
-
-        activityRoot.getViewTreeObserver().addOnGlobalLayoutListener(layoutListener);
-        return new DefaultUnRegister(activity, layoutListener);
-    }
-
-    public static boolean isKeyboardVisible(Activity activity) {
-        Rect windowFrame = new Rect();
-        View root = getActivityRoot(activity);
-
-        if (root != null) {
-            root.getWindowVisibleDisplayFrame(windowFrame);
-            int heightDiff = root.getRootView().getHeight() - windowFrame.height();
-            return heightDiff > WXViewUtils.dip2px(KEYBOARD_VISIBLE_THRESHOLD_DIP);
-        }
-        return false;
-    }
-
-    public static @Nullable View getActivityRoot(Activity activity) {
-        if (activity != null) {
-            return activity.findViewById(android.R.id.content);
-        }
-        return null;
-    }
-
-    public static final class DefaultUnRegister implements Unregister {
-
-        private WeakReference<Activity> activityRef;
-        private WeakReference<ViewTreeObserver.OnGlobalLayoutListener> listenerRef;
-
-        public DefaultUnRegister(Activity activity, ViewTreeObserver.OnGlobalLayoutListener listener) {
-            this.activityRef = new WeakReference<>(activity);
-            this.listenerRef = new WeakReference<>(listener);
-        }
-
-        @Override
-        public void execute() {
-            Activity activity = activityRef.get();
-            ViewTreeObserver.OnGlobalLayoutListener listener = listenerRef.get();
-
-            if (activity != null && listener != null) {
-                View root = SoftKeyboardDetector.getActivityRoot(activity);
-                if (root != null) {
-                    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
-                        root.getViewTreeObserver().removeOnGlobalLayoutListener(listener);
-                    } else {
-                        root.getViewTreeObserver().removeGlobalOnLayoutListener(listener);
-                    }
-                }
-            }
-
-            activityRef.clear();
-            listenerRef.clear();
-        }
-    }
-
-    public interface Unregister {
-        void execute();
-    }
-
-    public interface OnKeyboardEventListener {
-        void onKeyboardEvent(boolean isShown);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/WXStickyHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/WXStickyHelper.java
deleted file mode 100644
index fca3c14..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/WXStickyHelper.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.helper;
-
-import com.taobao.weex.ui.component.Scrollable;
-import com.taobao.weex.ui.component.WXComponent;
-
-import java.util.HashMap;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-
-/**
- * Created by miomin on 16/7/7.
- */
-public class WXStickyHelper {
-
-    private Scrollable scrollable;
-
-    public WXStickyHelper(Scrollable scrollable) {
-        this.scrollable = scrollable;
-    }
-
-    public void bindStickStyle(WXComponent component, Map<String, Map<String, WXComponent>> mStickyMap) {
-        Scrollable scroller = component.getParentScroller();
-        if (scroller == null) {
-            return;
-        }
-        Map<String, WXComponent> stickyMap = mStickyMap.get(scroller
-                .getRef());
-        if (stickyMap == null) {
-            stickyMap = new ConcurrentHashMap<>();
-        }
-        if (stickyMap.containsKey(component.getRef())) {
-            return;
-        }
-        stickyMap.put(component.getRef(), component);
-        mStickyMap.put(scroller.getRef(), stickyMap);
-    }
-
-    public void unbindStickStyle(WXComponent component, Map<String, Map<String, WXComponent>> mStickyMap) {
-        Scrollable scroller = component.getParentScroller();
-        if (scroller == null) {
-            return;
-        }
-        Map<String, WXComponent> stickyMap = mStickyMap.get(scroller
-                .getRef());
-        if (stickyMap == null) {
-            return;
-        }
-        stickyMap.remove(component.getRef());
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/WXTimeInputHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/WXTimeInputHelper.java
deleted file mode 100644
index d666439..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/helper/WXTimeInputHelper.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.helper;
-
-import android.support.annotation.Nullable;
-import android.widget.TextView;
-
-import com.taobao.weex.appfram.pickers.DatePickerImpl;
-import com.taobao.weex.ui.component.AbstractEditComponent;
-
-/**
- * Created by moxun on 16/10/12.
- */
-
-public class WXTimeInputHelper {
-  public static void pickDate(String max, String min, final AbstractEditComponent component) {
-    final TextView target = component.getHostView();
-
-    DatePickerImpl.pickDate(
-            target.getContext(),
-            target.getText().toString(),
-            max,
-            min,
-            new DatePickerImpl.OnPickListener() {
-              @Override
-              public void onPick(boolean set, @Nullable String result) {
-                if (set) {
-                  target.setText(result);
-                  component.performOnChange(result);
-                }
-              }
-            },
-            null);
-  }
-
-  public static void pickTime(final AbstractEditComponent component) {
-    final TextView target = component.getHostView();
-
-    DatePickerImpl.pickTime(
-            target.getContext(),
-            target.getText().toString(),
-            new DatePickerImpl.OnPickListener() {
-              @Override
-              public void onPick(boolean set, @Nullable String result) {
-                if (set) {
-                  target.setText(result);
-                  component.performOnChange(result);
-                }
-              }
-            },
-            null
-    );
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/BasicListComponent.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/BasicListComponent.java
deleted file mode 100644
index 0db53a8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/BasicListComponent.java
+++ /dev/null
@@ -1,1475 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.annotation.SuppressLint;
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.graphics.Color;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v4.util.ArrayMap;
-import android.support.v4.view.MotionEventCompat;
-import android.support.v4.view.ViewCompat;
-import android.support.v7.widget.GridLayoutManager;
-import android.support.v7.widget.LinearLayoutManager;
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-import android.text.TextUtils;
-import android.util.SparseArray;
-import android.view.Gravity;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewTreeObserver;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.ICheckBindingScroller;
-import com.taobao.weex.common.OnWXScrollListener;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.AppearanceHelper;
-import com.taobao.weex.ui.component.Scrollable;
-import com.taobao.weex.ui.component.WXBaseRefresh;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXComponentProp;
-import com.taobao.weex.ui.component.WXHeader;
-import com.taobao.weex.ui.component.WXLoading;
-import com.taobao.weex.ui.component.WXRefresh;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.component.helper.ScrollStartEndHelper;
-import com.taobao.weex.ui.component.helper.WXStickyHelper;
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-import com.taobao.weex.ui.view.listview.adapter.IOnLoadMoreListener;
-import com.taobao.weex.ui.view.listview.adapter.IRecyclerAdapterListener;
-import com.taobao.weex.ui.view.listview.adapter.ListBaseViewHolder;
-import com.taobao.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
-import com.taobao.weex.ui.view.listview.adapter.WXRecyclerViewOnScrollListener;
-import com.taobao.weex.ui.view.refresh.wrapper.BounceRecyclerView;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.ArrayDeque;
-import java.util.ArrayList;
-import java.util.Deque;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.regex.Pattern;
-
-/**
- * Created by sospartan on 13/12/2016.
- */
-
-public abstract class BasicListComponent<T extends ViewGroup & ListComponentView> extends WXVContainer<T> implements
-    IRecyclerAdapterListener<ListBaseViewHolder>, IOnLoadMoreListener, Scrollable {
-  public static final String TRANSFORM = "transform";
-  public static final String LOADMOREOFFSET = "loadmoreoffset";
-  private String TAG = "BasicListComponent";
-  private int mListCellCount = 0;
-  private boolean mForceLoadmoreNextTime = false;
-  private static final Pattern transformPattern = Pattern.compile("([a-z]+)\\(([0-9\\.]+),?([0-9\\.]+)?\\)");
-
-  private Map<String, AppearanceHelper> mAppearComponents = new HashMap<>();
-  private Runnable mAppearChangeRunnable = null;
-  private long mAppearChangeRunnableDelay = 50;
-
-  private boolean isScrollable = true;
-  private ArrayMap<String, Long> mRefToViewType;
-  private SparseArray<ArrayList<WXComponent>> mViewTypes;
-  private WXRecyclerViewOnScrollListener mViewOnScrollListener = new WXRecyclerViewOnScrollListener(this);
-
-  private static final int MAX_VIEWTYPE_ALLOW_CACHE = 9;
-  private static boolean mAllowCacheViewHolder = true;
-  private static boolean mDownForBidCacheViewHolder = false;
-
-
-  protected int mLayoutType = WXRecyclerView.TYPE_LINEAR_LAYOUT;
-  protected int mColumnCount = 1;
-  protected float mColumnGap = 0;
-  protected float mColumnWidth = 0;
-  protected float mLeftGap = 0;
-  protected float mRightGap = 0;
-
-  private int mOffsetAccuracy = 10;
-  private Point mLastReport = new Point(-1, -1);
-  private boolean mHasAddScrollEvent = false;
-
-  private RecyclerView.ItemAnimator mItemAnimator;
-
-  private DragHelper mDragHelper;
-
-  /**
-   * exclude cell when dragging(attributes for cell)
-   */
-  private static final String EXCLUDED = "dragExcluded";
-
-  /**
-   * the type to trigger drag-drop
-   */
-  private static final String DRAG_TRIGGER_TYPE = "dragTriggerType";
-
-  private static final String DEFAULT_TRIGGER_TYPE = DragTriggerType.LONG_PRESS;
-  private static final boolean DEFAULT_EXCLUDED = false;
-
-  private static final String DRAG_ANCHOR = "dragAnchor";
-
-  /**
-   * gesture type which can trigger drag&drop
-   */
-  interface DragTriggerType {
-    String PAN = "pan";
-    String LONG_PRESS = "longpress";
-  }
-
-  private String mTriggerType;
-
-  /**
-   * Map for storing component that is sticky.
-   **/
-  private Map<String, Map<String, WXComponent>> mStickyMap = new HashMap<>();
-  private WXStickyHelper stickyHelper;
-
-  /**
-   * scroll start and scroll end event
-   * */
-  private ScrollStartEndHelper mScrollStartEndHelper;
-
-  /**
-   * keep positon
-   * */
-  private  WXComponent keepPositionCell = null;
-  private  Runnable keepPositionCellRunnable = null;
-  private  long keepPositionLayoutDelay = 150;
-
-
-  public BasicListComponent(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-    stickyHelper = new WXStickyHelper(this);
-  }
-
-  @SuppressLint("RtlHardcoded")
-  @Override
-  public void setMarginsSupportRTL(ViewGroup.MarginLayoutParams lp, int left, int top, int right, int bottom) {
-    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR1) {
-      lp.setMargins(left, top, right, bottom);
-      lp.setMarginStart(left);
-      lp.setMarginEnd(right);
-    } else {
-      if (lp instanceof FrameLayout.LayoutParams) {
-        FrameLayout.LayoutParams lp_frameLayout = (FrameLayout.LayoutParams) lp;
-        if (this.isLayoutRTL()) {
-          lp_frameLayout.gravity = Gravity.RIGHT | Gravity.TOP;
-          lp.setMargins(right, top, left, bottom);
-        } else {
-          lp_frameLayout.gravity = Gravity.LEFT | Gravity.TOP;
-          lp.setMargins(left, top, right, bottom);
-        }
-      } else {
-        lp.setMargins(left, top, right, bottom);
-      }
-    }
-  }
-
-  @Override
-  public void setLayout(WXComponent component) {
-    if (component.getHostView() != null) {
-      int layoutDirection = component.isLayoutRTL() ? ViewCompat.LAYOUT_DIRECTION_RTL : ViewCompat.LAYOUT_DIRECTION_LTR;
-      ViewCompat.setLayoutDirection(component.getHostView(), layoutDirection);
-    }
-    super.setLayout(component);
-  }
-
-  @Override
-  protected void onHostViewInitialized(T host) {
-    super.onHostViewInitialized(host);
-
-    WXRecyclerView recyclerView = host.getInnerView();
-    if (recyclerView == null || recyclerView.getAdapter() == null) {
-      WXLogUtils.e(TAG, "RecyclerView is not found or Adapter is not bound");
-      return;
-    }
-    if(WXUtils.getBoolean(getAttrs().get("prefetchGapDisable"), false)){
-      if(recyclerView.getLayoutManager() != null){
-        recyclerView.getLayoutManager().setItemPrefetchEnabled(false);
-      }
-    }
-
-    if (mChildren == null) {
-      WXLogUtils.e(TAG, "children is null");
-      return;
-    }
-
-    mDragHelper = new DefaultDragHelper(mChildren, recyclerView, new EventTrigger() {
-      @Override
-      public void triggerEvent(String type, Map<String, Object> args) {
-        fireEvent(type, args);
-      }
-    });
-
-    mTriggerType = getTriggerType(this);
-  }
-
-  /**
-   * Measure the size of the recyclerView.
-   *
-   * @param width  the expected width
-   * @param height the expected height
-   * @return the result of measurement
-   */
-  @Override
-  protected MeasureOutput measure(int width, int height) {
-    int screenH = WXViewUtils.getScreenHeight(getInstanceId());
-    int weexH = WXViewUtils.getWeexHeight(getInstanceId());
-    int outHeight = height > (weexH >= screenH ? screenH : weexH) ? weexH - getAbsoluteY() : height;
-    return super.measure(width, outHeight);
-  }
-
-  public int getOrientation() {
-    return Constants.Orientation.VERTICAL;
-  }
-
-  @Override
-  public void destroy() {
-    if(mAppearChangeRunnable != null &&  getHostView() != null) {
-      getHostView().removeCallbacks(mAppearChangeRunnable);
-      mAppearChangeRunnable = null;
-    }
-    super.destroy();
-    if (mStickyMap != null)
-      mStickyMap.clear();
-    if (mViewTypes != null)
-      mViewTypes.clear();
-    if (mRefToViewType != null)
-      mRefToViewType.clear();
-
-  }
-
-  @Override
-  public ViewGroup.LayoutParams getChildLayoutParams(WXComponent child, View hostView, int width, int height, int left, int right, int top, int bottom) {
-    ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) hostView.getLayoutParams();
-    if (child instanceof WXBaseRefresh && params == null) {
-      params = new LinearLayout.LayoutParams(width, height);
-    } else if (params == null) {
-      params = new RecyclerView.LayoutParams(width, height);
-    } else {
-      params.width = width;
-      params.height = height;
-
-      this.setMarginsSupportRTL(params, left, 0, right, 0);
-    }
-    return params;
-  }
-
-  abstract T generateListView(Context context, int orientation);
-
-  @Override
-  protected T initComponentHostView(@NonNull Context context) {
-    T bounceRecyclerView = generateListView(context, getOrientation());
-
-    String transforms = getAttrByKey(TRANSFORM);
-    if (transforms != null) {
-      bounceRecyclerView.getInnerView().addItemDecoration(RecyclerTransform.parseTransforms(getOrientation(), transforms));
-    }
-    if(getAttrs().get(Constants.Name.KEEP_POSITION_LAYOUT_DELAY) != null){
-      keepPositionLayoutDelay = WXUtils.getNumberInt(getAttrs().get(Constants.Name.KEEP_POSITION_LAYOUT_DELAY), (int)keepPositionLayoutDelay);
-    }
-    if(getAttrs().get("appearActionDelay") != null){
-      mAppearChangeRunnableDelay =  WXUtils.getNumberInt(getAttrs().get("appearActionDelay"), (int) mAppearChangeRunnableDelay);
-    }
-
-    mItemAnimator=bounceRecyclerView.getInnerView().getItemAnimator();
-
-    RecyclerViewBaseAdapter recyclerViewBaseAdapter = new RecyclerViewBaseAdapter<>(this);
-    recyclerViewBaseAdapter.setHasStableIds(true);
-    bounceRecyclerView.setRecyclerViewBaseAdapter(recyclerViewBaseAdapter);
-    bounceRecyclerView.setOverScrollMode(View.OVER_SCROLL_NEVER);
-    bounceRecyclerView.getInnerView().addOnScrollListener(mViewOnScrollListener);
-    if(getAttrs().get(Constants.Name.HAS_FIXED_SIZE) != null){
-      boolean hasFixedSize = WXUtils.getBoolean(getAttrs().get(Constants.Name.HAS_FIXED_SIZE), false);
-      bounceRecyclerView.getInnerView().setHasFixedSize(hasFixedSize);
-    }
-
-    bounceRecyclerView.getInnerView().addOnScrollListener(new RecyclerView.OnScrollListener() {
-      @Override
-      public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
-        super.onScrollStateChanged(recyclerView, newState);
-        getScrollStartEndHelper().onScrollStateChanged(newState);
-        List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
-        int size;
-        OnWXScrollListener listener;
-        if (listeners != null && (size = listeners.size()) > 0) {
-          for (int i=0; i<size; ++i) {
-            if(i >= listeners.size()){
-              break;
-            }
-            listener = listeners.get(i);
-            if (listener != null) {
-              View topView = recyclerView.getChildAt(0);
-              if (topView != null) {
-                int y = topView.getTop();
-                listener.onScrollStateChanged(recyclerView, 0, y, newState);
-              }
-            }
-          }
-        }
-      }
-
-      @Override
-      public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
-        super.onScrolled(recyclerView, dx, dy);
-        List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
-        if (listeners != null && listeners.size() > 0) {
-          try {
-            for (OnWXScrollListener listener : listeners) {
-              if (listener != null) {
-                if (listener instanceof ICheckBindingScroller) {
-                  if (((ICheckBindingScroller) listener).isNeedScroller(getRef(), null)) {
-                    listener.onScrolled(recyclerView, dx, dy);
-                  }
-                } else {
-                  listener.onScrolled(recyclerView, dx, dy);
-                }
-              }
-            }
-          } catch (Exception e) {
-            e.printStackTrace();
-          }
-        }
-      }
-    });
-
-    bounceRecyclerView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
-      @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
-      @Override
-      public void onGlobalLayout() {
-        T view;
-        if ((view = getHostView()) == null)
-          return;
-        mViewOnScrollListener.onScrolled(view.getInnerView(), 0, 0);
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
-          view.getViewTreeObserver().removeOnGlobalLayoutListener(this);
-        } else {
-          view.getViewTreeObserver().removeGlobalOnLayoutListener(this);
-        }
-      }
-    });
-    return bounceRecyclerView;
-  }
-
-  @Override
-  public void bindStickStyle(WXComponent component) {
-    stickyHelper.bindStickStyle(component, mStickyMap);
-  }
-
-  @Override
-  public void unbindStickStyle(WXComponent component) {
-    stickyHelper.unbindStickStyle(component, mStickyMap);
-    WXHeader cell = (WXHeader) findTypeParent(component, WXHeader.class);
-    if(cell != null && getHostView() != null) {
-      getHostView().notifyStickyRemove(cell);
-    }
-  }
-
-  private
-  @Nullable
-  WXComponent findDirectListChild(WXComponent comp) {
-    WXComponent parent;
-    if (comp == null || (parent = comp.getParent()) == null) {
-      return null;
-    }
-
-    if (parent instanceof BasicListComponent) {
-      return comp;
-    }
-
-    return findDirectListChild(parent);
-  }
-
-  @Override
-  protected boolean setProperty(String key, Object param) {
-    switch (key) {
-      case LOADMOREOFFSET:
-        return true;
-      case Constants.Name.SCROLLABLE:
-        boolean scrollable = WXUtils.getBoolean(param, true);
-        setScrollable(scrollable);
-        return true;
-      case Constants.Name.OFFSET_ACCURACY:
-        int accuracy = WXUtils.getInteger(param, 10);
-        setOffsetAccuracy(accuracy);
-        return true;
-      case Constants.Name.DRAGGABLE:
-        boolean draggable = WXUtils.getBoolean(param,false);
-        setDraggable(draggable);
-        return true;
-      case Constants.Name.SHOW_SCROLLBAR:
-        Boolean result = WXUtils.getBoolean(param,null);
-        if (result != null)
-          setShowScrollbar(result);
-        return true;
-    }
-    return super.setProperty(key, param);
-  }
-
-  @WXComponentProp(name = Constants.Name.SCROLLABLE)
-  public void setScrollable(boolean scrollable) {
-    this.isScrollable = scrollable;
-    WXRecyclerView inner = getHostView().getInnerView();
-    if(inner != null) {
-      inner.setScrollable(scrollable);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.OFFSET_ACCURACY)
-  public void setOffsetAccuracy(int accuracy) {
-    float real = WXViewUtils.getRealPxByWidth(accuracy, getInstance().getInstanceViewPortWidth());
-    this.mOffsetAccuracy = (int) real;
-  }
-
-  @WXComponentProp(name = Constants.Name.DRAGGABLE)
-  public void setDraggable(boolean isDraggable) {
-    if (mDragHelper != null) {
-      mDragHelper.setDraggable(isDraggable);
-    }
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("set draggable : " + isDraggable);
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.SHOW_SCROLLBAR)
-  public void setShowScrollbar(boolean show) {
-    if(getHostView() == null || getHostView().getInnerView() == null){
-      return;
-    }
-    if (getOrientation() == Constants.Orientation.VERTICAL) {
-      getHostView().getInnerView().setVerticalScrollBarEnabled(show);
-    } else {
-      getHostView().getInnerView().setHorizontalScrollBarEnabled(show);
-    }
-  }
-
-  @Override
-  public boolean isScrollable() {
-    return isScrollable;
-  }
-
-
-  private void setAppearanceWatch(WXComponent component, int event, boolean enable) {
-    AppearanceHelper item = mAppearComponents.get(component.getRef());
-    if (item != null) {
-      item.setWatchEvent(event, enable);
-    } else if (!enable) {
-      //Do nothing if disable target not exist.
-    } else {
-      WXComponent dChild = findDirectListChild(component);
-      int index = mChildren.indexOf(dChild);
-      if (index != -1) {
-        item = new AppearanceHelper(component, index);
-        item.setWatchEvent(event, true);
-        mAppearComponents.put(component.getRef(), item);
-      }
-    }
-  }
-
-  @Override
-  public void bindAppearEvent(WXComponent component) {
-    setAppearanceWatch(component, AppearanceHelper.APPEAR, true);
-    if(mAppearChangeRunnable == null){
-      mAppearChangeRunnable =  new Runnable() {
-        @Override
-        public void run() {
-          if(mAppearChangeRunnable != null) {
-            notifyAppearStateChange(0, 0, 0, 0);
-          }
-        }
-      };
-    }
-    if (getHostView() != null) {
-      getHostView().removeCallbacks(mAppearChangeRunnable);
-      getHostView().postDelayed(mAppearChangeRunnable, mAppearChangeRunnableDelay);
-    }
-  }
-
-  @Override
-  public void bindDisappearEvent(WXComponent component) {
-    setAppearanceWatch(component, AppearanceHelper.DISAPPEAR, true);
-  }
-
-  @Override
-  public void unbindAppearEvent(WXComponent component) {
-    setAppearanceWatch(component, AppearanceHelper.APPEAR, false);
-  }
-
-  @Override
-  public void unbindDisappearEvent(WXComponent component) {
-    setAppearanceWatch(component, AppearanceHelper.DISAPPEAR, false);
-  }
-
-  @Override
-  public void scrollTo(WXComponent component, Map<String, Object> options) {
-    float offsetFloat = 0;
-    boolean smooth = true;
-
-    if (options != null) {
-      String offsetStr = options.get(Constants.Name.OFFSET) == null ? "0" : options.get(Constants.Name.OFFSET).toString();
-      smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
-      if (offsetStr != null) {
-        try {
-          offsetFloat = WXViewUtils.getRealPxByWidth(Float.parseFloat(offsetStr), getInstance().getInstanceViewPortWidth());
-        }catch (Exception e ){
-          WXLogUtils.e("Float parseFloat error :"+e.getMessage());
-        }
-      }
-    }
-
-    final int offset = (int) offsetFloat;
-
-    T bounceRecyclerView = getHostView();
-    if (bounceRecyclerView == null) {
-      return;
-    }
-
-    WXComponent parent = component;
-    WXCell cell = null;
-    while (parent != null) {
-      if (parent instanceof WXCell) {
-        cell = (WXCell) parent;
-        break;
-      }
-      parent = parent.getParent();
-    }
-
-    if (cell != null) {
-      final int pos = mChildren.indexOf(cell);
-      if (pos == -1) {
-        //Invalid position
-        return;
-      }
-      final WXRecyclerView view = bounceRecyclerView.getInnerView();
-      view.scrollTo(smooth, pos, offset, getOrientation());
-    }
-  }
-
-  @Override
-  public void onBeforeScroll(int dx, int dy) {
-    T bounceRecyclerView = getHostView();
-    if (mStickyMap == null || bounceRecyclerView == null) {
-      return;
-    }
-    Map<String, WXComponent> stickyMap = mStickyMap.get(getRef());
-    if (stickyMap == null) {
-      return;
-    }
-    Iterator<Map.Entry<String, WXComponent>> iterator = stickyMap.entrySet().iterator();
-    Map.Entry<String, WXComponent> entry;
-    WXComponent stickyComponent;
-    int currentStickyPos = -1;
-    while (iterator.hasNext()) {
-      entry = iterator.next();
-      stickyComponent = entry.getValue();
-
-      if (stickyComponent != null && stickyComponent instanceof WXCell) {
-
-        WXCell cell = (WXCell) stickyComponent;
-        if (cell.getHostView() == null) {
-          return;
-        }
-
-        int[] location = new int[2];
-        stickyComponent.getHostView().getLocationOnScreen(location);
-        int[] parentLocation = new int[2];
-        stickyComponent.getParentScroller().getView().getLocationOnScreen(parentLocation);
-        int top = location[1] - parentLocation[1];
-
-
-        RecyclerView.LayoutManager layoutManager;
-        boolean beforeFirstVisibleItem = false;
-        boolean removeOldSticky = false;
-        layoutManager = getHostView().getInnerView().getLayoutManager();
-        if (layoutManager instanceof LinearLayoutManager || layoutManager instanceof GridLayoutManager) {
-          int firstVisiblePosition = ((LinearLayoutManager) layoutManager).findFirstVisibleItemPosition();
-          int lastVisiblePosition = ((LinearLayoutManager) layoutManager).findLastVisibleItemPosition();
-          int pos = mChildren.indexOf(cell);
-          cell.setScrollPositon(pos);
-          if (pos <= firstVisiblePosition
-                  || (cell.getStickyOffset() > 0 && firstVisiblePosition < pos && pos <= lastVisiblePosition  &&
-                  top <= cell.getStickyOffset())) {
-            beforeFirstVisibleItem = true;
-            if(pos > currentStickyPos) {
-              currentStickyPos = pos;
-            }
-          }else{
-            removeOldSticky = true;
-          }
-        } else if(layoutManager instanceof StaggeredGridLayoutManager){
-          int [] firstItems= new int[3];
-          int firstVisiblePosition = ((StaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(firstItems)[0];
-          int lastVisiblePosition = ((StaggeredGridLayoutManager)  layoutManager).findLastVisibleItemPositions(firstItems)[0];
-          int pos = mChildren.indexOf(cell);
-
-          if (pos <= firstVisiblePosition || (cell.getStickyOffset() > 0 && firstVisiblePosition < pos && pos <= lastVisiblePosition  &&
-                  top <= cell.getStickyOffset())) {
-            beforeFirstVisibleItem = true;
-            if(pos > currentStickyPos) {
-              currentStickyPos = pos;
-            }
-          }else{
-            removeOldSticky = true;
-          }
-        }
-
-
-        boolean showSticky = beforeFirstVisibleItem && cell.getLocationFromStart() >= 0 && top <= cell.getStickyOffset() && dy >= 0;
-        boolean removeSticky = cell.getLocationFromStart() <= cell.getStickyOffset() && top > cell.getStickyOffset() && dy <= 0;
-        if (showSticky) {
-          bounceRecyclerView.notifyStickyShow(cell);
-        } else if (removeSticky || removeOldSticky) {
-          bounceRecyclerView.notifyStickyRemove(cell);
-        }
-        cell.setLocationFromStart(top);
-      }
-    }
-
-    if(currentStickyPos >= 0){
-      bounceRecyclerView.updateStickyView(currentStickyPos);
-    }else{
-      if(bounceRecyclerView instanceof BounceRecyclerView){
-        ((BounceRecyclerView) bounceRecyclerView).getStickyHeaderHelper().clearStickyHeaders();
-      }
-    }
-  }
-
-  @Override
-  public int getScrollY() {
-    T bounceRecyclerView = getHostView();
-    return bounceRecyclerView == null ? 0 : bounceRecyclerView.getInnerView().getScrollY();
-  }
-
-  @Override
-  public int getScrollX() {
-    T bounceRecyclerView = getHostView();
-    return bounceRecyclerView == null ? 0 : bounceRecyclerView.getInnerView().getScrollX();
-  }
-
-  /**
-   * Append a child component to the end of list. This will not refresh the underlying
-   * view immediately. The message of index of the inserted child is given to the adapter, and the
-   * adapter will determine when to refresh. The default implementation of adapter will push the
-   * message into a message and refresh the view in a period of time.
-   *
-   * @param child the inserted child
-   */
-  @Override
-  public void addChild(WXComponent child) {
-    addChild(child, -1);
-  }
-
-  @Override
-  protected int getChildrenLayoutTopOffset() {
-    return 0;
-  }
-
-  /**
-   * @param child the inserted child
-   * @param index the index of the child to be inserted.
-   * @see #addChild(WXComponent)
-   */
-  @Override
-  public void addChild(WXComponent child, int index) {
-    super.addChild(child, index);
-    if (child == null || index < -1) {
-      return;
-    }
-    int count = mChildren.size();
-    index = index >= count ? -1 : index;
-    bindViewType(child);
-
-    int adapterPosition = index == -1 ? mChildren.size() - 1 : index;
-    final T view = getHostView();
-    if (view != null) {
-      boolean isAddAnimation = false;
-      if (getBasicComponentData() != null) {
-        Object attr = getAttrs().get(Constants.Name.INSERT_CELL_ANIMATION);
-        if (Constants.Value.DEFAULT.equals(attr)) {
-          isAddAnimation = true;
-        }
-      }
-      if (isAddAnimation) {
-        view.getInnerView().setItemAnimator(mItemAnimator);
-      } else {
-        view.getInnerView().setItemAnimator(null);
-      }
-      boolean isKeepScrollPosition =  false;
-      if (child.getBasicComponentData() != null) {
-        Object attr = child.getAttrs().get(Constants.Name.KEEP_SCROLL_POSITION);
-        if (WXUtils.getBoolean(attr, false) && index <= getChildCount() && index>-1) {
-          isKeepScrollPosition = true;
-        }
-      }
-      if (isKeepScrollPosition) {
-        if(view.getInnerView().getLayoutManager() instanceof  LinearLayoutManager){
-          if(keepPositionCell == null){
-            int last=((LinearLayoutManager)view.getInnerView().getLayoutManager()).findLastCompletelyVisibleItemPosition();
-            ListBaseViewHolder holder = (ListBaseViewHolder) view.getInnerView().findViewHolderForAdapterPosition(last);
-            if(holder != null){
-              keepPositionCell = holder.getComponent();
-            }
-            if(keepPositionCell != null) {
-              if(!view.getInnerView().isLayoutFrozen()){ //frozen, prevent layout when scroll
-                view.getInnerView().setLayoutFrozen(true);
-              }
-              if(keepPositionCellRunnable != null){
-                view.removeCallbacks(keepPositionCellRunnable);
-              }
-              keepPositionCellRunnable = new Runnable() {
-                @Override
-                public void run() {
-                  if(keepPositionCell != null){
-                    int keepPosition = indexOf(keepPositionCell);
-                    int offset = 0;
-                    if(keepPositionCell.getHostView() != null){
-                      offset = keepPositionCell.getHostView().getTop();
-                    }
-                    if(offset > 0) {
-                      ((LinearLayoutManager) view.getInnerView().getLayoutManager()).scrollToPositionWithOffset(keepPosition, offset);
-                    }else{
-                      view.getInnerView().getLayoutManager().scrollToPosition(keepPosition);
-
-                    }
-                    view.getInnerView().setLayoutFrozen(false);
-                    keepPositionCell = null;
-                    keepPositionCellRunnable = null;
-                  }
-                }
-              };
-            }
-          }
-          if(keepPositionCellRunnable == null){
-            view.getInnerView().scrollToPosition(((LinearLayoutManager)view.getInnerView().getLayoutManager()).findLastVisibleItemPosition());
-          }
-        }
-        view.getRecyclerViewBaseAdapter().notifyItemInserted(adapterPosition);
-        if(keepPositionCellRunnable != null){
-          view.removeCallbacks(keepPositionCellRunnable);
-          view.postDelayed(keepPositionCellRunnable, keepPositionLayoutDelay);
-        }
-      } else {
-        view.getRecyclerViewBaseAdapter().notifyItemChanged(adapterPosition);
-      }
-    }
-    relocateAppearanceHelper();
-  }
-
-  private void relocateAppearanceHelper() {
-    Iterator<Map.Entry<String, AppearanceHelper>> iterator = mAppearComponents.entrySet().iterator();
-    while (iterator.hasNext()) {
-      Map.Entry<String, AppearanceHelper> item = iterator.next();
-      AppearanceHelper value = item.getValue();
-      WXComponent dChild = findDirectListChild(value.getAwareChild());
-      int index = mChildren.indexOf(dChild);
-      value.setCellPosition(index);
-    }
-  }
-
-
-  /**
-   * RecyclerView manage its children in a way that different from {@link WXVContainer}. Therefore,
-   * {@link WXVContainer#addSubView(View, int)} is an empty implementation in {@link
-   * com.taobao.weex.ui.view.listview.WXRecyclerView}
-   */
-  @Override
-  public void addSubView(View child, int index) {
-
-  }
-
-  /**
-   * Remove the child from list. This method will use {@link
-   * java.util.List#indexOf(Object)} to retrieve the component to be deleted. Like {@link
-   * #addChild(WXComponent)}, this method will not refresh the view immediately, the adapter will
-   * decide when to refresh.
-   *
-   * @param child the child to be removed
-   */
-  @Override
-  public void remove(WXComponent child, boolean destroy) {
-    int index = mChildren.indexOf(child);
-    if (destroy) {
-      child.detachViewAndClearPreInfo();
-    }
-    unBindViewType(child);
-
-    T view = getHostView();
-    if (view == null) {
-      return;
-    }
-
-    boolean isRemoveAnimation = false;
-    Object attr = child.getAttrs().get(Constants.Name.DELETE_CELL_ANIMATION);
-    if (Constants.Value.DEFAULT.equals(attr)) {
-      isRemoveAnimation = true;
-    }
-    if (isRemoveAnimation) {
-      view.getInnerView().setItemAnimator(mItemAnimator);
-    } else {
-      view.getInnerView().setItemAnimator(null);
-    }
-
-    view.getRecyclerViewBaseAdapter().notifyItemRemoved(index);
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d(TAG, "removeChild child at " + index);
-    }
-    super.remove(child, destroy);
-  }
-
-
-
-  @Override
-  public void computeVisiblePointInViewCoordinate(PointF pointF) {
-    RecyclerView view = getHostView().getInnerView();
-    pointF.set(view.computeHorizontalScrollOffset(), view.computeVerticalScrollOffset());
-  }
-
-  /**
-   * Recycle viewHolder and its underlying view. This may because the view is removed or reused.
-   * Either case, this method will be called.
-   *
-   * @param holder The view holder to be recycled.
-   */
-  @Override
-  public void onViewRecycled(ListBaseViewHolder holder) {
-    long begin = System.currentTimeMillis();
-
-    holder.setComponentUsing(false);
-    if (holder != null
-            && holder.canRecycled()
-            && holder.getComponent() != null
-            && !holder.getComponent().isUsing()) {
-      holder.recycled();
-
-    } else {
-      WXLogUtils.w(TAG, "this holder can not be allowed to  recycled");
-    }
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d(TAG, "Recycle holder " + (System.currentTimeMillis() - begin) + "  Thread:" + Thread.currentThread().getName());
-    }
-  }
-
-  /**
-   * Bind the component of the position to the holder. Then flush the view.
-   *
-   * @param holder   viewHolder, which holds reference to the view
-   * @param position position of component in list
-   */
-  @Override
-  public void onBindViewHolder(final ListBaseViewHolder holder, int position) {
-    if (holder == null) return;
-    holder.setComponentUsing(true);
-    WXComponent component = getChild(position);
-    if (component == null
-            || (component instanceof WXRefresh)
-            || (component instanceof WXLoading)
-            || (component.isFixed())
-            ) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.d(TAG, "Bind WXRefresh & WXLoading " + holder);
-      }
-      if(component instanceof  WXBaseRefresh
-              && holder.getView() != null
-              && (component.getAttrs().get("holderBackground") != null)){
-        Object holderBackground = component.getAttrs().get("holderBackground");
-        int color = WXResourceUtils.getColor(holderBackground.toString(), Color.WHITE);
-        holder.getView().setBackgroundColor(color);
-        holder.getView().setVisibility(View.VISIBLE);
-        holder.getView().postInvalidate();
-      }
-      return;
-    }
-
-    if (holder.getComponent() != null && holder.getComponent() instanceof WXCell) {
-      if(holder.isRecycled()) {
-        holder.bindData(component);
-        component.onRenderFinish(STATE_UI_FINISH);
-      }
-      if (mDragHelper == null || !mDragHelper.isDraggable()) {
-        return;
-      }
-      mTriggerType = (mTriggerType == null) ? DEFAULT_TRIGGER_TYPE : mTriggerType;
-
-      WXCell cell = (WXCell) holder.getComponent();
-      boolean isExcluded = DEFAULT_EXCLUDED;
-      WXAttr cellAttrs = cell.getAttrs();
-      isExcluded = WXUtils.getBoolean(cellAttrs.get(EXCLUDED), DEFAULT_EXCLUDED);
-
-      mDragHelper.setDragExcluded(holder, isExcluded);
-
-      //NOTICE: event maybe consumed by other views
-      if (DragTriggerType.PAN.equals(mTriggerType)) {
-        mDragHelper.setLongPressDragEnabled(false);
-
-        WXComponent anchorComponent = findComponentByAnchorName(cell, DRAG_ANCHOR);
-
-        if (anchorComponent != null && anchorComponent.getHostView() != null && !isExcluded) {
-          View anchor = anchorComponent.getHostView();
-          anchor.setOnTouchListener(new View.OnTouchListener() {
-            @SuppressLint("ClickableViewAccessibility")
-            @Override
-            public boolean onTouch(View v, MotionEvent event) {
-              if (MotionEventCompat.getActionMasked(event) == MotionEvent.ACTION_DOWN) {
-                mDragHelper.startDrag(holder);
-              }
-              return true;
-            }
-          });
-        } else {
-          if (WXEnvironment.isApkDebugable()) {
-            if(!isExcluded) {
-              WXLogUtils.e(TAG, "[error] onBindViewHolder: the anchor component or view is not found");
-            } else {
-              WXLogUtils.d(TAG, "onBindViewHolder: position "+ position + " is drag excluded");
-            }
-          }
-        }
-
-      } else if (DragTriggerType.LONG_PRESS.equals(mTriggerType)) {
-        mDragHelper.setLongPressDragEnabled(true);
-      }
-    }
-
-  }
-
-  protected void markComponentUsable(){
-    for (WXComponent component : mChildren){
-      component.setUsing(false);
-    }
-  }
-  /**
-   * Create an instance of {@link ListBaseViewHolder} for the given viewType (not for the given
-   * index). This  markComponentUsable();method will look up for the first component that fits the viewType requirement and
-   * doesn't be used. Then create the certain type of view, detach the view f[rom the component.
-   *
-   * @param parent   the ViewGroup into which the new view will be inserted
-   * @param viewType the type of the new view
-   * @return the created view holder.
-   */
-  @Override
-  public ListBaseViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
-    if (mChildren != null) {
-      if (mViewTypes == null)
-        return createVHForFakeComponent(viewType);
-      ArrayList<WXComponent> mTypes = mViewTypes.get(viewType);
-      checkRecycledViewPool(viewType);
-      if (mTypes == null)
-        return createVHForFakeComponent(viewType);
-
-      for (int i = 0; i < mTypes.size(); i++) {
-        WXComponent component = mTypes.get(i);
-        if (component == null
-            || component.isUsing()) {
-          continue;
-        }
-        if (component.isFixed()) {
-          return createVHForFakeComponent(viewType);
-        } else {
-          if (component instanceof WXCell) {
-            if (component.getRealView() != null) {
-              return new ListBaseViewHolder(component, viewType);
-            } else {
-              component.lazy(false);
-              component.createView();
-              component.applyLayoutAndEvent(component);
-              return new ListBaseViewHolder(component, viewType, true);
-            }
-          } else if (component instanceof WXBaseRefresh) {
-            return createVHForRefreshComponent(viewType);
-          } else {
-            WXLogUtils.e(TAG, "List cannot include element except cell、header、fixed、refresh and loading");
-            return createVHForFakeComponent(viewType);
-          }
-        }
-      }
-    }
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.e(TAG, "Cannot find request viewType: " + viewType);
-    }
-    return createVHForFakeComponent(viewType);
-  }
-
-  /**
-   * Forbid ViewHolder cache if viewType > MAX_VIEWTYPE_ALLOW_CACHE
-   *
-   * @param viewType
-   */
-  private void checkRecycledViewPool(int viewType) {
-    try {
-      if (mViewTypes.size() > MAX_VIEWTYPE_ALLOW_CACHE)
-        mAllowCacheViewHolder = false;
-
-      if (mDownForBidCacheViewHolder)
-        if (getHostView() != null && getHostView().getInnerView() != null)
-          getHostView().getInnerView().getRecycledViewPool().setMaxRecycledViews(viewType, 0);
-
-      if (!mDownForBidCacheViewHolder) {
-        if (!mAllowCacheViewHolder) {
-          if (getHostView() != null && getHostView().getInnerView() != null) {
-            for (int i = 0; i < mViewTypes.size(); i++) {
-              getHostView().getInnerView().getRecycledViewPool().setMaxRecycledViews(mViewTypes.keyAt(i), 0);
-            }
-            mDownForBidCacheViewHolder = true;
-          }
-        }
-      }
-    } catch (Exception e) {
-      WXLogUtils.e(TAG, "Clear recycledViewPool error!");
-    }
-  }
-
-  /**
-   * Return the child component type. The type is defined by scopeValue in .we file.
-   *
-   * @param position the position of the child component.
-   * @return the type of certain component.
-   */
-  @Override
-  public int getItemViewType(int position) {
-    return generateViewType(getChild(position));
-  }
-
-  @Nullable
-  private WXComponent findComponentByAnchorName(@NonNull WXComponent root, @NonNull String anchorName) {
-    long start = 0;
-    if (WXEnvironment.isApkDebugable()) {
-      start = System.currentTimeMillis();
-    }
-
-    Deque<WXComponent> deque = new ArrayDeque<>();
-    deque.add(root);
-    while (!deque.isEmpty()) {
-      WXComponent curComponent = deque.removeFirst();
-      if (curComponent != null) {
-        String isAnchorSet = WXUtils.getString(curComponent.getAttrs().get(anchorName), null);
-
-        //hit
-        if (isAnchorSet != null && isAnchorSet.equals("true")) {
-          if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.d("dragPerf", "findComponentByAnchorName time: " + (System.currentTimeMillis() - start) + "ms");
-          }
-          return curComponent;
-        }
-      }
-      if (curComponent instanceof WXVContainer) {
-        WXVContainer container = (WXVContainer) curComponent;
-        for (int i = 0, len = container.childCount(); i < len; i++) {
-          WXComponent child = container.getChild(i);
-          deque.add(child);
-        }
-      }
-    }
-
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("dragPerf", "findComponentByAnchorName elapsed time: " + (System.currentTimeMillis() - start) + "ms");
-    }
-    return null;
-
-  }
-
-  private String getTriggerType(@Nullable WXComponent component) {
-    String triggerType = DEFAULT_TRIGGER_TYPE;
-    if (component == null) {
-      return triggerType;
-    }
-    triggerType = WXUtils.getString(component.getAttrs().get(DRAG_TRIGGER_TYPE), DEFAULT_TRIGGER_TYPE);
-    if (!DragTriggerType.LONG_PRESS.equals(triggerType) && !DragTriggerType.PAN.equals(triggerType)) {
-      triggerType = DEFAULT_TRIGGER_TYPE;
-    }
-
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d(TAG, "trigger type is " + triggerType);
-    }
-
-    return triggerType;
-  }
-
-
-  /**
-   * ViewType will be classified into {HashMap<Integer,ArrayList<Integer>> mViewTypes}
-   *
-   * @param component
-   */
-  private void bindViewType(WXComponent component) {
-    int id = generateViewType(component);
-
-    if (mViewTypes == null) {
-      mViewTypes = new SparseArray<>();
-    }
-
-    ArrayList<WXComponent> mTypes = mViewTypes.get(id);
-
-    if (mTypes == null) {
-      mTypes = new ArrayList<>();
-      mViewTypes.put(id, mTypes);
-    }
-    mTypes.add(component);
-  }
-
-  private void unBindViewType(WXComponent component) {
-    int id = generateViewType(component);
-
-    if (mViewTypes == null)
-      return;
-    ArrayList<WXComponent> mTypes = mViewTypes.get(id);
-    if (mTypes == null)
-      return;
-
-    mTypes.remove(component);
-  }
-
-  /**
-   * generate viewtype by component
-   *
-   * @param component
-   * @return
-   */
-  private int generateViewType(WXComponent component) {
-    long id;
-    try {
-      id = Integer.parseInt(component.getRef());
-      String type = component.getAttrs().getScope();
-
-      if (!TextUtils.isEmpty(type)) {
-        if (mRefToViewType == null) {
-          mRefToViewType = new ArrayMap<>();
-        }
-        if (!mRefToViewType.containsKey(type)) {
-          mRefToViewType.put(type, id);
-        }
-        id = mRefToViewType.get(type);
-
-      }
-    } catch (RuntimeException e) {
-      WXLogUtils.eTag(TAG, e);
-      id = RecyclerView.NO_ID;
-      WXLogUtils.e(TAG, "getItemViewType: NO ID, this will crash the whole render system of WXListRecyclerView");
-    }
-    return (int) id;
-  }
-
-  /**
-   * Get child component num.
-   *
-   * @return return the size of {@link #mChildren} if mChildren is not empty, otherwise, return 0;
-   */
-  @Override
-  public int getItemCount() {
-    return getChildCount();
-  }
-
-  @Override
-  public boolean onFailedToRecycleView(ListBaseViewHolder holder) {
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d(TAG, "Failed to recycle " + holder);
-    }
-    return false;
-  }
-
-  @Override
-  public long getItemId(int position) {
-    long id;
-    try {
-      id = Long.parseLong(getChild(position).getRef());
-    } catch (RuntimeException e) {
-      WXLogUtils.e(TAG, WXLogUtils.getStackTrace(e));
-      id = RecyclerView.NO_ID;
-    }
-    return id;
-  }
-
-  @Override
-  public void onLoadMore(int offScreenY) {
-    try {
-      String offset = getAttrs().getLoadMoreOffset();
-
-      if (TextUtils.isEmpty(offset)) {
-        offset = "0";
-      }
-
-
-      float offsetParsed = WXViewUtils.getRealPxByWidth(WXUtils.getInt(offset),getInstance().getInstanceViewPortWidth());
-
-      if (offScreenY <= offsetParsed && getEvents().contains(Constants.Event.LOADMORE)) {
-        if (mListCellCount != mChildren.size()
-            || mForceLoadmoreNextTime) {
-          fireEvent(Constants.Event.LOADMORE);
-          mListCellCount = mChildren.size();
-          mForceLoadmoreNextTime = false;
-        }
-      }
-    } catch (Exception e) {
-      WXLogUtils.d(TAG + "onLoadMore :", e);
-    }
-  }
-
-  @Override
-  public void notifyAppearStateChange(int firstVisible, int lastVisible, int directionX, int directionY) {
-    if(mAppearChangeRunnable != null) {
-      getHostView().removeCallbacks(mAppearChangeRunnable);
-      mAppearChangeRunnable = null;
-    }
-    //notify appear state
-    Iterator<AppearanceHelper> it = mAppearComponents.values().iterator();
-    String direction = directionY > 0 ? Constants.Value.DIRECTION_UP :
-            directionY < 0 ? Constants.Value.DIRECTION_DOWN : null;
-    if (getOrientation() == Constants.Orientation.HORIZONTAL && directionX != 0) {
-      direction = directionX > 0 ? Constants.Value.DIRECTION_LEFT : Constants.Value.DIRECTION_RIGHT;
-    }
-
-    while (it.hasNext()) {
-      AppearanceHelper item = it.next();
-      WXComponent component = item.getAwareChild();
-
-      if (!item.isWatch()) {
-        continue;
-      }
-
-
-      View view = component.getHostView();
-      if (view == null) {
-        continue;
-      }
-
-      boolean outOfVisibleRange = !ViewCompat.isAttachedToWindow(view);
-      boolean visible = (!outOfVisibleRange) && item.isViewVisible(true);
-
-      int result = item.setAppearStatus(visible);
-      if (result == AppearanceHelper.RESULT_NO_CHANGE) {
-        continue;
-      }
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.d("appear", "item " + item.getCellPositionINScollable() + " result " + result);
-      }
-      component.notifyAppearStateChange(result == AppearanceHelper.RESULT_APPEAR ? Constants.Event.APPEAR : Constants.Event.DISAPPEAR, direction);
-    }
-  }
-
-  @NonNull
-  private ListBaseViewHolder createVHForFakeComponent(int viewType) {
-    FrameLayout view = new FrameLayout(getContext());
-    view.setBackgroundColor(Color.WHITE);
-    view.setLayoutParams(new FrameLayout.LayoutParams(0, 0));
-    return new ListBaseViewHolder(view, viewType);
-  }
-
-
-  private ListBaseViewHolder createVHForRefreshComponent(int viewType) {
-    FrameLayout view = new FrameLayout(getContext());
-    view.setLayoutParams(new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, 1));
-    return new ListBaseViewHolder(view, viewType);
-  }
-
-  @JSMethod
-  public void resetLoadmore() {
-    mForceLoadmoreNextTime = true;
-    mListCellCount = 0;
-  }
-
-  @Override
-  public void addEvent(String type) {
-    super.addEvent(type);
-    if (ScrollStartEndHelper.isScrollEvent(type)
-            && getHostView() != null
-            && getHostView().getInnerView() != null
-            && !mHasAddScrollEvent) {
-      mHasAddScrollEvent = true;
-      WXRecyclerView innerView = getHostView().getInnerView();
-      innerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
-        private int offsetXCorrection, offsetYCorrection;
-        private boolean mFirstEvent = true;
-
-        @Override
-        public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
-          super.onScrolled(recyclerView, dx, dy);
-//          WXLogUtils.e("SCROLL", dx + ", " + dy + ", " + recyclerView.computeHorizontalScrollRange()
-//          + ", " + recyclerView.computeVerticalScrollRange()
-//          + ", " + recyclerView.computeHorizontalScrollOffset()
-//          + ", " + recyclerView.computeVerticalScrollOffset());
-
-          int offsetX = recyclerView.computeHorizontalScrollOffset();
-          int offsetY = recyclerView.computeVerticalScrollOffset();
-
-          if (dx == 0 && dy == 0) {
-            offsetXCorrection = offsetX;
-            offsetYCorrection = offsetY;
-            offsetX = 0;
-            offsetY = 0;
-          } else {
-            offsetX = offsetX - offsetXCorrection;
-            offsetY = offsetY - offsetYCorrection;
-          }
-          getScrollStartEndHelper().onScrolled(offsetX, offsetY);
-          if(!getEvents().contains(Constants.Event.SCROLL)){
-            return;
-          }
-          if (mFirstEvent) {
-            //skip first event
-            mFirstEvent = false;
-            return;
-          }
-
-          RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
-          if (!layoutManager.canScrollVertically()) {
-            return;
-          }
-
-          if (shouldReport(offsetX, offsetY)) {
-            fireScrollEvent(recyclerView, offsetX, offsetY);
-          }
-        }
-      });
-    }
-  }
-
-  private void fireScrollEvent(RecyclerView recyclerView, int offsetX, int offsetY) {
-    fireEvent(Constants.Event.SCROLL, getScrollEvent(recyclerView, offsetX, offsetY));
-  }
-
-  public Map<String, Object> getScrollEvent(RecyclerView recyclerView, int offsetX, int offsetY){
-    if(getOrientation() == Constants.Orientation.VERTICAL){
-      offsetY = - calcContentOffset(recyclerView);
-    }
-    int contentWidth = recyclerView.getMeasuredWidth() + recyclerView.computeHorizontalScrollRange();
-    int contentHeight = 0;
-    for (int i = 0; i < getChildCount(); i++) {
-      WXComponent child = getChild(i);
-      if (child != null) {
-        contentHeight += child.getLayoutHeight();
-      }
-    }
-
-    Map<String, Object> event = new HashMap<>(3);
-    Map<String, Object> contentSize = new HashMap<>(3);
-    Map<String, Object> contentOffset = new HashMap<>(3);
-
-    contentSize.put(Constants.Name.WIDTH, WXViewUtils.getWebPxByWidth(contentWidth, getInstance().getInstanceViewPortWidth()));
-    contentSize.put(Constants.Name.HEIGHT, WXViewUtils.getWebPxByWidth(contentHeight, getInstance().getInstanceViewPortWidth()));
-
-    contentOffset.put(Constants.Name.X, - WXViewUtils.getWebPxByWidth(offsetX, getInstance().getInstanceViewPortWidth()));
-    contentOffset.put(Constants.Name.Y, - WXViewUtils.getWebPxByWidth(offsetY, getInstance().getInstanceViewPortWidth()));
-    event.put(Constants.Name.CONTENT_SIZE, contentSize);
-    event.put(Constants.Name.CONTENT_OFFSET, contentOffset);
-    event.put(Constants.Name.ISDRAGGING, recyclerView.getScrollState() == RecyclerView.SCROLL_STATE_DRAGGING);
-    return event;
-  }
-
-  private boolean shouldReport(int offsetX, int offsetY) {
-    if (mLastReport.x == -1 && mLastReport.y == -1) {
-      mLastReport.x = offsetX;
-      mLastReport.y = offsetY;
-      return true;
-    }
-
-    int gapX = Math.abs(mLastReport.x - offsetX);
-    int gapY = Math.abs(mLastReport.y - offsetY);
-
-    if (gapX >= mOffsetAccuracy || gapY >= mOffsetAccuracy) {
-      mLastReport.x = offsetX;
-      mLastReport.y = offsetY;
-      return true;
-    }
-
-    return false;
-  }
-
-
-
-  public int calcContentOffset(RecyclerView recyclerView) {
-    RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
-    if (layoutManager instanceof LinearLayoutManager) {
-      int firstVisibleItemPosition = ((LinearLayoutManager) layoutManager).findFirstVisibleItemPosition();
-      if (firstVisibleItemPosition == -1) {
-        return 0;
-      }
-
-      View firstVisibleView = layoutManager.findViewByPosition(firstVisibleItemPosition);
-      int firstVisibleViewOffset = 0;
-      if (firstVisibleView != null) {
-        firstVisibleViewOffset = firstVisibleView.getTop();
-      }
-
-      int offset = 0;
-      for (int i=0;i<firstVisibleItemPosition;i++) {
-        WXComponent child = getChild(i);
-        if (child != null) {
-          offset -= child.getLayoutHeight();
-        }
-      }
-
-      if (layoutManager instanceof GridLayoutManager) {
-        int spanCount = ((GridLayoutManager) layoutManager).getSpanCount();
-        offset = offset / spanCount;
-      }
-
-      offset += firstVisibleViewOffset;
-      return offset;
-    } else if (layoutManager instanceof StaggeredGridLayoutManager) {
-      int spanCount = ((StaggeredGridLayoutManager) layoutManager).getSpanCount();
-      int firstVisibleItemPosition = ((StaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(null)[0];
-      if (firstVisibleItemPosition == -1) {
-        return 0;
-      }
-
-      View firstVisibleView = layoutManager.findViewByPosition(firstVisibleItemPosition);
-      int firstVisibleViewOffset = 0;
-      if (firstVisibleView != null) {
-        firstVisibleViewOffset = firstVisibleView.getTop();
-      }
-
-      int offset = 0;
-      for (int i=0;i<firstVisibleItemPosition;i++) {
-        WXComponent child = getChild(i);
-        if (child != null) {
-          offset -= child.getLayoutHeight();
-        }
-      }
-
-      offset = offset / spanCount;
-      offset += firstVisibleViewOffset;
-      return offset;
-    }
-    //Unhandled LayoutManager type
-    return -1;
-  }
-
-  public ScrollStartEndHelper getScrollStartEndHelper() {
-    if(mScrollStartEndHelper == null){
-      mScrollStartEndHelper = new ScrollStartEndHelper(this);
-    }
-    return mScrollStartEndHelper;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DefaultDragHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DefaultDragHelper.java
deleted file mode 100644
index 50c4bb7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DefaultDragHelper.java
+++ /dev/null
@@ -1,173 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.helper.ItemTouchHelper;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Description:
- * Drag-drop support for list
- * <p>
- * Created by rowandjj(chuyi)<br/>
- */
-
-class DefaultDragHelper implements DragHelper {
-
-    private boolean mLongPressEnabled;
-
-    @NonNull
-    private final EventTrigger mEventTrigger;
-    @NonNull
-    private final RecyclerView mRecyclerView;
-    @NonNull
-    private final List<WXComponent> mDataSource;
-    @NonNull
-    private ItemTouchHelper mItemTouchHelper;
-
-    private static final String EVENT_START_DRAG = "dragstart";
-    private static final String EVENT_END_DRAG = "dragend";
-
-    private static final String TAG_EXCLUDED = "drag_excluded";
-
-    private static final String TAG = "WXListExComponent";
-
-    private boolean isDraggable = false;
-
-    DefaultDragHelper(@NonNull List<WXComponent> dataSource, @NonNull RecyclerView recyclerView, @NonNull EventTrigger trigger) {
-        this.mDataSource = dataSource;
-        this.mEventTrigger = trigger;
-        this.mRecyclerView = recyclerView;
-
-        //attach
-        this.mItemTouchHelper = new ItemTouchHelper(new DragSupportCallback(this, true));
-        try {
-            mItemTouchHelper.attachToRecyclerView(mRecyclerView);
-        }catch (Throwable e) {
-            //ignore
-        }
-    }
-
-    @Override
-    public void onDragStart(@NonNull WXComponent component, int from) {
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.d(TAG, "list on drag start : from index " + from);
-        }
-        mEventTrigger.triggerEvent(EVENT_START_DRAG, buildEvent(component.getRef(), from, -1));
-    }
-
-    @Override
-    public void onDragEnd(@NonNull WXComponent component, int from, int to) {
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.d(TAG, "list on drag end : " + "from index " + from + " to index " + to);
-        }
-        mEventTrigger.triggerEvent(EVENT_END_DRAG, buildEvent(component.getRef(), from, to));
-    }
-
-    @Override
-    public void onDragging(int fromPos, int toPos) {
-        if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.d(TAG, "list on dragging : from index " + fromPos + " to index " + toPos);
-        }
-
-        RecyclerView.Adapter adapter = mRecyclerView.getAdapter();
-        if (adapter == null) {
-            WXLogUtils.e(TAG, "drag failed because of RecyclerView#Adapter is not bound");
-            return;
-        }
-
-        if (fromPos >= 0 && fromPos <= mDataSource.size() - 1 && toPos >= 0 && toPos <= mDataSource.size() - 1) {
-            Collections.swap(mDataSource, fromPos, toPos);
-            adapter.notifyItemMoved(fromPos, toPos);
-        }
-    }
-
-    @Override
-    public boolean isLongPressDragEnabled() {
-        return mLongPressEnabled;
-    }
-
-    @Override
-    public void setLongPressDragEnabled(boolean enabled) {
-        this.mLongPressEnabled = enabled;
-    }
-
-    @Override
-    public void startDrag(@NonNull RecyclerView.ViewHolder viewHolder) {
-        if (isDraggable) {
-            mItemTouchHelper.startDrag(viewHolder);
-        }
-    }
-
-    @Override
-    public boolean isDraggable() {
-        return this.isDraggable;
-    }
-
-    @Override
-    public void setDraggable(boolean draggable) {
-        this.isDraggable = draggable;
-    }
-
-    @Override
-    public void setDragExcluded(@NonNull RecyclerView.ViewHolder viewHolder, boolean isExcluded) {
-        if (viewHolder.itemView == null) {
-            if (WXEnvironment.isApkDebugable()) {
-                WXLogUtils.e(TAG, "[error] viewHolder.itemView is null");
-            }
-            return;
-        }
-        if (isExcluded) {
-            viewHolder.itemView.setTag(TAG_EXCLUDED);
-        } else {
-            viewHolder.itemView.setTag(null);
-        }
-    }
-
-    @Override
-    public boolean isDragExcluded(@NonNull RecyclerView.ViewHolder viewHolder) {
-        if (viewHolder.itemView == null) {
-            if (WXEnvironment.isApkDebugable()) {
-                WXLogUtils.e(TAG, "[error] viewHolder.itemView is null");
-            }
-            return false;
-        }
-        return viewHolder.itemView.getTag() != null && TAG_EXCLUDED.equals(viewHolder.itemView.getTag());
-    }
-
-    private Map<String, Object> buildEvent(@Nullable String target, int fromIndex, int toIndex) {
-        Map<String, Object> args = new HashMap<>(4);
-        args.put("target", target == null ? "unknown" : target);
-        args.put("fromIndex", fromIndex);
-        args.put("toIndex", toIndex);
-        args.put("timestamp", System.currentTimeMillis());
-        return args;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DragHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DragHelper.java
deleted file mode 100644
index ea66feb..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DragHelper.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.support.annotation.NonNull;
-import android.support.v7.widget.RecyclerView;
-
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Description:
- *
- * interface for drag&drop support
- *
- * <p>
- * Created by rowandjj(chuyi)<br/>
- * Date: 16/4/5<br/>
- * Time: 上午11:34<br/>
- */
-interface DragHelper {
-
-    void onDragStart(@NonNull WXComponent component, int from);
-
-    void onDragEnd(@NonNull WXComponent component, int from, int to);
-
-    void onDragging(int fromPos, int toPos);
-
-    boolean isLongPressDragEnabled();
-
-    void setLongPressDragEnabled(boolean enabled);
-
-    void startDrag(@NonNull RecyclerView.ViewHolder viewHolder);
-
-    boolean isDraggable();
-
-    void setDraggable(boolean draggable);
-
-    void setDragExcluded(@NonNull RecyclerView.ViewHolder viewHolder, boolean isExcluded);
-
-    boolean isDragExcluded(@NonNull RecyclerView.ViewHolder viewHolder);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DragSupportCallback.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DragSupportCallback.java
deleted file mode 100644
index 9b82517..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/DragSupportCallback.java
+++ /dev/null
@@ -1,146 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.support.annotation.NonNull;
-import android.support.v7.widget.GridLayoutManager;
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-import android.support.v7.widget.helper.ItemTouchHelper;
-
-import com.taobao.weex.ui.view.listview.adapter.ListBaseViewHolder;
-import com.taobao.weex.utils.WXLogUtils;
-
-/**
- * Description:
- * An implementation of {@link ItemTouchHelper.Callback}. with drag&drop support:)
- *
- * <p>
- * Created by rowandjj(chuyi)<br/>
- * Date: 17/4/22<br/>
- * Time: 上午11:25<br/>
- */
-class DragSupportCallback extends ItemTouchHelper.Callback {
-    private final DragHelper mDragHelper;
-    private boolean mEnableDifferentViewTypeDrag = false;
-
-    private int dragFrom = -1;
-    private int dragTo = -1;
-
-    private static final String TAG = "WXListExComponent";
-
-    DragSupportCallback(@NonNull DragHelper DragHelper) {
-        this.mDragHelper = DragHelper;
-        this.mEnableDifferentViewTypeDrag = false;
-    }
-
-    DragSupportCallback(@NonNull DragHelper DragHelper, boolean enableDifferentViewTypeDrag) {
-        this.mDragHelper = DragHelper;
-        this.mEnableDifferentViewTypeDrag = enableDifferentViewTypeDrag;
-    }
-
-    @Override
-    public int getMovementFlags(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) {
-        if (recyclerView.getLayoutManager() instanceof GridLayoutManager || recyclerView.getLayoutManager() instanceof StaggeredGridLayoutManager) {
-            int dragFlags = ItemTouchHelper.UP | ItemTouchHelper.DOWN | ItemTouchHelper.LEFT | ItemTouchHelper.RIGHT;
-            int swipeFlags = 0;
-            return makeMovementFlags(dragFlags, swipeFlags);
-        } else {
-            int dragFlags = ItemTouchHelper.UP | ItemTouchHelper.DOWN;
-            int swipeFlags = ItemTouchHelper.START | ItemTouchHelper.END;
-            return makeMovementFlags(dragFlags, swipeFlags);
-        }
-    }
-
-    @Override
-    public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target) {
-        if (viewHolder == null || target == null) {
-            return false;
-        }
-
-        if (!mEnableDifferentViewTypeDrag && viewHolder.getItemViewType() != target.getItemViewType()) {
-            return false;
-        }
-
-        if (mDragHelper.isDragExcluded(viewHolder)) {
-            return false;
-        }
-
-        try {
-            int fromPos = viewHolder.getAdapterPosition();
-            int toPos = target.getAdapterPosition();
-
-            if (dragFrom == -1) {
-                dragFrom = fromPos;
-            }
-            dragTo = toPos;
-
-            mDragHelper.onDragging(fromPos, toPos);
-            return true;
-        } catch (Exception e) {
-            WXLogUtils.e(TAG, e.getMessage());
-            return false;
-        }
-    }
-
-
-    @Override
-    public boolean isLongPressDragEnabled() {
-        return mDragHelper.isDraggable() && mDragHelper.isLongPressDragEnabled();
-    }
-
-    @Override
-    public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction) {
-    }
-
-    @Override
-    public boolean isItemViewSwipeEnabled() {
-        return false;
-    }
-
-    @Override
-    public void onSelectedChanged(RecyclerView.ViewHolder viewHolder, int actionState) {
-        if (actionState != ItemTouchHelper.ACTION_STATE_IDLE && viewHolder instanceof ListBaseViewHolder) {
-            ListBaseViewHolder vh = (ListBaseViewHolder) viewHolder;
-            if (vh.getComponent() != null) {
-                mDragHelper.onDragStart(vh.getComponent(), vh.getAdapterPosition());
-            }
-        }
-
-        super.onSelectedChanged(viewHolder, actionState);
-    }
-
-
-    @Override
-    public void clearView(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) {
-        super.clearView(recyclerView, viewHolder);
-
-        if (viewHolder instanceof ListBaseViewHolder) {
-            ListBaseViewHolder vh = (ListBaseViewHolder) viewHolder;
-            if (vh.getComponent() != null) {
-                if (dragFrom != -1 && dragTo != -1) {
-                    mDragHelper.onDragEnd(vh.getComponent(), dragFrom, dragTo);
-                }
-            }
-
-        }
-
-        dragFrom = dragTo = -1;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/EventTrigger.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/EventTrigger.java
deleted file mode 100644
index 26c9e5c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/EventTrigger.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import java.util.Map;
-
-interface EventTrigger {
-    void triggerEvent(String type, Map<String, Object> args);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/GapItemDecoration.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/GapItemDecoration.java
deleted file mode 100644
index 96d1770..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/GapItemDecoration.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.graphics.Rect;
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-import android.view.View;
-
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.utils.WXViewUtils;
-
-/**
- * Created by furture on 2018/2/12.
- * recyclerview's height is layout width + column gap,
- * so the the offset should include, leftGap and rightGap is via this
- */
-public class GapItemDecoration extends RecyclerView.ItemDecoration {
-
-    private WXListComponent listComponent;
-
-    public GapItemDecoration(WXListComponent listComponent) {
-        this.listComponent = listComponent;
-    }
-
-    @Override
-    public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) {
-        final Float[] spanOffsets = listComponent.getSpanOffsets();
-        if (spanOffsets == null) {
-            return;
-        }
-        int position = parent.getChildAdapterPosition(view);
-        if(position < 0) {
-            return;
-        }
-        if(view.getLayoutParams() instanceof StaggeredGridLayoutManager.LayoutParams){
-            StaggeredGridLayoutManager.LayoutParams params = (StaggeredGridLayoutManager.LayoutParams) view.getLayoutParams();
-            if(params.isFullSpan()){
-                return;
-            }
-            WXComponent component = listComponent.getChild(position);
-            if(component instanceof WXCell){
-                WXCell cell = (WXCell) component;
-                if(cell.isFixed() || cell.isSticky()) {
-                    return;
-                }
-
-                if (params.getSpanIndex() >= spanOffsets.length) {
-                    return;
-                }
-
-                int index = listComponent.isLayoutRTL() ? spanOffsets.length - params.getSpanIndex() - 1 : params.getSpanIndex();
-                float spanOffset = listComponent.getSpanOffsets()[index];
-                int   spanOffsetPx =  Math.round(WXViewUtils.getRealPxByWidth(spanOffset, listComponent.getViewPortWidth()));
-                if (listComponent.isLayoutRTL()) {
-                    outRect.left = -spanOffsetPx;
-                    outRect.right = spanOffsetPx;
-                } else {
-                    outRect.left = spanOffsetPx;
-                    outRect.right = -spanOffsetPx;
-                }
-            }
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/HorizontalListComponent.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/HorizontalListComponent.java
deleted file mode 100644
index aebde71..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/HorizontalListComponent.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXVContainer;
-
-/**
- * Created by sospartan on 6/2/16.
- */
-@Component(lazyload = false)
-
-public class HorizontalListComponent extends WXListComponent {
-  public HorizontalListComponent(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
-    super(instance, parent, lazy, basicComponentData);
-  }
-
-  @Override
-  public int getOrientation() {
-    return Constants.Orientation.HORIZONTAL;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/ListComponentView.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/ListComponentView.java
deleted file mode 100644
index d29aeec..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/ListComponentView.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-import com.taobao.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
-
-/**
- * Created by sospartan on 13/12/2016.
- */
-
-public interface ListComponentView {
-  WXRecyclerView getInnerView();
-  void setRecyclerViewBaseAdapter(RecyclerViewBaseAdapter adapter);
-  void notifyStickyShow(WXCell component);
-  void notifyStickyRemove(WXCell component);
-  void updateStickyView(int currentStickyPos);
-  RecyclerViewBaseAdapter getRecyclerViewBaseAdapter();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/RecyclerTransform.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/RecyclerTransform.java
deleted file mode 100644
index 15beede..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/RecyclerTransform.java
+++ /dev/null
@@ -1,90 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.support.v7.widget.RecyclerView;
-
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.view.listview.adapter.TransformItemDecoration;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-
-/**
- * recycler item decoration transform
- * Created by jianbai.gbj on 2017/9/14.
- */
-public class RecyclerTransform {
-
-    public static final String TRANSFORM = Constants.Name.TRANSFORM;
-    private static final Pattern transformPattern = Pattern.compile("([a-z]+)\\(([0-9\\.]+),?([0-9\\.]+)?\\)");
-    private static final String TAG = "RecyclerTransform";
-
-    /**
-     * These transform functions are supported:
-     * - `scale(x,y)`: scale item, x and y should be a positive float number.
-     * - `translate(x,y)`: translate item, `x` and `y` shoule be integer numbers.
-     * - `opacity(n)`: change the transparency of item, `n` must in `[0,1.0]`.
-     * - `rotate(n)`: rotate item, n is integer number.
-     *
-     * @param raw
-     * @return
-     */
-    public static RecyclerView.ItemDecoration parseTransforms(int orientation, String raw) {
-        if (raw == null) {
-            return null;
-        }
-        float scaleX = 0f, scaleY = 0f;
-        int translateX = 0, translateY = 0;
-        float opacity = 0f;
-        int rotate = 0;
-        //public TransformItemDecoration(boolean isVertical,float alpha,int translateX,int translateY,int rotation,float scale)
-        Matcher matcher = transformPattern.matcher(raw);
-        while (matcher.find()) {
-            String match = matcher.group();
-            String name = matcher.group(1);
-            try {
-                switch (name) {
-                    case "scale":
-                        scaleX = Float.parseFloat(matcher.group(2));
-                        scaleY = Float.parseFloat(matcher.group(3));
-                        break;
-                    case "translate":
-                        translateX = Integer.parseInt(matcher.group(2));
-                        translateY = Integer.parseInt(matcher.group(3));
-                        break;
-                    case "opacity":
-                        opacity = Float.parseFloat(matcher.group(2));
-                        break;
-                    case "rotate":
-                        rotate = Integer.parseInt(matcher.group(2));
-                        break;
-                    default:
-                        WXLogUtils.e(TAG, "Invaild transform expression:" + match);
-                        break;
-                }
-            } catch (NumberFormatException e) {
-                WXLogUtils.e("", e);
-                WXLogUtils.e(TAG, "Invaild transform expression:" + match);
-            }
-        }
-        return new TransformItemDecoration(orientation == Constants.Orientation.VERTICAL, opacity, translateX, translateY, rotate, scaleX, scaleY);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/SimpleListComponent.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/SimpleListComponent.java
deleted file mode 100644
index 288abe0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/SimpleListComponent.java
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.content.Context;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-
-/**
- * A simple list component based on regular recyclerview, do not support refreshing and loading.
- * Created by sospartan on 13/12/2016.
- *
- */
-public class SimpleListComponent extends BasicListComponent<SimpleRecyclerView>{
-
-  public SimpleListComponent(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  @Override
-  protected SimpleRecyclerView generateListView(Context context, int orientation) {
-    SimpleRecyclerView view = new SimpleRecyclerView(context);
-    view.initView(context, WXRecyclerView.TYPE_LINEAR_LAYOUT, orientation);
-    return view;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/SimpleRecyclerView.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/SimpleRecyclerView.java
deleted file mode 100644
index 269e804..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/SimpleRecyclerView.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.content.Context;
-import android.view.View;
-import android.view.ViewGroup;
-
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-import com.taobao.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
-
-import java.util.Stack;
-
-/**
- * Simple list is used for specific occasion, NOT Support sticky,load more,bounce etc.
- * Created by sospartan on 13/12/2016.
- */
-
-class SimpleRecyclerView extends WXRecyclerView implements ListComponentView{
-  private RecyclerViewBaseAdapter mAdapter = null;
-
-  public SimpleRecyclerView(Context context) {
-    super(context);
-  }
-
-  @Override
-  public WXRecyclerView getInnerView() {
-    return this;
-  }
-
-  @Override
-  public void setRecyclerViewBaseAdapter(RecyclerViewBaseAdapter adapter) {
-    setAdapter(adapter);
-    this.mAdapter = adapter;
-  }
-
-  /**
-   * @param component
-   */
-  public void notifyStickyShow(WXCell component) {
-    //Simple list is used for specific occasion, NOT Support sticky,load more,bounce etc.
-  }
-
-  /**
-   * @param component
-   */
-  public void notifyStickyRemove(WXCell component) {
-    //Simple list is used for specific occasion, NOT Support sticky,load more,bounce etc.
-  }
-
-  @Override
-  public void updateStickyView(int currentStickyPos) {
-    //Simple list is used for specific occasion, NOT Support sticky,load more,bounce etc.
-  }
-
-  @Override
-  public RecyclerViewBaseAdapter getRecyclerViewBaseAdapter() {
-    return mAdapter;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/StickyHeaderHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/StickyHeaderHelper.java
deleted file mode 100644
index 5a12e2e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/StickyHeaderHelper.java
+++ /dev/null
@@ -1,207 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.view.View;
-import android.view.ViewGroup;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-/**
- * Created by sospartan on 17/03/2017.
- */
-
-public class StickyHeaderHelper {
-  private final ViewGroup mParent;
-  private Map<String,View> mHeaderViews = new HashMap<>(); // map for <ref,view>
-  private Map<String,WXCell> mHeaderComps = new HashMap<>(); // map for <ref,comp>
-  private String mCurrentStickyRef = null;
-
-  public StickyHeaderHelper(ViewGroup parent){
-    this.mParent = parent;
-  }
-
-  /**
-   * @param component
-   */
-  public void notifyStickyShow(WXCell component) {
-    if (component == null)
-      return;
-    mHeaderComps.put(component.getRef(),component);
-    if(mCurrentStickyRef != null){
-      WXCell cell = mHeaderComps.get(mCurrentStickyRef);
-      if(cell ==null || component.getScrollPositon() > cell.getScrollPositon()){
-        mCurrentStickyRef = component.getRef();
-      }
-    }else{
-      mCurrentStickyRef = component.getRef();
-    }
-
-    {
-      if(mCurrentStickyRef==null){
-        WXLogUtils.e("Current Sticky ref is null.");
-        return;
-      }
-
-      WXCell headComponent = mHeaderComps.get(mCurrentStickyRef);
-      final View headerView = headComponent.getRealView();
-      if (headerView == null) {
-        WXLogUtils.e("Sticky header's real view is null.");
-        return;
-      }
-      View header = mHeaderViews.get(headComponent.getRef());
-      if( header != null){
-        //already there
-        header.bringToFront();
-      }else {
-        mHeaderViews.put(headComponent.getRef(), headerView);
-        //record translation, it should not change after transformation
-        final float translationX = headerView.getTranslationX();
-        final float translationY = headerView.getTranslationY();
-        headComponent.removeSticky();
-
-        ViewGroup existedParent;
-        if ((existedParent = (ViewGroup) headerView.getParent()) != null) {
-          existedParent.removeView(headerView);
-        }
-        headerView.setTag(headComponent.getRef());
-        ViewGroup.MarginLayoutParams mlp =
-                new ViewGroup.MarginLayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
-                        ViewGroup.LayoutParams.WRAP_CONTENT);
-        mParent.addView(headerView, mlp);
-        headerView.setTag(this);
-        if(headComponent.getStickyOffset() > 0) {
-          ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) headerView.getLayoutParams();
-          if(headComponent.getStickyOffset() != params.topMargin) {
-            params.topMargin = headComponent.getStickyOffset();
-          }
-        }
-        //recover translation, sometimes it will be changed on fling
-        headerView.setTranslationX(translationX);
-        headerView.setTranslationY(translationY);
-      }
-      changeFrontStickyVisible();
-      if (headComponent.getEvents().contains("sticky")) {
-        headComponent.fireEvent("sticky");
-      }
-    }
-  }
-
-
-  public void notifyStickyRemove(WXCell compToRemove) {
-    if (compToRemove == null)
-      return;
-    final WXCell component = mHeaderComps.containsValue(compToRemove) ? mHeaderComps.remove(compToRemove.getRef()) : compToRemove;
-    final View headerView = mHeaderViews.remove(compToRemove.getRef());
-
-    if(component == null || headerView == null){
-      if(WXEnvironment.isApkDebugable()) {
-      }
-      return;
-    }
-    if(mCurrentStickyRef != null && mCurrentStickyRef.equals(compToRemove.getRef())){
-      mCurrentStickyRef = null;
-    }
-    mParent.post(WXThread.secure(new Runnable() {
-      @Override
-      public void run() {
-        mParent.removeView(headerView);
-        if(headerView.getVisibility() != View.VISIBLE){
-          headerView.setVisibility(View.VISIBLE);
-        }
-        component.recoverySticky();
-        changeFrontStickyVisible();
-
-      }
-    }));
-    if (component.getEvents().contains("unsticky")) {
-      component.fireEvent("unsticky");
-    }
-  }
-
-
-  public void updateStickyView(int currentStickyPos) {
-    Iterator<Map.Entry<String, WXCell>> iterator = mHeaderComps.entrySet().iterator();
-    List<WXCell> toRemove = new ArrayList<>();
-    while(iterator.hasNext()){
-      Map.Entry<String, WXCell> next = iterator.next();
-      WXCell cell = next.getValue();
-      int pos = cell.getScrollPositon();
-      if(pos > currentStickyPos){
-        toRemove.add(cell);
-      }else if(pos == currentStickyPos){
-        mCurrentStickyRef = cell.getRef();
-        View view = mHeaderViews.get(cell.getRef());
-        if(view != null){
-          view.bringToFront();
-          changeFrontStickyVisible();
-        }
-      }
-    }
-    for(WXCell cell:toRemove){
-      notifyStickyRemove(cell);
-    }
-  }
-
-  public void  clearStickyHeaders(){
-    if(mHeaderViews.size() <= 0){
-      return;
-    }
-    Iterator<Map.Entry<String, WXCell>> iterator = mHeaderComps.entrySet().iterator();
-
-    while (iterator.hasNext()) {
-      Map.Entry<String, WXCell> next = iterator.next();
-      WXCell value = next.getValue();
-      iterator.remove();
-      notifyStickyRemove(value);
-    }
-  }
-
-
-  private void changeFrontStickyVisible(){
-    if(mHeaderViews.size() <= 0){
-      return;
-    }
-    boolean  fontVisible = false;
-    for(int i=mParent.getChildCount()-1; i>=0; i--){
-      View view = mParent.getChildAt(i);
-      if(fontVisible && view.getTag() instanceof  StickyHeaderHelper){
-        if(view.getVisibility() != View.GONE){
-          view.setVisibility(View.GONE);
-        }
-      }else{
-        if(view.getTag() instanceof  StickyHeaderHelper){
-          fontVisible = true;
-          if(view != null && view.getVisibility() != View.VISIBLE){
-            view.setVisibility(View.VISIBLE);
-          }
-        }
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXCell.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXCell.java
deleted file mode 100644
index 1687545..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXCell.java
+++ /dev/null
@@ -1,280 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.content.Context;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.RestrictTo;
-import android.text.TextUtils;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.FrameLayout;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXHeader;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.flat.WidgetContainer;
-import com.taobao.weex.ui.view.WXFrameLayout;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import org.w3c.dom.Text;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.LinkedList;
-
-import static com.taobao.weex.common.Constants.Name.STICKY_OFFSET;
-
-/**
- * Root component for components in {@link WXListComponent}
- */
-@Component(lazyload = false)
-
-public class WXCell extends WidgetContainer<WXFrameLayout> {
-
-    private int mLastLocationY = 0;
-    private ViewGroup mRealView;
-    private View mTempStickyView;
-    private View mHeadView;
-
-    /** used in list sticky detect **/
-    private int mScrollPosition = -1;
-    private boolean mFlatUIEnabled = false;
-
-
-    private Object  renderData;
-
-    private boolean isSourceUsed = false;
-
-    private boolean isAppendTreeDone;
-
-    private CellAppendTreeListener cellAppendTreeListener;
-
-    public static class Creator implements ComponentCreator {
-        public WXComponent createInstance(WXSDKInstance instance,
-                                          WXVContainer parent,
-                                          BasicComponentData basicComponentData)
-                throws IllegalAccessException, InvocationTargetException, InstantiationException {
-            return new WXCell(instance, parent, true, basicComponentData);
-        }
-    }
-
-    @Deprecated
-    public WXCell(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-        super(instance, parent, basicComponentData);
-    }
-
-    public WXCell(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
-        super(instance, parent, basicComponentData);
-        lazy(true);
-        if(Build.VERSION.SDK_INT< Build.VERSION_CODES.LOLLIPOP) {
-            try {
-                //TODO a WTF is necessary if anyone try to change the flat flag during update attrs.
-                WXAttr attr = getAttrs();
-                if (attr.containsKey(Constants.Name.FLAT)) {
-                    mFlatUIEnabled = WXUtils.getBoolean(attr.get(Constants.Name.FLAT), false);
-                }
-            } catch (NullPointerException e) {
-                WXLogUtils.e("Cell", WXLogUtils.getStackTrace(e));
-            }
-        }
-        if (!canRecycled()){
-            instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_CELL_DATA_UN_RECYCLE_NUM,1);
-        }
-        if (TextUtils.isEmpty(getAttrs().getScope())){
-            instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_CELL_UN_RE_USE_NUM,1);
-        }
-    }
-
-    @Override
-    public boolean isLazy() {
-        return super.isLazy() && !isFixed();
-    }
-
-    @Override
-    @RestrictTo(RestrictTo.Scope.LIBRARY)
-    public boolean isFlatUIEnabled() {
-        return mFlatUIEnabled;
-    }
-
-    /**
-     * If Cell is Sticky, need wraped FrameLayout
-     */
-    @Override
-    protected WXFrameLayout initComponentHostView(@NonNull Context context) {
-        if (isSticky() || this instanceof WXHeader) {
-            WXFrameLayout view = new WXFrameLayout(context);
-            mRealView = new WXFrameLayout(context);
-            view.addView(mRealView);
-            //TODO Maybe there is a better solution for hardware-acceleration view's display list.
-            if (isFlatUIEnabled()) {
-                view.setLayerType(View.LAYER_TYPE_HARDWARE, null);
-            }
-            return view;
-        } else {
-            WXFrameLayout view = new WXFrameLayout(context);
-            mRealView = view;
-            if (isFlatUIEnabled()) {
-                view.setLayerType(View.LAYER_TYPE_HARDWARE, null);
-            }
-            return view;
-        }
-    }
-
-    public int getLocationFromStart(){
-        return mLastLocationY;
-    }
-
-    public void setLocationFromStart(int l){
-        mLastLocationY = l;
-    }
-
-    void setScrollPositon(int pos){
-        mScrollPosition = pos;
-    }
-
-    public int getScrollPositon() {
-        return mScrollPosition;
-    }
-
-    @Override
-    public ViewGroup getRealView() {
-        return mRealView;
-    }
-
-    public void removeSticky() {
-        if(getHostView().getChildCount() > 0) {
-            mHeadView = getHostView().getChildAt(0);
-            int[] location = new int[2];
-            int[] parentLocation = new int[2];
-            getHostView().getLocationOnScreen(location);
-            getParentScroller().getView().getLocationOnScreen(parentLocation);
-            int headerViewOffsetX = location[0] - parentLocation[0];
-            int headerViewOffsetY = getParent().getHostView().getTop();
-            getHostView().removeView(mHeadView);
-            mRealView = (ViewGroup) mHeadView;
-            mTempStickyView = new FrameLayout(getContext());
-            FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams((int) getLayoutWidth(),
-                    (int) getLayoutHeight());
-            getHostView().addView(mTempStickyView, lp);
-            mHeadView.setTranslationX(headerViewOffsetX);
-            mHeadView.setTranslationY(headerViewOffsetY);
-        }
-    }
-
-    public void recoverySticky() {
-        if(mHeadView != null){
-            if(mHeadView.getLayoutParams() != null){
-                ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) mHeadView.getLayoutParams();
-                if(params.topMargin > 0){
-                    params.topMargin = 0;
-                }
-            }
-            if(mHeadView.getVisibility() != View.VISIBLE){
-                mHeadView.setVisibility(View.VISIBLE);
-            }
-            if(mHeadView.getParent() != null){
-                ((ViewGroup)mHeadView.getParent()).removeView(mHeadView);
-            }
-            getHostView().removeView(mTempStickyView);
-            getHostView().addView(mHeadView);
-            mHeadView.setTranslationX(0);
-            mHeadView.setTranslationY(0);
-        }
-    }
-
-    @Override
-    protected void mountFlatGUI() {
-        if(getHostView()!=null) {
-            if(widgets == null){
-                widgets = new LinkedList<>();
-            }
-            getHostView().mountFlatGUI(widgets);
-        }
-    }
-
-    @Override
-    public void unmountFlatGUI() {
-        if (getHostView() != null) {
-            getHostView().unmountFlatGUI();
-        }
-    }
-
-    @Override
-    public boolean intendToBeFlatContainer() {
-        return getInstance().getFlatUIContext().isFlatUIEnabled(this) && WXCell.class.equals(getClass()) && !isSticky();
-    }
-
-    public int getStickyOffset(){
-        if(getAttrs().get(STICKY_OFFSET) == null){
-            return 0;
-        }
-        float  offset = WXUtils.getFloat(getAttrs().get(STICKY_OFFSET));
-        return (int)(WXViewUtils.getRealPxByWidth(offset, getViewPortWidth()));
-    }
-
-    public Object getRenderData() {
-        return renderData;
-    }
-
-    public void setRenderData(Object renderData) {
-        this.renderData = renderData;
-    }
-
-    public boolean isSourceUsed() {
-        return isSourceUsed;
-    }
-
-    public void setSourceUsed(boolean sourceUsed) {
-        isSourceUsed = sourceUsed;
-    }
-
-
-    public boolean isAppendTreeDone(){
-        return isAppendTreeDone;
-    }
-
-    @Override
-    public void appendTreeCreateFinish() {
-        super.appendTreeCreateFinish();
-        isAppendTreeDone = true;
-        if(cellAppendTreeListener != null){
-            cellAppendTreeListener.onAppendTreeDone();
-        }
-    }
-
-    public void setCellAppendTreeListener(CellAppendTreeListener cellAppendTreeListener) {
-        this.cellAppendTreeListener = cellAppendTreeListener;
-        if(isAppendTreeDone){
-            cellAppendTreeListener.onAppendTreeDone();
-        }
-    }
-
-    public interface CellAppendTreeListener{
-        public void onAppendTreeDone();
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXListComponent.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXListComponent.java
deleted file mode 100644
index 95364e1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXListComponent.java
+++ /dev/null
@@ -1,341 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import static com.taobao.weex.ui.view.listview.WXRecyclerView.TYPE_LINEAR_LAYOUT;
-
-import android.content.Context;
-import android.support.v4.util.ArrayMap;
-import android.support.v7.widget.PagerSnapHelper;
-import android.text.TextUtils;
-import com.alibaba.fastjson.JSON;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXBaseRefresh;
-import com.taobao.weex.ui.component.WXBasicComponentType;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXComponentProp;
-import com.taobao.weex.ui.component.WXLoading;
-import com.taobao.weex.ui.component.WXRefresh;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-import com.taobao.weex.ui.view.listview.adapter.ListBaseViewHolder;
-import com.taobao.weex.ui.view.refresh.wrapper.BounceRecyclerView;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import java.lang.reflect.InvocationTargetException;
-import java.util.Arrays;
-import java.util.List;
-import java.util.Locale;
-import java.util.Map;
-
-/**
- * Unlike other components, there is immutable bi-directional association between View and
- * ViewHolder, while only mutable and temporal uni-directional association between view and
- * components. The association only exist from {@link #onBindViewHolder(ListBaseViewHolder, int)} to
- * {@link #onViewRecycled(ListBaseViewHolder)}. In other situations, the association may not valid
- * or not even exist.
- */
-@Component(lazyload = false)
-
-public class WXListComponent extends BasicListComponent<BounceRecyclerView> {
-  private String TAG = "WXListComponent";
-  //  private WXRecyclerDomObject mDomObject;
-  private float mPaddingLeft;
-  private float mPaddingRight;
-  private String mSpanOffsetsStr;
-  private Float[] mSpanOffsets;
-  private boolean hasSetGapItemDecoration = false;
-
-  public static class Creator implements ComponentCreator {
-    public WXComponent createInstance(WXSDKInstance instance,
-                                      WXVContainer parent,
-                                      BasicComponentData basicComponentData)
-            throws IllegalAccessException, InvocationTargetException, InstantiationException {
-      return new WXListComponent(instance, parent, true, basicComponentData);
-    }
-  }
-
-  @Deprecated
-  public WXListComponent(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
-    this(instance, parent, isLazy, basicComponentData);
-  }
-
-
-  public WXListComponent(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  @Override
-  protected BounceRecyclerView generateListView(Context context, int orientation) {
-    BounceRecyclerView bounceRecyclerView = new BounceRecyclerView(context, mLayoutType, mColumnCount, mColumnGap, orientation);
-    if (bounceRecyclerView.getSwipeLayout() != null) {
-      if (WXUtils.getBoolean(getAttrs().get(Constants.Name.NEST_SCROLLING_ENABLED), false)) {
-        bounceRecyclerView.getSwipeLayout().setNestedScrollingEnabled(true);
-      }
-    }
-
-    /**
-     *  enable pagingEnabled attr
-     */
-    if(WXUtils.getBoolean(getAttrs().get(Constants.Name.PAGE_ENABLED),false)){
-      PagerSnapHelper snapHelper = null;
-      String pageSize = WXUtils.getString(getAttrs().get(Constants.Name.PAGE_SIZE), null);
-      if(TextUtils.isEmpty(pageSize)) {
-        snapHelper = new PagerSnapHelper();
-      } else  {
-        snapHelper = new WXPagerSnapHelper();
-      }
-
-      snapHelper.attachToRecyclerView(bounceRecyclerView.getInnerView());
-    }
-
-    return bounceRecyclerView;
-  }
-
-  @Override
-  public void addChild(WXComponent child, int index) {
-    super.addChild(child, index);
-    if (child == null || index < -1) {
-      return;
-    }
-    setRefreshOrLoading(child);
-    // Synchronize DomObject's attr to Component and Native View
-    if(getHostView() != null && hasColumnPros()) {
-      updateRecyclerAttr();
-      getHostView().getInnerView().initView(getContext(), mLayoutType,mColumnCount,mColumnGap,getOrientation());
-    }
-  }
-
-  private boolean hasColumnPros() {
-    return (getAttrs().containsKey(Constants.Name.COLUMN_WIDTH) && mColumnWidth != WXUtils.parseFloat(getAttrs().get(Constants.Name.COLUMN_WIDTH))) ||
-            (getAttrs().containsKey(Constants.Name.COLUMN_COUNT) &&  mColumnCount != WXUtils.parseInt(getAttrs().get(Constants.Name.COLUMN_COUNT))) ||
-            (getAttrs().containsKey(Constants.Name.COLUMN_GAP) && mColumnGap != WXUtils.parseFloat(getAttrs().get(Constants.Name.COLUMN_GAP)));
-  }
-
-  /**
-   * Setting refresh view and loading view
-   *
-   * @param child the refresh_view or loading_view
-   */
-  private boolean setRefreshOrLoading(final WXComponent child) {
-
-    if (getHostView() == null) {
-      WXLogUtils.e(TAG, "setRefreshOrLoading: HostView == null !!!!!! check list attr has append =tree");
-      return true;
-    }
-    if (child instanceof WXRefresh) {
-      getHostView().setOnRefreshListener((WXRefresh) child);
-      getHostView().postDelayed(WXThread.secure(new Runnable() {
-        @Override
-        public void run() {
-          getHostView().setHeaderView(child);
-        }
-      }), 100);
-      return true;
-    }
-
-    if (child instanceof WXLoading) {
-      getHostView().setOnLoadingListener((WXLoading) child);
-      getHostView().postDelayed(WXThread.secure(new Runnable() {
-        @Override
-        public void run() {
-          getHostView().setFooterView(child);
-        }
-      }), 100);
-      return true;
-    }
-    return false;
-  }
-
-  private void updateRecyclerAttr() {
-    mColumnCount = WXUtils.parseInt(getAttrs().get(Constants.Name.COLUMN_COUNT));
-    if (mColumnCount <= 0 && mLayoutType != TYPE_LINEAR_LAYOUT) {
-      Map<String, String> ext = new ArrayMap<>();
-      ext.put("componentType", getComponentType());
-      ext.put("attribute", getAttrs().toString());
-      ext.put("stackTrace", Arrays.toString(Thread.currentThread().getStackTrace()));
-      WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),
-          WXErrorCode.WX_RENDER_ERR_LIST_INVALID_COLUMN_COUNT, "columnCount",
-          String.format(Locale.ENGLISH,
-              "You are trying to set the list/recycler/vlist/waterfall's column to %d, which is illegal. The column count should be a positive integer",
-              mColumnCount),
-          ext);
-      mColumnCount = Constants.Value.COLUMN_COUNT_NORMAL;
-    }
-    mColumnGap = WXUtils.parseFloat(getAttrs().get(Constants.Name.COLUMN_GAP));
-    mColumnWidth = WXUtils.parseFloat(getAttrs().get(Constants.Name.COLUMN_WIDTH));
-    mPaddingLeft = WXUtils.parseFloat(getAttrs().get(Constants.Name.PADDING_LEFT));
-    mPaddingRight = WXUtils.parseFloat(getAttrs().get(Constants.Name.PADDING_RIGHT));
-    mSpanOffsetsStr = (String)getAttrs().get(Constants.Name.SPAN_OFFSETS);
-
-    try {
-      if (!TextUtils.isEmpty(mSpanOffsetsStr)) {
-        List<Float> list = JSON.parseArray(mSpanOffsetsStr, Float.class);
-        final int size = list.size();
-        if (null == mSpanOffsets || mSpanOffsets.length != size) {
-          mSpanOffsets = new Float[size];
-        }
-        list.toArray(mSpanOffsets);
-      } else {
-        mSpanOffsets = null;
-      }
-    } catch (Throwable e) {
-      WXLogUtils.w("Parser SpanOffsets error ", e);
-    }
-
-    if (!hasSetGapItemDecoration && null != getSpanOffsets() && null != getHostView()
-        && null != getHostView().getInnerView()) {
-      hasSetGapItemDecoration = true;
-      getHostView().getInnerView().addItemDecoration(new GapItemDecoration(this));
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.SPAN_OFFSETS)
-  public void setSpanOffsets(String spanOffsets)  {
-    if (!TextUtils.equals(spanOffsets, mSpanOffsetsStr)) {
-      markComponentUsable();
-      updateRecyclerAttr();
-      WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-      wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.COLUMN_WIDTH)
-  public void setColumnWidth(float columnWidth)  {
-    if(columnWidth != mColumnWidth){
-      markComponentUsable();
-      updateRecyclerAttr();
-      WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-      wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap,getOrientation());
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.COLUMN_COUNT)
-  public void setColumnCount(int columnCount){
-    if(columnCount != mColumnCount) {
-      markComponentUsable();
-      updateRecyclerAttr();
-      WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-      wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap,getOrientation());
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.COLUMN_GAP)
-  public void setColumnGap(float columnGap) throws InterruptedException {
-    if(columnGap != mColumnGap) {
-      markComponentUsable();
-      updateRecyclerAttr();
-      WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-      wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
-    }
-  }
-
-  @WXComponentProp(name = Constants.Name.SCROLLABLE)
-  public void setScrollable(boolean scrollable) {
-    WXRecyclerView inner = getHostView().getInnerView();
-    inner.setScrollable(scrollable);
-  }
-
-  @Override
-  public void updateProperties(Map<String, Object> props) {
-    super.updateProperties(props);
-    if (isRecycler(this)) {
-      if(WXBasicComponentType.WATERFALL.equals(getComponentType())){
-        mLayoutType = WXRecyclerView.TYPE_STAGGERED_GRID_LAYOUT;
-      }else{
-        mLayoutType = getAttrs().getLayoutType();
-      }
-    }
-
-    if(props.containsKey(Constants.Name.PADDING)
-            ||props.containsKey(Constants.Name.PADDING_LEFT)
-            || props.containsKey(Constants.Name.PADDING_RIGHT)){
-      if(mPaddingLeft != WXUtils.parseFloat(props.get(Constants.Name.PADDING_LEFT)) || mPaddingRight != WXUtils.parseFloat(props.get(Constants.Name.PADDING_RIGHT))) {
-        markComponentUsable();
-        updateRecyclerAttr();
-        WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-        wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
-      }
-    }
-  }
-
-  @Override
-  public void createChildViewAt(int index) {
-    int indexToCreate = index;
-    if (indexToCreate < 0) {
-      indexToCreate = childCount() - 1;
-      if (indexToCreate < 0) {
-        return;
-      }
-    }
-    final WXComponent child = getChild(indexToCreate);
-    if (child instanceof WXBaseRefresh) {
-      child.createView();
-      if (child instanceof WXRefresh) {
-        getHostView().setOnRefreshListener((WXRefresh) child);
-        getHostView().postDelayed(new Runnable() {
-          @Override
-          public void run() {
-            getHostView().setHeaderView(child);
-          }
-        }, 100);
-      } else if (child instanceof WXLoading) {
-        getHostView().setOnLoadingListener((WXLoading) child);
-        getHostView().postDelayed(new Runnable() {
-          @Override
-          public void run() {
-            getHostView().setFooterView(child);
-          }
-        }, 100);
-      }
-    } else {
-      super.createChildViewAt(indexToCreate);
-    }
-  }
-
-  public void remove(WXComponent child, boolean destroy) {
-    super.remove(child, destroy);
-    removeFooterOrHeader(child);
-  }
-
-  private void removeFooterOrHeader(WXComponent child) {
-    if (child instanceof WXLoading) {
-      getHostView().removeFooterView(child);
-    } else if (child instanceof WXRefresh) {
-      getHostView().removeHeaderView(child);
-    }
-  }
-
-  private boolean isRecycler(WXComponent component) {
-    return WXBasicComponentType.WATERFALL.equals(component.getComponentType())
-            || WXBasicComponentType.RECYCLE_LIST.equals(component.getComponentType())
-            || WXBasicComponentType.RECYCLER.equals(component.getComponentType());
-  }
-
-  public Float[] getSpanOffsets() {
-    return mSpanOffsets;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXPagerSnapHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXPagerSnapHelper.java
deleted file mode 100644
index 633ac0c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/WXPagerSnapHelper.java
+++ /dev/null
@@ -1,75 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v7.widget.OrientationHelper;
-import android.support.v7.widget.PagerSnapHelper;
-import android.support.v7.widget.RecyclerView;
-import android.view.View;
-
-public class WXPagerSnapHelper extends PagerSnapHelper {
-    @Nullable
-    private OrientationHelper mVerticalHelper;
-    @Nullable
-    private OrientationHelper mHorizontalHelper;
-
-    @Nullable
-    @Override
-    public int[] calculateDistanceToFinalSnap(@NonNull RecyclerView.LayoutManager layoutManager, @NonNull View targetView) {
-
-        int[] out = new int[2];
-        if (layoutManager.canScrollHorizontally()) {
-            out[0] = this.distanceToStart(layoutManager, targetView, this.getHorizontalHelper(layoutManager));
-        } else {
-            out[0] = 0;
-        }
-
-        if (layoutManager.canScrollVertically()) {
-            out[1] = this.distanceToStart(layoutManager, targetView, this.getVerticalHelper(layoutManager));
-        } else {
-            out[1] = 0;
-        }
-
-        return out;
-    }
-
-    @NonNull
-    private OrientationHelper getVerticalHelper(@NonNull RecyclerView.LayoutManager layoutManager) {
-        if (this.mVerticalHelper == null) {
-            this.mVerticalHelper = OrientationHelper.createVerticalHelper(layoutManager);
-        }
-
-        return this.mVerticalHelper;
-    }
-
-    @NonNull
-    private OrientationHelper getHorizontalHelper(@NonNull RecyclerView.LayoutManager layoutManager) {
-        if (this.mHorizontalHelper == null) {
-            this.mHorizontalHelper = OrientationHelper.createHorizontalHelper(layoutManager);
-        }
-
-        return this.mHorizontalHelper;
-    }
-
-    private int distanceToStart(@NonNull RecyclerView.LayoutManager layoutManager, @NonNull View targetView, OrientationHelper helper) {
-        return helper.getDecoratedStart(targetView) - helper.getStartAfterPadding();
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/AsyncCellLoadTask.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/AsyncCellLoadTask.java
deleted file mode 100644
index d186c81..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/AsyncCellLoadTask.java
+++ /dev/null
@@ -1,129 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import android.os.AsyncTask;
-import android.os.Looper;
-import android.os.MessageQueue;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.Iterator;
-import java.util.concurrent.ConcurrentLinkedQueue;
-
-/**
- * Created by furture on 2018/1/25.
- * async template cell component copy in background and init component when idle
- */
-class AsyncCellLoadTask extends AsyncTask<Void,Void, Void> {
-
-    private String template;
-    private WXCell source;
-    private WXRecyclerTemplateList templateList;
-
-    public AsyncCellLoadTask(String template, WXCell source, WXRecyclerTemplateList templateList) {
-        this.template = template;
-        this.source = source;
-        this.templateList = templateList;
-    }
-
-    /**
-     * async template cell component copy in background
-     * */
-    @Override
-    protected Void doInBackground(Void... params) {
-        TemplateCache cellCache = templateList.getTemplatesCache().get(template);
-        if(cellCache == null || cellCache.cells == null){
-            return null;
-        }
-        while (cellCache.cells.size() < templateList.getTemplateCacheSize()){
-            long start = System.currentTimeMillis();
-            WXCell component = (WXCell) templateList.copyComponentFromSourceCell(source);
-            if(WXEnvironment.isOpenDebugLog() && WXRecyclerTemplateList.ENABLE_TRACE_LOG){
-                WXLogUtils.d(WXRecyclerTemplateList.TAG, " AsyncCellLoadTask load " + template
-                        + "  " +  component.hashCode()
-                + " used " + (System.currentTimeMillis() - start));
-            }
-            if(component == null){
-                return null;
-            }
-            if(isDestory()){
-                return null;
-            }
-            cellCache.cells.add(component);
-        }
-        return null;
-    }
-
-    /**
-     * init component view when main thread idle
-     * */
-    @Override
-    protected void onPostExecute(Void aVoid) {
-        if(isDestory()){
-            return;
-        }
-        final TemplateCache cellCache = templateList.getTemplatesCache().get(template);
-        if(cellCache == null){
-            return;
-        }
-        if(cellCache.cells == null
-                || cellCache.cells.size() == 0){
-            cellCache.isLoadIng = false;
-            return;
-        }
-        Looper.myQueue().addIdleHandler(new MessageQueue.IdleHandler() {
-            @Override
-            public boolean queueIdle() {
-                if(isDestory()){
-                    return false;
-                }
-                ConcurrentLinkedQueue<WXCell> queue =  cellCache.cells;
-                Iterator<WXCell> iterator =  queue.iterator();
-                while (iterator.hasNext()){
-                    WXCell component =  iterator.next();
-                    if(component.isLazy()){
-                        templateList.doCreateCellViewBindData(component, template, true);
-                        return iterator.hasNext();
-                    }
-                }
-                return false;
-            }
-        });
-        cellCache.isLoadIng = false;
-    }
-
-    private boolean isDestory(){
-        if(source.getInstance() == null
-                || source.getInstance().isDestroy()){
-            return true;
-        }
-        return templateList.isDestoryed();
-    }
-
-    /**
-     * start cell load task on THREAD_POOL_EXECUTOR
-     * */
-    public void startTask(){
-        executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellDataManager.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellDataManager.java
deleted file mode 100644
index 5b75346..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellDataManager.java
+++ /dev/null
@@ -1,271 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-
-import com.alibaba.fastjson.JSONArray;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by furture on 2018/1/23.
- * template data manager, manage data and render state
- */
-public class CellDataManager {
-
-    private static final String VIRTUAL_COMPONENT_SEPRATOR = "@";
-
-    public static final String SUB_COMPONENT_TEMPLATE_ID = "@templateId";
-
-    public static final String VIRTUAL_COMPONENT_ID = "@virtualComponentId";
-
-    /**
-     * template list data, update should vis data manager interface, this field is read only
-     * */
-    JSONArray listData;
-
-    /**
-     * current template list
-     * */
-    public final WXRecyclerTemplateList templateList;
-
-    /**
-     * data render state for position, itemId、dirty、and other info
-     * */
-    private Map<Integer, CellRenderState> renderStates = new ArrayMap<>();
-
-
-    /**
-     * list virtual component data, rendet state
-     * key virtual component id, value is cell render state.
-     * */
-    private Map<String, CellRenderState> virtualComponentRenderStates;
-
-
-
-    /**
-     * template list data manager
-     * */
-    public CellDataManager(WXRecyclerTemplateList templateList) {
-        this.templateList = templateList;
-    }
-
-    /**
-     * get current render state for current position, never return null.
-     * */
-    public CellRenderState getRenderState(int position){
-        CellRenderState renderState = renderStates.get(position);
-        if(renderState == null){
-            renderState = new CellRenderState();
-            renderState.position = position;
-            renderStates.put(position, renderState);
-        }
-        if(position != renderState.position) {
-            renderState.position = position;
-            renderState.hasPositionChange = true;
-        }
-        return renderState;
-    }
-
-    /**
-     * @param  virutalComponentId virutalComponentId
-     * @param  data   update    virutalComponent's data
-     * update virtual component data
-     * */
-    public void updateVirtualComponentData(String virutalComponentId, Object data){
-        if(virtualComponentRenderStates != null){
-            CellRenderState cellRenderState = virtualComponentRenderStates.get(virutalComponentId);
-            if(cellRenderState != null){
-                cellRenderState.getVirtualComponentDatas().put(virutalComponentId, data);
-                cellRenderState.hasVirtualCompoentUpdate = true;
-            }else{
-                if(WXEnvironment.isApkDebugable()) {
-                    throw new IllegalArgumentException("virtualComponentDatas illegal state empty render state" + virutalComponentId);
-                }
-            }
-        }else{
-            if(WXEnvironment.isApkDebugable()){
-                throw  new IllegalArgumentException("virtualComponentDatas illegal state " + virutalComponentId);
-            }
-        }
-    }
-
-    /**
-     * @param  position  current position virtual component
-     * @param  virutalComponentId virutalComponentId
-     * @param  data   update    virutalComponent's data
-     * create virtual component data
-     * */
-    public void createVirtualComponentData(int position, String virutalComponentId, Object data){
-        if(virtualComponentRenderStates == null){
-            virtualComponentRenderStates = new HashMap<>(8);
-        }
-        CellRenderState renderState = renderStates.get(position);
-        renderState.getVirtualComponentDatas().put(virutalComponentId, data);
-        virtualComponentRenderStates.put(virutalComponentId, renderState);
-
-    }
-
-
-
-
-    /**
-     * @param  listData setList data
-     * clear render state for current cell, and virtual component data
-     * */
-    public void setListData(JSONArray listData) {
-        if(this.listData != listData) {
-            if(this.listData != null){
-                if(WXUtils.getBoolean(templateList.getAttrs().get("exitDetach"), true)){
-                    for(int i=0; i<this.listData.size(); i++){
-                        cleanRenderState(renderStates.remove(i));
-                    }
-                }
-            }
-            this.listData = listData;
-            renderStates.clear();
-            if (virtualComponentRenderStates != null) {
-                virtualComponentRenderStates.clear();
-            }
-        }
-    }
-
-    /**
-     * @param index insert index
-     * @param  data  data object
-     * insert data at current index
-     * */
-    public boolean insertData(int index, Object data){
-        listData.add(index, data);
-        boolean renderStateChange = false;
-        for(int i=listData.size(); i>= index; i--){
-            CellRenderState state = renderStates.remove(i);
-            if(state != null){
-                renderStates.put(i + 1, state);
-                renderStateChange = true;
-            }
-        }
-        return renderStateChange;
-    }
-
-    /**
-     *
-     * @param index insert index
-     * @param  data  data object
-     * insert data at current index
-     * */
-    public boolean insertRange(int index, JSONArray data){
-        listData.addAll(index, data);
-        boolean renderStateChange = false;
-        for(int i = listData.size()-1; i >= index; i--){
-            CellRenderState state = renderStates.remove(i);
-            if(state != null){
-                renderStates.put(i + 1, state);
-                renderStateChange = true;
-            }
-        }
-        return renderStateChange;
-    }
-
-    /**
-     * @param  data  data object
-     * @param index insert index
-     * update data, reset new render state,
-     * return true if only data changed, false if viewType changed
-     * */
-    public boolean  updateData(Object data, int index){
-        boolean onlyDataChange = TextUtils.equals(templateList.getTemplateKey(index), templateList.getTemplateKey(data));
-        listData.set(index, data);
-        if(!onlyDataChange){
-            //structure changed, reset render state
-            cleanRenderState(renderStates.remove(index));
-        }else{
-            CellRenderState renderState = renderStates.get(index);
-            if(renderState != null){
-                renderState.hasDataUpdate = true;
-            }
-        }
-        return onlyDataChange;
-    }
-
-    /**
-     * @param index
-     * remove data, and its render state  and  virtual's data
-     * */
-    public void  removeData(Integer index){
-        listData.remove((int)index); //remove by index
-        cleanRenderState(renderStates.remove(index));
-        int count = listData.size() + 1;
-        for(int i=index + 1; i < count; i++){
-            CellRenderState state = renderStates.remove(i);
-            if(state != null){
-                renderStates.put(i-1, state);
-            }
-        }
-    }
-
-    /**
-     *  clean render state, if has virtual component, call virtual component detach lifecycle
-     * */
-    private void  cleanRenderState(CellRenderState renderState){
-        if(renderState == null){
-            return;
-        }
-        if(renderState.hasVirtualComponents()){
-            Collection<String> virtualComponentIds =  renderState.getVirtualComponentIds().values();
-            for(String virtualComponentId : virtualComponentIds){
-                if(virtualComponentRenderStates != null){
-                    virtualComponentRenderStates.remove(virtualComponentId);
-                }
-                WXBridgeManager.getInstance().asyncCallJSEventVoidResult(WXBridgeManager.METHD_COMPONENT_HOOK_SYNC,
-                        templateList.getInstanceId(),
-                        null,
-                        virtualComponentId, VirtualComponentLifecycle.LIFECYCLE, VirtualComponentLifecycle.DETACH, null);
-
-            }
-        }
-    }
-
-
-    /**
-     * create virtualComponentId
-     * */
-    public static String createVirtualComponentId(String listRef, String viewTreeKey, long itemId){
-        return  listRef + VIRTUAL_COMPONENT_SEPRATOR  + viewTreeKey + VIRTUAL_COMPONENT_SEPRATOR + itemId;
-    }
-
-    /**
-     * get list ref from virtualComponentId
-     * */
-    public static String getListRef(String virtualComponentId){
-        if(virtualComponentId == null){
-            return null;
-        }
-        return virtualComponentId.split(VIRTUAL_COMPONENT_SEPRATOR)[0];
-    }
-    
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellRenderContext.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellRenderContext.java
deleted file mode 100644
index 36fea10..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellRenderContext.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import com.taobao.weex.el.parse.ArrayStack;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by furture on 2018/1/23.
- * render context for cell template
- */
-public class CellRenderContext {
-    /**
-     * code execute stack
-     * */
-    public ArrayStack stack = new ArrayStack();
-    /**
-     * init context data
-     * */
-    public Map map = new HashMap(8);
-
-
-    /**
-     * component data context
-     * */
-    public CellRenderState renderState;
-
-    /**
-     * current position
-     * */
-    public int position;
-
-    /**
-     * current list component
-     * */
-    public WXRecyclerTemplateList templateList;
-
-
-    /**
-     * get current render state
-     * */
-    public CellRenderState getRenderState() {
-        if(renderState != null) {
-            renderState =  templateList.getCellDataManager().getRenderState(position);
-        }
-        return renderState;
-    }
-
-
-    public void clear(){
-        if(stack.getList().size() > 0) {
-            stack.getList().clear();
-        }
-        if(map.size() > 0) {
-            map.clear();
-        }
-        renderState  = null;
-        position = 0;
-        templateList = null;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellRenderState.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellRenderState.java
deleted file mode 100644
index 2f71a81..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/CellRenderState.java
+++ /dev/null
@@ -1,122 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import android.support.v7.widget.RecyclerView;
-
-import com.taobao.weex.el.parse.ArrayStack;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by furture on 2018/1/24.
- * render state for one cell, manage it's render state
- */
-public class CellRenderState {
-
-    /**
-     * dirty for current position, for example virtual component has update
-     * */
-    boolean hasVirtualCompoentUpdate = false;
-
-    /**
-     * has date update
-     * */
-    boolean hasDataUpdate = false;
-
-    /**
-     * position changed
-     * */
-    boolean hasPositionChange = false;
-
-    /**
-     *  may use position, when position changed should be rendered
-     * */
-    int  position;
-
-    /**
-     * unique itemId for current position, generate via key core
-     * */
-    long itemId = RecyclerView.NO_ID;
-
-
-
-    /**
-     * virtualCompoentId for cell, key is viewTreeKey, value is virutalComponentId.
-     * lazy init,
-     * */
-    private Map<String, String> virtualComponentIds;
-    private Map<String, Object> virtualComponentDatas;
-
-
-    /**
-     * mark once statements has rendered
-     * */
-    private Map<String,ArrayStack> onceComponentStates;
-
-
-    public Map<String, String> getVirtualComponentIds() {
-        if(virtualComponentIds == null){
-            virtualComponentIds = new HashMap<>(8);
-        }
-        return virtualComponentIds;
-    }
-
-    /**
-     * return current cell has virtual component
-     * */
-    public boolean hasVirtualComponents(){
-        return virtualComponentIds != null && virtualComponentIds.size() > 0;
-    }
-
-    public Map<String, Object> getVirtualComponentDatas() {
-        if(virtualComponentDatas == null){
-            virtualComponentDatas = new HashMap<>(4);
-        }
-        return virtualComponentDatas;
-    }
-
-    public Map<String, ArrayStack> getOnceComponentStates() {
-        if(onceComponentStates == null){
-            onceComponentStates = new HashMap<>();
-        }
-        return onceComponentStates;
-    }
-
-    public boolean isDirty() {
-        return hasDataUpdate
-                || hasVirtualCompoentUpdate
-                || hasPositionChange;
-    }
-
-    public boolean isHasDataUpdate() {
-        return hasDataUpdate;
-    }
-
-
-
-    public void  resetDirty(){
-        hasDataUpdate = false;
-        hasVirtualCompoentUpdate = false;
-        hasPositionChange = false;
-    }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/PositionRef.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/PositionRef.java
deleted file mode 100644
index d176302..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/PositionRef.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import com.alibaba.fastjson.JSONAware;
-import com.alibaba.fastjson.annotation.JSONType;
-
-/**
- * position render state, when render state change, position changed
- * Created by furture on 2018/2/2.
- */
-public class PositionRef extends  Number implements JSONAware {
-
-    private CellRenderState renderState;
-
-    public PositionRef(CellRenderState renderState) {
-        this.renderState = renderState;
-    }
-
-    @Override
-    public int intValue() {
-        return getPosition();
-    }
-
-    @Override
-    public long longValue() {
-        return getPosition();
-    }
-
-    @Override
-    public float floatValue() {
-        return getPosition();
-    }
-
-    @Override
-    public double doubleValue() {
-        return getPosition();
-    }
-
-    private int getPosition(){
-        if(renderState == null){
-            return  -1;
-        }
-        return renderState.position;
-    }
-
-    @Override
-    public String toString() {
-        return String.valueOf(getPosition());
-    }
-
-    @Override
-    public String toJSONString() {
-        return String.valueOf(getPosition());
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/Selector.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/Selector.java
deleted file mode 100644
index 3765c81..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/Selector.java
+++ /dev/null
@@ -1,120 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import android.text.TextUtils;
-
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.component.list.WXCell;
-
-import java.util.List;
-
-/**
- * Created by furture on 2018/7/24.
- */
-
-public class Selector {
-
-    /**
-     * @param  selector  [att=xx]
-     * query elements match selector, current only support attr selector
-     * */
-    public static void queryElementAll(WXComponent component, String selector, List<WXComponent> componentList){
-        if(TextUtils.isEmpty(selector)){
-            return;
-        }
-        selector = selector.replaceAll("\\[|]", "");
-        String[] args = selector.split("=");
-        if(args.length <= 0){
-            return;
-        }
-        String key = args[0];
-        String value = null;
-        if(args.length > 1){
-            value = args[1].trim();
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            for(int i=0; i<container.getChildCount(); i++){
-                queryElementAllByAttrs(container.getChild(i), key, value, componentList);
-            }
-        }
-    }
-
-
-    public static void closest(WXComponent component, String selector,List<WXComponent> componentList){
-        if(TextUtils.isEmpty(selector)){
-            return;
-        }
-        selector = selector.replaceAll("\\[|]", "");
-        String[] args = selector.split("=");
-        if(args.length <= 0){
-            return;
-        }
-        String key = args[0];
-        String value = null;
-        if(args.length > 1){
-            value = args[1].trim();
-        }
-        closestByAttrs(component, key, value, componentList);
-    }
-
-    private static void closestByAttrs(WXComponent component, String key, String value, List<WXComponent> componentList){
-        if(matchAttrs(component, key, value)){
-            componentList.add(component);
-        }
-        if(component instanceof  WXCell || component instanceof  WXRecyclerTemplateList){
-            return;
-        }
-        queryElementAllByAttrs(component.getParent(), key, value, componentList);
-    }
-
-
-    private static void queryElementAllByAttrs(WXComponent component, String key, String value, List<WXComponent> componentList){
-        if(matchAttrs(component, key, value)){
-            componentList.add(component);
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            for(int i=0; i<container.getChildCount(); i++){
-                queryElementAllByAttrs(container.getChild(i), key, value, componentList);
-            }
-        }
-    }
-
-
-    private static boolean matchAttrs(WXComponent component, String key, String value){
-        if(component.isWaste()){
-            return false;
-        }
-        if(!component.getAttrs().containsKey(key)){
-            return false;
-        }
-        if(TextUtils.isEmpty(value)){
-            return true;
-        }
-        Object attrValue = component.getAttrs().get(key);
-        if(attrValue == null){
-            return false;
-        }
-        return value.equals(attrValue.toString());
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateCache.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateCache.java
deleted file mode 100644
index 4ae98c3..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateCache.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import com.taobao.weex.ui.component.list.WXCell;
-
-import java.util.concurrent.ConcurrentLinkedQueue;
-
-/**
- * preload cell cache
- * Created by furture on 2017/9/29.
- */
-class TemplateCache {
-    ConcurrentLinkedQueue<WXCell> cells = new ConcurrentLinkedQueue<>();
-    boolean isLoadIng = false;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateDom.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateDom.java
deleted file mode 100644
index 78f7d90..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateDom.java
+++ /dev/null
@@ -1,226 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import android.support.v4.view.ViewCompat;
-import android.view.View;
-
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Created by furture on 2018/6/27.
- */
-
-public class TemplateDom {
-
-    public static final String KEY_RESET_ANIMATION = "resetAnimation";
-    public static final String KEY_ATTRS = "attrs";
-    public static final String KEY_TYPE = "type";
-    public static final String KEY_VIRTUAL_DOM_REF = "ref";
-    public static final String VIRTUAL_DOM_IDENTIFY = "[[VirtualElement]]";
-
-
-    public static final String ATTRS_KEY_REF = "ref";
-
-    public static final String ATTACH_CELL_SLOT = "_attach_slot";
-    public static final String DETACH_CELL_SLOT = "_detach_slot";
-
-    public static final char SEPARATOR = '@';
-
-
-    public static String genKeyVirtualDomRef(String listRef, int position, String key){
-        return listRef + SEPARATOR + position + SEPARATOR  +  key;
-    }
-
-    public static WXComponent findVirtualComponentByVRef(String pageId, String virtualRef) {
-        try{
-
-            String[]  segments = virtualRef.split(SEPARATOR + "");
-            String listRef = segments[0]; // list ref
-            WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(pageId, listRef);
-            if(!(component instanceof WXRecyclerTemplateList)){
-                return null;
-            }
-            WXRecyclerTemplateList templateList = (WXRecyclerTemplateList) component;
-            if(templateList.getHostView() == null || templateList.getHostView().getInnerView() == null){
-                return null;
-            }
-            int position = Integer.parseInt(segments[1]); // position
-            WXRecyclerView recyclerView = templateList.getHostView().getInnerView();
-            TemplateViewHolder itemHolder = (TemplateViewHolder) recyclerView.findViewHolderForAdapterPosition(position);
-            if(itemHolder == null){
-                return null;
-            }
-
-            WXCell cell = itemHolder.getTemplate();
-            String viewKey = segments[2]; //viewkey
-            WXComponent target = findComponentByViewTreeKey(cell, viewKey);
-            return  target;
-        }catch (Exception e){
-            return  null;
-        }
-    }
-
-    /**
-     * find all component that contains ref attr
-     * */
-    public static Map<String,Object> findAllComponentRefs(String listRef, int position , WXComponent component){
-        Map<String,Object> refs = new HashMap<>();
-        findAllComponentRefs(listRef, position, component, refs);
-        Map<String,Object> refsMap = new HashMap<>();
-        refsMap.put("refs", refs);
-        refsMap.put("position", position);
-        refsMap.put("listRef", listRef);
-        return refsMap;
-    }
-
-    private static void findAllComponentRefs(String listRef, int position, WXComponent component, Map<String,Object> refs){
-        if(component.isWaste()){
-            return;
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            for(int i=0; i<container.getChildCount(); i++){
-                WXComponent child = container.getChild(i);
-                findAllComponentRefs(listRef, position, child, refs);
-            }
-        }
-        WXAttr attrs = component.getAttrs();
-        if(attrs != null
-                && attrs.get(TemplateDom.ATTRS_KEY_REF) == null){
-            return;
-        }
-        String ref  = attrs.get(TemplateDom.ATTRS_KEY_REF).toString();
-        List<Object> refList = (List<Object>) refs.get(ref);
-        if(refList == null){
-            refList = new ArrayList<>();
-            refs.put(ref, refList);
-        }
-        Map map = toMap(listRef, position, component);
-        refList.add(map);
-    }
-
-
-    public static Map toMap(String listRef, int position, WXComponent component){
-        Map map = new HashMap();
-        map.put(TemplateDom.KEY_ATTRS, component.getAttrs());
-        map.put(TemplateDom.KEY_TYPE, component.getComponentType());
-        map.put(TemplateDom.KEY_VIRTUAL_DOM_REF, TemplateDom.genKeyVirtualDomRef(listRef, position, component.getViewTreeKey()));
-        map.put(VIRTUAL_DOM_IDENTIFY, true);
-        return map;
-    }
-
-
-    public static boolean isVirtualDomRef(String ref){
-        if(ref != null){
-            return  ref.indexOf(SEPARATOR) > 0;
-        }
-        return  false;
-    }
-
-
-    public static void resetAnimaiton(View view){
-        if(view == null){
-            return;
-        }
-        if(ViewCompat.getTranslationX(view) != 0){
-            ViewCompat.setTranslationX(view, 0);
-        }
-
-        if(ViewCompat.getTranslationY(view) != 0){
-            ViewCompat.setTranslationY(view, 0);
-        }
-
-        if(ViewCompat.getTranslationZ(view) != 0){
-            ViewCompat.setTranslationZ(view, 0);
-        }
-
-        if(ViewCompat.getScaleX(view) != 1.0f){
-            ViewCompat.setScaleX(view, 1.0f);
-        }
-
-        if(ViewCompat.getScaleY(view) != 1.0f){
-            ViewCompat.setScaleY(view, 1.0f);
-        }
-
-        if(ViewCompat.getRotationX(view) != 0){
-            ViewCompat.setRotationX(view, 0);
-        }
-
-        if(ViewCompat.getRotationY(view) != 0){
-            ViewCompat.setRotationY(view, 0);
-        }
-
-        if(ViewCompat.getElevation(view) != 0){
-            ViewCompat.setElevation(view, 0);
-        }
-    }
-
-
-    /**
-     * find child list, has same ref
-     * */
-    public static final  WXComponent findComponentByViewTreeKey(WXComponent component, String viewKey){
-        if(component.getViewTreeKey().equals(viewKey)){
-            return component;
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            for(int i=0; i<container.getChildCount(); i++){
-                WXComponent element = container.getChild(i);
-                if(findComponentByViewTreeKey(element, viewKey) != null){
-                    return element;
-                }
-            }
-
-        }
-        return null;
-    }
-
-    /**
-     * find child by ref
-     * */
-    private  static WXComponent findChildByAttrsRef(WXComponent component, String ref){
-        if(component.getAttrs() != null && ref.equals(component.getAttrs().get(TemplateDom.ATTRS_KEY_REF))){
-            return component;
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            for(int i=0; i<container.getChildCount(); i++){
-                WXComponent child = findChildByAttrsRef(container.getChild(i), ref);
-                if(child != null){
-                    return  child;
-                }
-            }
-        }
-        return  null;
-    }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateStickyHelper.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateStickyHelper.java
deleted file mode 100644
index ffc6b07..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateStickyHelper.java
+++ /dev/null
@@ -1,250 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import android.support.v4.util.ArrayMap;
-import android.support.v7.widget.LinearLayoutManager;
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.FrameLayout;
-
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.view.refresh.wrapper.BounceRecyclerView;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * StickyHelper For Template List
- * Created by furture on 2017/8/24.
- */
-public class TemplateStickyHelper {
-    private WXRecyclerTemplateList recyclerTemplateList;
-    private List<Integer> stickyPositions;
-    private ArrayMap<Integer, TemplateViewHolder>   stickyHolderCache;
-    private List<String> mStickyTypes;
-
-
-    public TemplateStickyHelper(WXRecyclerTemplateList recyclerTemplateList) {
-        this.recyclerTemplateList = recyclerTemplateList;
-        this.stickyPositions = new ArrayList<>();
-        this.stickyHolderCache = new ArrayMap();
-        this.mStickyTypes = new ArrayList<>(8);
-    }
-
-    /**
-     * dispatch scroll event, sticky  header
-     * */
-    public void onBeforeScroll(int dx, int dy) {
-        if(stickyPositions == null || stickyPositions.size() == 0){
-           return;
-        }
-        BounceRecyclerView bounceRecyclerView = recyclerTemplateList.getHostView();
-        RecyclerView recyclerView = recyclerTemplateList.getHostView().getInnerView();
-        RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
-        int firstVisiblePosition = -1;
-        int lastVisiblePosition = -1;
-        if (layoutManager instanceof LinearLayoutManager) {
-            firstVisiblePosition = ((LinearLayoutManager) layoutManager).findFirstVisibleItemPosition();
-            lastVisiblePosition  = ((LinearLayoutManager) layoutManager).findLastVisibleItemPosition();
-        }else if (layoutManager instanceof StaggeredGridLayoutManager) {
-            int [] firstVisibleItemPositions = new int[3];//max 3 column
-            firstVisiblePosition = ((StaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(firstVisibleItemPositions)[0];
-            lastVisiblePosition = ((StaggeredGridLayoutManager) layoutManager).findLastVisibleItemPositions(firstVisibleItemPositions)[0];
-        }
-        if(firstVisiblePosition < 0){
-            return;
-        }
-
-        TemplateViewHolder firstVisibleItemHolder = (TemplateViewHolder) recyclerView.findViewHolderForAdapterPosition(firstVisiblePosition);
-        if(firstVisibleItemHolder == null){
-            return;
-        }
-
-        //find match sticky position
-        int matchStickyPosition = -1;
-        for (Integer headerPosition : stickyPositions){
-            if(headerPosition == null){
-                continue;
-            }
-            if(headerPosition <= firstVisiblePosition){
-                matchStickyPosition = Math.max(matchStickyPosition, headerPosition);
-            }else{
-                break;
-            }
-        }
-        if(matchStickyPosition < 0){
-            //remove holder for match position not found
-            View stickyFakeView = bounceRecyclerView.getChildAt(bounceRecyclerView.getChildCount() - 1);
-            if(stickyFakeView.getTag() instanceof TemplateViewHolder){
-                TemplateViewHolder stickyFakeViewHolder = (TemplateViewHolder) stickyFakeView.getTag();
-                bounceRecyclerView.removeView(stickyFakeViewHolder.itemView);
-                stickyFakeViewHolder.itemView.setTranslationY(0);
-                if(stickyFakeViewHolder.getComponent() != null
-                        && stickyFakeViewHolder.getComponent().getEvents().contains(Constants.Event.UNSTICKY)){
-                    stickyFakeViewHolder.getComponent().fireEvent(Constants.Event.UNSTICKY);
-                }
-            }
-
-            /**check has sticky cell not visible */
-            for(int i=0; i<recyclerView.getChildCount(); i++) {
-                View itemView = recyclerView.getChildAt(i);
-                TemplateViewHolder itemHolder = (TemplateViewHolder) recyclerView.getChildViewHolder(itemView);
-                if (itemHolder == null) {
-                    continue;
-                }
-                int adapterPosition = itemHolder.getAdapterPosition();
-                if (!stickyPositions.contains(adapterPosition)) {
-                    continue;
-                }
-                if(itemView.getVisibility() != View.VISIBLE) {
-                    itemView.setVisibility(View.VISIBLE);
-                }
-            }
-            return;
-        }
-
-        //onCreate holder for match position if not exist
-        View stickyFakeView = bounceRecyclerView.getChildAt(bounceRecyclerView.getChildCount() - 1);
-        if(!(stickyFakeView.getTag() instanceof TemplateViewHolder)
-                || ((TemplateViewHolder) stickyFakeView.getTag()).getHolderPosition() != matchStickyPosition){
-
-             //remove previous sticky header
-            if(stickyFakeView.getTag() instanceof TemplateViewHolder &&
-                    ((TemplateViewHolder) stickyFakeView.getTag()).getHolderPosition() != matchStickyPosition){
-                TemplateViewHolder stickyFakeViewHolder = (TemplateViewHolder) stickyFakeView.getTag();
-                bounceRecyclerView.removeView(stickyFakeViewHolder.itemView);
-                stickyFakeViewHolder.itemView.setTranslationY(0);
-                if(stickyFakeViewHolder.getComponent() != null
-                        && stickyFakeViewHolder.getComponent().getEvents().contains(Constants.Event.UNSTICKY)){
-                    stickyFakeViewHolder.getComponent().fireEvent(Constants.Event.UNSTICKY);
-                }
-            }
-
-            //onCreate new sticky
-            int stickyHolderType = recyclerTemplateList.getItemViewType(matchStickyPosition);
-            TemplateViewHolder fakeStickyHolder = stickyHolderCache.get(stickyHolderType);
-            if(fakeStickyHolder == null){
-                fakeStickyHolder = recyclerTemplateList.onCreateViewHolder(recyclerView, stickyHolderType);
-                stickyHolderCache.put(stickyHolderType, fakeStickyHolder);
-            }
-            recyclerTemplateList.onBindViewHolder(fakeStickyHolder, matchStickyPosition);
-            fakeStickyHolder.itemView.setTranslationY(0);
-            fakeStickyHolder.itemView.setTag(fakeStickyHolder);
-            FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
-            fakeStickyHolder.getComponent().clearPreLayout();
-            if(fakeStickyHolder.itemView.getParent() != null){
-                ViewGroup parent = (ViewGroup) fakeStickyHolder.itemView.getParent();
-                parent.removeView(fakeStickyHolder.itemView);
-            }
-            bounceRecyclerView.addView(fakeStickyHolder.itemView, params);
-            fakeStickyHolder.getComponent().setLayout(fakeStickyHolder.getComponent());
-            stickyFakeView = fakeStickyHolder.itemView;
-            if(fakeStickyHolder.getComponent() != null
-                    && fakeStickyHolder.getComponent().getEvents().contains(Constants.Event.STICKY)){
-                fakeStickyHolder.getComponent().fireEvent(Constants.Event.STICKY);
-            }
-        }
-        TemplateViewHolder stickyFakeViewHolder = (TemplateViewHolder) stickyFakeView.getTag();
-        for(int i=0; i<recyclerView.getChildCount(); i++){
-            View itemView = recyclerView.getChildAt(i);
-            TemplateViewHolder itemHolder = (TemplateViewHolder) recyclerView.getChildViewHolder(itemView);
-            if(itemHolder == null){
-                continue;
-            }
-            int adapterPosition = itemHolder.getAdapterPosition();
-            if(!stickyPositions.contains(adapterPosition)){
-                continue;
-            }
-            if(adapterPosition == stickyFakeViewHolder.getHolderPosition()){
-                if(itemView.getVisibility() != View.INVISIBLE) {
-                    itemView.setVisibility(View.INVISIBLE);
-                }
-            }else{
-                if(itemView.getVisibility() != View.VISIBLE) {
-                    itemView.setVisibility(View.VISIBLE);
-                }
-            }
-        }
-
-        if(firstVisibleItemHolder.getComponent().isSticky()){
-            if(firstVisibleItemHolder.itemView.getY() < 0){
-                if(firstVisibleItemHolder.itemView.getVisibility() != View.INVISIBLE) {
-                    firstVisibleItemHolder.itemView.setVisibility(View.INVISIBLE);
-                }
-                if(stickyFakeView.getVisibility() != View.VISIBLE) {
-                    stickyFakeView.setVisibility(View.VISIBLE);
-                }
-                stickyFakeView.bringToFront();
-            }else{
-                if(firstVisibleItemHolder.itemView.getVisibility() != View.VISIBLE) {
-                    firstVisibleItemHolder.itemView.setVisibility(View.VISIBLE);
-                }
-                if(stickyFakeView.getVisibility() != View.GONE) {
-                    stickyFakeView.setVisibility(View.GONE);
-                }
-            }
-        }else{
-            if(stickyFakeView.getVisibility() != View.VISIBLE){
-                stickyFakeView.setVisibility(View.VISIBLE);
-            }
-        }
-
-        //handle sticky is related, find next sticky position on screen
-        int nextVisiblePostion = firstVisiblePosition + 1;
-        if(lastVisiblePosition > 0){
-            for(int i=nextVisiblePostion; i<= lastVisiblePosition; i++){
-                if(stickyPositions.contains(i)){
-                    nextVisiblePostion = i;
-                    break;
-                }
-            }
-        }
-        if(!stickyPositions.contains(nextVisiblePostion)){
-            if(stickyFakeViewHolder.itemView.getTranslationY() < 0){
-                stickyFakeViewHolder.itemView.setTranslationY(0);
-            }
-            return;
-        }
-        TemplateViewHolder nextStickyHolder = (TemplateViewHolder) recyclerView.findViewHolderForAdapterPosition(nextVisiblePostion);
-        if(nextStickyHolder == null
-                || nextStickyHolder.getComponent() == null){
-            return;
-        }
-        int translationY = (int)(nextStickyHolder.itemView.getY() - stickyFakeViewHolder.itemView.getMeasuredHeight());
-        if(translationY <= 0){
-            stickyFakeViewHolder.itemView.setTranslationY(translationY);
-        }else{
-            stickyFakeViewHolder.itemView.setTranslationY(0);
-        }
-    }
-
-    public List<Integer> getStickyPositions() {
-        if(stickyPositions == null){
-            stickyPositions = new ArrayList<>();
-        }
-        return stickyPositions;
-    }
-
-    public List<String> getStickyTypes() {
-        return mStickyTypes;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateViewHolder.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateViewHolder.java
deleted file mode 100644
index c0d4fb0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/TemplateViewHolder.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import android.os.AsyncTask;
-import android.view.View;
-
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.ui.view.listview.adapter.ListBaseViewHolder;
-
-/**
- * Created by furture on 2017/8/17.
- */
-
-public class TemplateViewHolder extends ListBaseViewHolder {
-
-    /**
-     * strong reference, prevent recycled
-     * */
-    private WXCell template;
-
-    private WXRecyclerTemplateList templateList;
-
-    private int holderPosition = -1;
-
-    public AsyncTask<Void, Void, Void> asyncTask;
-
-    public Object  data;
-
-    /**
-     * header position
-     * */
-
-    public TemplateViewHolder(WXRecyclerTemplateList templateList, WXCell component, int viewType) {
-        super(component, viewType);
-        this.template = component;
-        this.templateList = templateList;
-    }
-
-    public TemplateViewHolder(WXRecyclerTemplateList templateList, View view, int viewType) {
-        super(view, viewType);
-        this.templateList = templateList;
-    }
-
-
-
-
-    public int getHolderPosition() {
-        return holderPosition;
-    }
-
-    public void setHolderPosition(int holderPosition) {
-        this.holderPosition = holderPosition;
-    }
-
-    public WXCell getTemplate() {
-        return template;
-    }
-
-    public WXRecyclerTemplateList getTemplateList() {
-        return templateList;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/VirtualComponentLifecycle.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/VirtualComponentLifecycle.java
deleted file mode 100644
index 5466621..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/VirtualComponentLifecycle.java
+++ /dev/null
@@ -1,45 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-
-/**
- * Created by furture on 2018/2/1.
- */
-
-public class VirtualComponentLifecycle {
-
-    /**
-     * lifecycle
-     * */
-    public static final  String LIFECYCLE = "lifecycle";
-
-
-    /**
-     * virtual component lifecycle
-     * */
-    public static final  String CREATE = "create";
-
-    public static final  String ATTACH = "attach";
-
-    public static final  String SYNSTATE = "syncState";
-
-    public static final  String DETACH = "detach";
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/WXRecyclerTemplateList.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/WXRecyclerTemplateList.java
deleted file mode 100644
index 33f6de6..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/WXRecyclerTemplateList.java
+++ /dev/null
@@ -1,2019 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template;
-
-import static com.taobao.weex.common.Constants.Name.LOADMOREOFFSET;
-import static com.taobao.weex.ui.view.listview.WXRecyclerView.TYPE_LINEAR_LAYOUT;
-
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.os.Build;
-import android.os.Looper;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v4.util.ArrayMap;
-import android.support.v7.widget.GridLayoutManager;
-import android.support.v7.widget.LinearLayoutManager;
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-import android.text.TextUtils;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewTreeObserver;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.annotation.Component;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.ICheckBindingScroller;
-import com.taobao.weex.common.OnWXScrollListener;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.el.parse.ArrayStack;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.AppearanceHelper;
-import com.taobao.weex.ui.component.Scrollable;
-import com.taobao.weex.ui.component.WXBaseRefresh;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXComponentProp;
-import com.taobao.weex.ui.component.WXLoading;
-import com.taobao.weex.ui.component.WXRefresh;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.component.binding.Layouts;
-import com.taobao.weex.ui.component.binding.Statements;
-import com.taobao.weex.ui.component.helper.ScrollStartEndHelper;
-import com.taobao.weex.ui.component.list.RecyclerTransform;
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-import com.taobao.weex.ui.view.listview.adapter.IOnLoadMoreListener;
-import com.taobao.weex.ui.view.listview.adapter.IRecyclerAdapterListener;
-import com.taobao.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
-import com.taobao.weex.ui.view.listview.adapter.WXRecyclerViewOnScrollListener;
-import com.taobao.weex.ui.view.refresh.wrapper.BounceRecyclerView;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Locale;
-import java.util.Map;
-import java.util.Set;
-import java.util.concurrent.ConcurrentHashMap;
-
-/**
- * weex template list supported, high performance recycler-list
- * https://github.com/Hanks10100/weex-native-directive
- * Created by jianbai.gbj on 2017/8/17.
- */
-@Component(lazyload = false)
-public class WXRecyclerTemplateList extends WXVContainer<BounceRecyclerView> implements
-        IRecyclerAdapterListener<TemplateViewHolder>, IOnLoadMoreListener, Scrollable {
-
-    /**
-     * trace log for template list
-     * */
-    public static final boolean ENABLE_TRACE_LOG = false;
-
-    public static final String TAG = "WXRecyclerTemplateList";
-
-    private static final String EMPTY_HOLDER_TEMPLATE_KEY  = "";
-    private static final String NAME_HAS_FIXED_SIZE = "hasFixedSize";
-    private static final String NAME_ITEM_VIEW_CACHE_SIZE = "itemViewCacheSize";
-    private static final String NAME_TEMPLATE_CACHE_SIZE = "templateCacheSize";
-
-    // TODO
-//    private WXRecyclerDomObject mDomObject;
-    protected int mLayoutType = TYPE_LINEAR_LAYOUT;
-    protected int mColumnCount = 1;
-    protected float mColumnGap = 0;
-    protected float mColumnWidth = 0;
-    private float mPaddingLeft;
-    private float mPaddingRight;
-
-    private WXRecyclerViewOnScrollListener mViewOnScrollListener = new WXRecyclerViewOnScrollListener(this);
-    private int mListCellCount = 0;
-    private boolean mForceLoadmoreNextTime = false;
-    private RecyclerView.ItemAnimator mItemAnimator;
-
-    /**
-     * default orientation
-     * */
-    private  int orientation = Constants.Orientation.VERTICAL;
-
-    /**
-     * offset reported
-     * */
-    private boolean isScrollable = true;
-    private int mOffsetAccuracy = 10;
-    private Point mLastReport = new Point(-1, -1);
-    private boolean mHasAddScrollEvent = false;
-
-
-    private CellDataManager cellDataManager;
-    private String listDataKey = Constants.Name.Recycler.LIST_DATA;
-    private String listDataItemKey = null;
-    private String listDataIndexKey = null;
-    private ArrayMap<String, Integer> mTemplateViewTypes;
-
-
-    private Map<String, WXCell> mTemplateSources;
-    private String  listDataTemplateKey = Constants.Name.Recycler.SLOT_TEMPLATE_CASE;
-    private Runnable listUpdateRunnable;
-    private ConcurrentHashMap<String, TemplateCache> mTemplatesCache;
-    private int templateCacheSize = 2;
-
-
-    /**
-     * case default cell and key
-     * */
-    private WXCell defaultTemplateCell;
-    private String defaultTemplateKey = "@default_template_cell";
-
-    /**
-     * scroll start and scroll end event
-     * */
-    private ScrollStartEndHelper mScrollStartEndHelper;
-
-
-    /**
-     * sticky helper
-     * */
-    private TemplateStickyHelper mStickyHelper;
-
-
-    /**
-     * appear and disappear event managaer
-     * */
-    private ArrayMap<Integer, List<AppearanceHelper>> mAppearHelpers = new ArrayMap<>();
-
-    /**
-     * disappear event will be fire,
-     * fist layer map key position,
-     * send layer map key String ref
-     * three layer map key view hash code, value is event arguments
-     * */
-    private ArrayMap<Integer, Map<String,Map<Integer, List<Object>>>> mDisAppearWatchList = new ArrayMap<>();
-
-    private CellRenderContext cellRenderContext = new CellRenderContext();
-
-    private Runnable mAppearChangeRunnable = null;
-    private static final long APPEAR_CHANGE_RUNNABLE_DELAY = 50;
-
-    /**
-     * has append tree done
-     * */
-    private boolean hasAppendTreeDone = false;
-
-    /**
-     * has layout done
-     * */
-    private boolean hasLayoutDone = false;
-
-    public WXRecyclerTemplateList(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-        super(instance, parent, basicComponentData);
-        initRecyclerTemplateList(instance, basicComponentData, parent);
-    }
-
-    private void initRecyclerTemplateList(WXSDKInstance instance, BasicComponentData basicComponentData,
-                                          WXVContainer parent){
-
-        updateRecyclerAttr();
-
-        mTemplateViewTypes = new ArrayMap<>();
-        mTemplateViewTypes.put(EMPTY_HOLDER_TEMPLATE_KEY, 0); //empty view, when template was not sended
-        mTemplateSources = new HashMap<>();
-        mTemplatesCache = new ConcurrentHashMap<>();
-        mStickyHelper = new TemplateStickyHelper(this);
-        orientation =  basicComponentData.getAttrs().getOrientation();
-        listDataTemplateKey = WXUtils.getString(getAttrs().get(Constants.Name.Recycler.LIST_DATA_TEMPLATE_SWITCH_KEY), Constants.Name.Recycler.SLOT_TEMPLATE_CASE);
-        listDataItemKey = WXUtils.getString(getAttrs().get(Constants.Name.Recycler.LIST_DATA_ITEM), listDataItemKey);
-        listDataIndexKey = WXUtils.getString(getAttrs().get(Constants.Name.Recycler.LIST_DATA_ITEM_INDEX), listDataIndexKey);
-        cellDataManager = new CellDataManager(this);
-        cellDataManager.listData = parseListDataToJSONArray(getAttrs().get(Constants.Name.Recycler.LIST_DATA));
-        /**
-         * we have separate cell with list, post add cell in dom thread ensure
-         * list has layout and can archive better user experience and better load time,
-         * which reduce waste cell layout when list layout changes.
-         * */
-        // TODO
-//        if(mDomObject != null
-//                && mDomObject.getCellList() != null
-//                && mDomObject.getCellList().size() > 0){
-//            Runnable runnable =  new Runnable() {
-//                // @Override
-//                public void run() {
-//                    if(isDestoryed()){
-//                        return;
-//                    }
-//                    long start = System.currentTimeMillis();
-//                    if(mDomObject != null && mDomObject.getCellList() != null){
-//                        for(int i=0; i<mDomObject.getCellList().size(); i++){
-//                            addChild(ComponentUtils.buildTree(mDomObject.getCellList().get(i),  WXRecyclerTemplateList.this));
-//                        }
-//                    }
-//                    if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG){
-//                        WXLogUtils.d(TAG, "TemplateList BuildDomTree Used " + (System.currentTimeMillis() - start));
-//                    }
-//                }
-//            };
-//            WXSDKManager.getInstance().getWXDomManager().post(runnable);
-//        }
-    }
-
-    @Override
-    protected BounceRecyclerView initComponentHostView(@NonNull Context context) {
-        final BounceRecyclerView bounceRecyclerView = new BounceRecyclerView(context,mLayoutType,mColumnCount,mColumnGap, getOrientation());
-        WXAttr attrs = getAttrs();
-        String transforms = (String) attrs.get(Constants.Name.TRANSFORM);
-        if (transforms != null) {
-            bounceRecyclerView.getInnerView().addItemDecoration(RecyclerTransform.parseTransforms(getOrientation(), transforms));
-        }
-        mItemAnimator = bounceRecyclerView.getInnerView().getItemAnimator();
-
-        if(attrs.get(NAME_TEMPLATE_CACHE_SIZE) != null){
-            templateCacheSize =  WXUtils.getInteger(attrs.get(NAME_TEMPLATE_CACHE_SIZE), templateCacheSize);
-        }
-
-        boolean hasFixedSize = false;
-        int itemViewCacheSize = 2;
-        if(attrs.get(NAME_ITEM_VIEW_CACHE_SIZE) != null){
-            itemViewCacheSize = WXUtils.getNumberInt(getAttrs().get(NAME_ITEM_VIEW_CACHE_SIZE), itemViewCacheSize);
-        }
-        if(attrs.get(NAME_HAS_FIXED_SIZE) != null){
-            hasFixedSize =  WXUtils.getBoolean(attrs.get(NAME_HAS_FIXED_SIZE), hasFixedSize);
-        }
-        RecyclerViewBaseAdapter recyclerViewBaseAdapter = new RecyclerViewBaseAdapter<>(this);
-        recyclerViewBaseAdapter.setHasStableIds(true);
-        bounceRecyclerView.getInnerView().setItemAnimator(null);
-        if(itemViewCacheSize != 2) {
-            bounceRecyclerView.getInnerView().setItemViewCacheSize(itemViewCacheSize);
-        }
-        if(bounceRecyclerView.getSwipeLayout()  != null){
-            if(WXUtils.getBoolean(getAttrs().get("nestedScrollingEnabled"), false)) {
-                bounceRecyclerView.getSwipeLayout().setNestedScrollingEnabled(true);
-            }
-        }
-        bounceRecyclerView.getInnerView().setHasFixedSize(hasFixedSize);
-        bounceRecyclerView.setRecyclerViewBaseAdapter(recyclerViewBaseAdapter);
-        bounceRecyclerView.setOverScrollMode(View.OVER_SCROLL_NEVER);
-        bounceRecyclerView.getInnerView().clearOnScrollListeners();
-        bounceRecyclerView.getInnerView().addOnScrollListener(mViewOnScrollListener);
-        bounceRecyclerView.getInnerView().addOnScrollListener(new RecyclerView.OnScrollListener() {
-            @Override
-            public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
-                super.onScrollStateChanged(recyclerView, newState);
-                getScrollStartEndHelper().onScrollStateChanged(newState);
-                List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
-                if (listeners != null && listeners.size() > 0) {
-                    for (OnWXScrollListener listener : listeners) {
-                        if (listener != null) {
-                            View topView = recyclerView.getChildAt(0);
-                            if (topView != null) {
-                                int y = topView.getTop();
-                                listener.onScrollStateChanged(recyclerView, 0, y, newState);
-                            }
-                        }
-                    }
-                }
-            }
-
-            @Override
-            public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
-                super.onScrolled(recyclerView, dx, dy);
-                List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
-                if (listeners != null && listeners.size() > 0) {
-                    try {
-                        for (OnWXScrollListener listener : listeners) {
-                            if (listener != null) {
-                                if (listener instanceof ICheckBindingScroller) {
-                                    if (((ICheckBindingScroller) listener).isNeedScroller(getRef(), null)) {
-                                        listener.onScrolled(recyclerView, dx, dy);
-                                    }
-                                } else {
-                                    listener.onScrolled(recyclerView, dx, dy);
-                                }
-                            }
-                        }
-                    } catch (Exception e) {
-                        e.printStackTrace();
-                    }
-                }
-            }
-        });
-        bounceRecyclerView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
-            @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
-            @Override
-            public void onGlobalLayout() {
-                BounceRecyclerView view;
-                if ((view = getHostView()) == null)
-                    return;
-                mViewOnScrollListener.onScrolled(view.getInnerView(), 0, 0);
-                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
-                    view.getViewTreeObserver().removeOnGlobalLayoutListener(this);
-                } else {
-                    view.getViewTreeObserver().removeGlobalOnLayoutListener(this);
-                }
-            }
-        });
-        listUpdateRunnable = new Runnable() {
-            @Override
-            public void run() {
-                /**
-                 * compute sticky position
-                 * */
-                if(mStickyHelper != null){
-                    if(mStickyHelper.getStickyTypes().size() > 0){
-                        mStickyHelper.getStickyPositions().clear();
-                        if(cellDataManager.listData != null){
-                            for(int i = 0; i< cellDataManager.listData.size(); i++){
-                                WXCell cell = getSourceTemplate(i);
-                                if(cell == null){
-                                    continue;
-                                }
-                                if(cell.isSticky()){
-                                    mStickyHelper.getStickyPositions().add(i);
-                                }
-                            }
-                        }
-                    }
-                }
-                if(getHostView() != null && getHostView().getRecyclerViewBaseAdapter() != null){
-                    getHostView().getRecyclerViewBaseAdapter().notifyDataSetChanged();
-                }
-                if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG){
-                    WXLogUtils.d(TAG, "WXTemplateList notifyDataSetChanged");
-                }
-            }
-        };
-        return bounceRecyclerView;
-    }
-
-
-
-
-    @Override
-    protected void onHostViewInitialized(BounceRecyclerView host) {
-        super.onHostViewInitialized(host);
-        WXRecyclerView recyclerView = host.getInnerView();
-        if (recyclerView == null || recyclerView.getAdapter() == null) {
-            WXLogUtils.e(TAG, "RecyclerView is not found or Adapter is not bound");
-            return;
-        }
-    }
-
-    /**
-     * Measure the size of the recyclerView.
-     *
-     * @param width  the expected width
-     * @param height the expected height
-     * @return the result of measurement
-     */
-    @Override
-    protected MeasureOutput measure(int width, int height) {
-        int screenH = WXViewUtils.getScreenHeight(WXEnvironment.sApplication);
-        int weexH = WXViewUtils.getWeexHeight(getInstanceId());
-        int outHeight = height > (weexH >= screenH ? screenH : weexH) ? weexH - getAbsoluteY() : height;
-        return super.measure(width, outHeight);
-    }
-
-
-    @Override
-    public void bindStickStyle(WXComponent component) {
-        WXComponent template = findParentType(component, WXCell.class);
-        if(template == null){
-            return;
-        }
-        if(mStickyHelper == null){
-            return;
-        }
-        if(!mStickyHelper.getStickyTypes().contains(template.getRef())){
-            mStickyHelper.getStickyTypes().add(template.getRef());
-            notifyUpdateList();
-        }
-    }
-
-    @Override
-    public void unbindStickStyle(WXComponent component) {
-        WXComponent template = findParentType(component, WXCell.class);
-        if(template == null
-                || mStickyHelper == null){
-            return;
-        }
-        if(mStickyHelper.getStickyTypes().contains(template.getRef())){
-            mStickyHelper.getStickyTypes().remove(template.getRef());
-            notifyUpdateList();
-        }
-    }
-
-    private @Nullable
-    WXCell findCell(WXComponent component) {
-        if(component instanceof WXCell){
-            return (WXCell) component;
-        }
-        WXComponent parent;
-        if (component == null || (parent = component.getParent()) == null) {
-            return null;
-        }
-        return findCell(parent);
-    }
-
-    private void setAppearanceWatch(WXComponent component, int event, boolean enable) {
-        if(cellDataManager.listData == null
-                || mAppearHelpers == null
-                || TextUtils.isEmpty(component.getRef())){
-            return;
-        }
-        WXCell cell = findCell(component);
-        int type = getCellTemplateItemType(cell);
-        if(type < 0){
-            return;
-        }
-        List<AppearanceHelper>  mAppearListeners = mAppearHelpers.get(type);
-        if(mAppearListeners == null){
-            mAppearListeners = new ArrayList<>();
-            mAppearHelpers.put(type, mAppearListeners);
-        }
-        AppearanceHelper item = null;
-        for(AppearanceHelper mAppearListener : mAppearListeners){
-            if(component.getRef().equals(mAppearListener.getAwareChild().getRef())){
-                item = mAppearListener;
-                break;
-            }
-        }
-        if (item != null) {
-            item.setWatchEvent(event, enable);
-        }else {
-            item = new AppearanceHelper(component,  type);
-            item.setWatchEvent(event, enable);
-            mAppearListeners.add(item);
-        }
-    }
-
-    @Override
-    public void bindAppearEvent(WXComponent component) {
-        setAppearanceWatch(component, AppearanceHelper.APPEAR, true);
-        if(mAppearChangeRunnable == null){
-            mAppearChangeRunnable =  new Runnable() {
-                @Override
-                public void run() {
-                    if(mAppearChangeRunnable != null) {
-                        notifyAppearStateChange(0, 0, 0, 0);
-                    }
-                }
-            };
-        }
-        if (getHostView() != null) {
-            getHostView().removeCallbacks(mAppearChangeRunnable);
-            getHostView().postDelayed(mAppearChangeRunnable, APPEAR_CHANGE_RUNNABLE_DELAY);
-        }
-    }
-
-    @Override
-    public void bindDisappearEvent(WXComponent component) {
-        setAppearanceWatch(component, AppearanceHelper.DISAPPEAR, true);
-        if(mAppearChangeRunnable == null){
-            mAppearChangeRunnable =  new Runnable() {
-                @Override
-                public void run() {
-                    if(mAppearChangeRunnable != null) {
-                        notifyAppearStateChange(0, 0, 0, 0);
-                    }
-                }
-            };
-        }
-        if (getHostView() != null) {
-            getHostView().removeCallbacks(mAppearChangeRunnable);
-            getHostView().postDelayed(mAppearChangeRunnable, APPEAR_CHANGE_RUNNABLE_DELAY);
-        }
-    }
-
-    @Override
-    public void unbindAppearEvent(WXComponent component) {
-        setAppearanceWatch(component, AppearanceHelper.APPEAR, false);
-    }
-
-    @Override
-    public void unbindDisappearEvent(WXComponent component) {
-        setAppearanceWatch(component, AppearanceHelper.DISAPPEAR, false);
-    }
-
-
-    @JSMethod(uiThread = true)
-    public void queryElement(String virtualRef, String selector, JSCallback callback){
-        try{
-            String[]  segments = virtualRef.split(TemplateDom.SEPARATOR + "");
-            String listRef = segments[0];
-            int position = Integer.parseInt(segments[1]); // position
-            WXComponent component = TemplateDom.findVirtualComponentByVRef(getInstanceId(), virtualRef);
-            if(component == null){
-                return;
-            }
-            if(getHostView() == null || getHostView().getInnerView() == null){
-                return;
-            }
-            List<WXComponent>  componentList  = new ArrayList<>(4);
-            Selector.queryElementAll(component, selector, componentList);
-            if(componentList.size() > 0){
-                callback.invoke(TemplateDom.toMap(listRef, position, componentList.get(0)));
-            }else{
-                callback.invoke(new HashMap<>(4));
-            }
-        }catch (Exception e){
-            callback.invoke(new HashMap<>(4));
-            WXLogUtils.e(TAG, e);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void queryElementAll(String virtualRef,  String selector, JSCallback callback){
-        List datas = new ArrayList();
-        try{
-            String[]  segments = virtualRef.split(TemplateDom.SEPARATOR + "");
-            String listRef = segments[0];
-            int position = Integer.parseInt(segments[1]); // position
-            WXComponent component = TemplateDom.findVirtualComponentByVRef(getInstanceId(), virtualRef);
-            if(component == null){
-                return;
-            }
-            if(getHostView() == null || getHostView().getInnerView() == null){
-                return;
-            }
-            List<WXComponent>  componentList  = new ArrayList<>(4);
-            Selector.queryElementAll(component, selector, componentList);
-            for(WXComponent child : componentList){
-                datas.add(TemplateDom.toMap(listRef, position, child));
-            }
-            callback.invoke(datas);
-        }catch (Exception e){
-            callback.invoke(datas);
-            WXLogUtils.e(TAG, e);
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void closest(String virtualRef,  String selector, JSCallback callback){
-        try{
-            String[]  segments = virtualRef.split(TemplateDom.SEPARATOR + "");
-            String listRef = segments[0];
-            int position = Integer.parseInt(segments[1]); // position
-            WXComponent component = TemplateDom.findVirtualComponentByVRef(getInstanceId(), virtualRef);
-            if(component == null){
-                return;
-            }
-            if(getHostView() == null || getHostView().getInnerView() == null){
-                return;
-            }
-            List<WXComponent>  componentList  = new ArrayList<>(4);
-            Selector.closest(component, selector, componentList);
-            if(componentList.size() > 0){
-                callback.invoke(TemplateDom.toMap(listRef, position, componentList.get(0)));
-            }else{
-                callback.invoke(new HashMap<>(4));
-            }
-        }catch (Exception e){
-            callback.invoke(new HashMap<>(4));
-            WXLogUtils.e(TAG, e);
-        }
-    }
-
-
-
-    @JSMethod(uiThread = true)
-    public void scrollToElement(String virtualRef, Map<String, Object> options){
-        scrollTo(virtualRef, options);
-    }
-
-
-    @JSMethod(uiThread = true)
-    public void scrollTo(String virtualRef, Map<String, Object> options){
-        int position = -1;
-        try{
-            if(virtualRef.indexOf(TemplateDom.SEPARATOR) > 0){
-                String[]  segments = virtualRef.split(TemplateDom.SEPARATOR + "");
-                position = Integer.parseInt(segments[0]);
-            }else{
-                position = (int) Float.parseFloat(virtualRef);
-            }
-            if (position >= 0) {
-                boolean smooth = true;
-                float offsetFloat = 0;
-                if(options != null) {
-                    smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
-                    String offsetStr = options.get(Constants.Name.OFFSET) == null ? "0" : options.get(Constants.Name.OFFSET).toString();
-                    smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
-                    if (offsetStr != null) {
-                        try {
-                            offsetFloat = WXViewUtils.getRealPxByWidth(Float.parseFloat(offsetStr), getInstance().getInstanceViewPortWidth());
-                        }catch (Exception e ){
-                            WXLogUtils.e("Float parseFloat error :"+e.getMessage());
-                        }
-                    }
-                }
-                final int offset = (int) offsetFloat;
-
-                final int pos = position;
-                BounceRecyclerView bounceRecyclerView = getHostView();
-                if (bounceRecyclerView == null) {
-                    return;
-                }
-                final WXRecyclerView view = bounceRecyclerView.getInnerView();
-                view.scrollTo(smooth, pos, offset, getOrientation());
-            }
-        }catch (Exception e){
-            WXLogUtils.e(TAG, e);
-        }
-    }
-
-
-    @Override
-    public void scrollTo(WXComponent component, Map<String, Object> options) {
-        float offsetFloat = 0;
-        boolean smooth = true;
-        int position = -1;
-        int typeIndex = -1;
-        if (options != null) {
-            String offsetStr = options.get(Constants.Name.OFFSET) == null ? "0" : options.get(Constants.Name.OFFSET).toString();
-            smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
-            if (offsetStr != null) {
-                try {
-                    offsetFloat = WXViewUtils.getRealPxByWidth(Float.parseFloat(offsetStr), getInstance().getInstanceViewPortWidth());
-                }catch (Exception e ){
-                    WXLogUtils.e("Float parseFloat error :"+e.getMessage());
-                }
-            }
-            position = WXUtils.getNumberInt(options.get(Constants.Name.Recycler.CELL_INDEX), -1);
-            typeIndex = WXUtils.getNumberInt(options.get(Constants.Name.Recycler.TYPE_INDEX), -1);
-        }
-        WXCell cell = findCell(component);
-        if(typeIndex >= 0){
-            if(cellDataManager.listData != null && component.getRef() != null){
-                int typePosition = 0;
-                for(int i = 0; i< cellDataManager.listData.size(); i++){
-                    WXCell template = getSourceTemplate(i);
-                    if(template == null){
-                        continue;
-                    }
-                    if(cell.getRef().equals(template.getRef())){
-                        typePosition ++;
-                    }
-                    if(typePosition > typeIndex){
-                        position = i;
-                        break;
-                    }
-                }
-                if(position < 0){
-                    position = cellDataManager.listData.size() - 1;
-                }
-            }
-        }
-
-        final int offset = (int) offsetFloat;
-        BounceRecyclerView bounceRecyclerView = getHostView();
-        if (bounceRecyclerView == null) {
-            return;
-        }
-        if (position >= 0) {
-            final int pos = position;
-            final WXRecyclerView view = bounceRecyclerView.getInnerView();
-            view.scrollTo(smooth, pos, offset, getOrientation());
-        }
-    }
-
-    @Override
-    public int getScrollY() {
-        BounceRecyclerView bounceRecyclerView = getHostView();
-        return bounceRecyclerView == null ? 0 : bounceRecyclerView.getInnerView().getScrollY();
-    }
-
-    @Override
-    public int getScrollX() {
-        BounceRecyclerView bounceRecyclerView = getHostView();
-        return bounceRecyclerView == null ? 0 : bounceRecyclerView.getInnerView().getScrollX();
-    }
-
-    public int getOrientation() {
-        return orientation;
-    }
-
-    @Override
-    public boolean isScrollable() {
-        return isScrollable;
-    }
-
-
-
-    @Override
-    public void addChild(WXComponent child) {
-        this.addChild(child, -1);
-    }
-
-    @Override
-    protected int getChildrenLayoutTopOffset() {
-        return 0;
-    }
-
-    @Override
-    public void addChild(WXComponent child, int index) {
-        /**
-         *  dom object in component is not tree, build tree
-         * */
-        if(!(child instanceof WXCell)) {
-            super.addChild(child, index);
-        }
-        if(child instanceof WXBaseRefresh){
-            return;
-        }
-        if(child instanceof WXCell){
-            if(child.getAttrs() != null){
-                Object templateId = child.getAttrs().get(Constants.Name.Recycler.SLOT_TEMPLATE_CASE);
-                String key = WXUtils.getString(templateId, null);
-                if(getAttrs().containsKey(Constants.Name.Recycler.LIST_DATA_TEMPLATE_SWITCH_KEY)){
-                    if(defaultTemplateCell == null){
-                        defaultTemplateCell = (WXCell) child;
-                        if(!TextUtils.isEmpty(key)){
-                            defaultTemplateKey = key;
-                        }else{
-                            key = defaultTemplateKey;
-                            child.getAttrs().put(Constants.Name.Recycler.SLOT_TEMPLATE_CASE, key);
-                        }
-                    }
-                }else{
-                    if(defaultTemplateCell == null
-                            || child.getAttrs().containsKey(Constants.Name.Recycler.SLOT_TEMPLATE_DEFAULT)){
-                        defaultTemplateCell = (WXCell) child;
-                        if(!TextUtils.isEmpty(key)){
-                            defaultTemplateKey = key;
-                        }else{
-                            key = defaultTemplateKey;
-                            child.getAttrs().put(Constants.Name.Recycler.SLOT_TEMPLATE_CASE, key);
-                        }
-                    }
-                }
-                if(key != null){
-                    // TODO
-//                    if(child.getDomObject() instanceof  WXCellDomObject
-//                            && getDomObject() instanceof  WXRecyclerDomObject){
-//                        WXCellDomObject domObject = (WXCellDomObject) child.getDomObject();
-//                        domObject.setRecyclerDomObject((WXRecyclerDomObject) getDomObject());
-//                    }
-                    mTemplateSources.put(key, (WXCell) child);
-                    if(mTemplateViewTypes.get(key) == null){
-                        mTemplateViewTypes.put(key, mTemplateViewTypes.size());
-                    }
-                }
-            }
-
-            ((WXCell) child).setCellAppendTreeListener(new WXCell.CellAppendTreeListener() {
-                @Override
-                public void onAppendTreeDone() {
-                    checkAppendDone(false);
-                }
-            });
-        }
-    }
-
-
-    /**
-     * check all the cell has append tree done, then show list
-     * */
-    private void  checkAppendDone(boolean listDone){
-        if(mTemplateSources.size() == 0){
-            return;
-        }
-        Set<Map.Entry<String,WXCell>> cells = mTemplateSources.entrySet();
-        for(Map.Entry<String,WXCell> entry : cells){
-            if(!entry.getValue().isAppendTreeDone()){
-                return;
-            }
-        }
-        hasAppendTreeDone = true;
-        if(hasLayoutDone) {
-            notifyUpdateList();
-        }
-    }
-
-    @Override
-    protected void setHostLayoutParams(BounceRecyclerView host, int width, int height, int left, int right, int top, int bottom) {
-        super.setHostLayoutParams(host, width, height, left, right, top, bottom);
-        if(!hasLayoutDone){
-            hasLayoutDone = true;
-            hasAppendTreeDone = true;
-            notifyUpdateList();
-        }
-    }
-
-
-    /**
-     * RecyclerView manage its children in a way that different from {@link WXVContainer}. Therefore,
-     * {@link WXVContainer#addSubView(View, int)} is an empty implementation in {@link
-     * com.taobao.weex.ui.view.listview.WXRecyclerView}
-     */
-    @Override
-    public void addSubView(View child, int index) {
-
-    }
-
-
-    /**
-     * all child is template, none need onCreate child except loading and refresh.
-     * */
-    @Override
-    public void createChildViewAt(int index) {
-        int indexToCreate = index;
-        if (indexToCreate < 0) {
-            indexToCreate = childCount() - 1;
-            if (indexToCreate < 0) {
-                return;
-            }
-        }
-        final WXComponent child = getChild(indexToCreate);
-        if (child instanceof WXBaseRefresh) {
-            child.createView();
-            setRefreshOrLoading(child);
-        }
-    }
-
-    @Override
-    public void remove(WXComponent child, boolean destroy) {
-        removeFooterOrHeader(child);
-        super.remove(child, destroy);
-    }
-
-
-
-    @Override
-    public void computeVisiblePointInViewCoordinate(PointF pointF) {
-        RecyclerView view = getHostView().getInnerView();
-        pointF.set(view.computeHorizontalScrollOffset(), view.computeVerticalScrollOffset());
-    }
-
-    @Override
-    protected boolean setProperty(String key, Object param) {
-        switch (key) {
-            case Constants.Name.Recycler.LIST_DATA:{
-                     setListData(param);
-                }
-                return true;
-            case Constants.Name.Recycler.LIST_DATA_ITEM:
-                listDataItemKey = WXUtils.getString(param, listDataItemKey);
-                return true;
-            case Constants.Name.Recycler.LIST_DATA_ITEM_INDEX:
-                listDataIndexKey = WXUtils.getString(param, listDataIndexKey);
-                return true;
-            case Constants.Name.Recycler.LIST_DATA_TEMPLATE_SWITCH_KEY:
-            case Constants.Name.Recycler.SLOT_TEMPLATE_CASE:
-                listDataTemplateKey = WXUtils.getString(param, Constants.Name.Recycler.SLOT_TEMPLATE_CASE);
-                return true;
-            case LOADMOREOFFSET:
-                return true;
-            case Constants.Name.SCROLLABLE:
-                boolean scrollable = WXUtils.getBoolean(param, true);
-                setScrollable(scrollable);
-                return true;
-            case Constants.Name.SCROLL_DIRECTION:
-                if(param != null) {
-                    setScrollDirection(param.toString());
-                }
-                return true;
-            case Constants.Name.SHOW_SCROLLBAR:
-                Boolean result = WXUtils.getBoolean(param,null);
-                if (result != null)
-                    setShowScrollbar(result);
-                return true;
-            case NAME_ITEM_VIEW_CACHE_SIZE:
-                return true;
-            case NAME_HAS_FIXED_SIZE:
-                return true;
-            case Constants.Name.OFFSET_ACCURACY:
-                int accuracy = WXUtils.getInteger(param, 10);
-                setOffsetAccuracy(accuracy);
-                return true;
-        }
-        return super.setProperty(key, param);
-    }
-
-
-    @WXComponentProp(name = Constants.Name.OFFSET_ACCURACY)
-    public void setOffsetAccuracy(int accuracy) {
-        float real = WXViewUtils.getRealPxByWidth(accuracy, getInstance().getInstanceViewPortWidth());
-        this.mOffsetAccuracy = (int) real;
-    }
-
-
-    private void updateRecyclerAttr(){
-        mLayoutType = getAttrs().getLayoutType();
-        mColumnCount = getAttrs().getColumnCount();
-        if (mColumnCount <= 0 && mLayoutType != TYPE_LINEAR_LAYOUT) {
-            Map<String, String> ext = new ArrayMap<>();
-            ext.put("componentType", getComponentType());
-            ext.put("attribute", getAttrs().toString());
-            ext.put("stackTrace", Arrays.toString(Thread.currentThread().getStackTrace()));
-            WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),
-                WXErrorCode.WX_RENDER_ERR_LIST_INVALID_COLUMN_COUNT, "columnCount",
-                String.format(Locale.ENGLISH,
-                    "You are trying to set the list/recycler/vlist/waterfall's column to %d, which is illegal. The column count should be a positive integer",
-                    mColumnCount),
-                ext);
-            mColumnCount = Constants.Value.COLUMN_COUNT_NORMAL;
-        }
-        mColumnGap = getAttrs().getColumnGap();
-        mColumnWidth = getAttrs().getColumnWidth();
-        mPaddingLeft = getPadding().get(CSSShorthand.EDGE.LEFT);
-        mPaddingRight = getPadding().get(CSSShorthand.EDGE.RIGHT);
-
-    }
-
-
-    @WXComponentProp(name = Constants.Name.SCROLL_DIRECTION)
-    public void setScrollDirection(String direction){
-        if(orientation != getAttrs().getOrientation()) {
-            orientation = getAttrs().getOrientation();
-            updateRecyclerAttr();
-            WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-            wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap, getOrientation());
-
-        }
-    }
-
-    @WXComponentProp(name = Constants.Name.COLUMN_WIDTH)
-    public void setColumnWidth(int columnCount)  {
-        if(getAttrs().getColumnWidth() != mColumnWidth){
-            updateRecyclerAttr();
-            WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-            wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap, getOrientation());
-        }
-    }
-
-    @WXComponentProp(name = Constants.Name.SHOW_SCROLLBAR)
-    public void setShowScrollbar(boolean show) {
-        if(getHostView() == null || getHostView().getInnerView() == null){
-            return;
-        }
-        if (getOrientation() == Constants.Orientation.VERTICAL) {
-            getHostView().getInnerView().setVerticalScrollBarEnabled(show);
-        } else {
-            getHostView().getInnerView().setHorizontalScrollBarEnabled(show);
-        }
-    }
-
-    @WXComponentProp(name = Constants.Name.COLUMN_COUNT)
-    public void setColumnCount(int columnCount){
-        if(getAttrs().getColumnCount() != mColumnCount){
-            updateRecyclerAttr();
-            WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-            wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap,getOrientation());
-        }
-    }
-
-    @WXComponentProp(name = Constants.Name.COLUMN_GAP)
-    public void setColumnGap(float columnGap) throws InterruptedException {
-        if(getAttrs().getColumnGap() != mColumnGap) {
-            updateRecyclerAttr();
-            WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-            wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
-        }
-    }
-
-    @WXComponentProp(name = Constants.Name.SCROLLABLE)
-    public void setScrollable(boolean scrollable) {
-        WXRecyclerView inner = getHostView().getInnerView();
-        inner.setScrollable(scrollable);
-    }
-
-    @JSMethod
-    public void setListData(Object param){
-        param = parseListDataToJSONArray(param);
-        boolean update = cellDataManager.listData != param;
-        if(param instanceof  JSONArray){
-            if(update){
-                cellDataManager.setListData((JSONArray) param);
-                notifyUpdateList();
-            }
-        }
-    }
-
-    @JSMethod
-    public void  appendData(JSONArray data){
-        if(data == null || data.size() == 0){
-            return;
-        }
-        if(cellDataManager.listData == null){
-            cellDataManager.listData = new JSONArray();
-        }
-        int position = cellDataManager.listData.size();
-        if(position < 0){
-            position = 0;
-        }
-        if(data instanceof  JSONArray){
-            cellDataManager.listData.addAll(data);
-        }
-        getHostView().getRecyclerViewBaseAdapter().notifyItemRangeInserted(position, data.size());
-    }
-
-    @JSMethod
-    public void  insertData(int index, Object data){
-        if(data == null){
-            return;
-        }
-
-        if(cellDataManager.listData == null || index > cellDataManager.listData.size()){
-            return;
-        }
-        boolean renderStateChanged = cellDataManager.insertData(index, data);
-        if(renderStateChanged){
-            notifyUpdateList();
-        }else{
-            getHostView().getRecyclerViewBaseAdapter().notifyItemInserted(index);
-        }
-    }
-
-    @JSMethod
-    public void  appendRange(int index, JSONArray data){
-         insertRange(index, data);
-    }
-
-
-    /**
-     * when update data, list maybe contains sticky, may use position, when position changed should be rendered
-     * so use notifyUpdateList is better
-     * */
-
-    @JSMethod
-    public void  insertRange(int index, JSONArray data){
-        if(data == null || data.size() == 0){
-            return;
-        }
-        if(cellDataManager.listData == null || index > cellDataManager.listData.size()){
-            return;
-        }
-        boolean renderStateChange = cellDataManager.insertRange(index, data);
-        if(renderStateChange){
-            notifyUpdateList();
-        }else{
-            getHostView().getRecyclerViewBaseAdapter().notifyItemRangeInserted(index, data.size());
-        }
-
-    }
-
-    @JSMethod
-    public void  updateData(int index, Object data){
-        if(data == null){
-            return;
-        }
-        if(cellDataManager.listData == null || index >= cellDataManager.listData.size()){
-            return;
-        }
-        boolean onlyDataChange = cellDataManager.updateData(data, index);
-        if(onlyDataChange) {
-            getHostView().getRecyclerViewBaseAdapter().notifyItemChanged(index, data);
-        }else{
-            notifyUpdateList();
-        }
-    }
-
-    @JSMethod
-    public void  removeData(int index, int count){
-        if(cellDataManager.listData == null
-                || index >= cellDataManager.listData.size()){
-            return;
-        }
-        if(count <= 0){
-            count = 1;
-        }
-        int removeCount = 0;
-        while (count > 0 && index < cellDataManager.listData.size()){
-            cellDataManager.removeData(index);
-            count--;
-            removeCount++;
-        }
-        if(removeCount > 0) {
-            notifyUpdateList();
-        }
-    }
-
-
-    @JSMethod
-    public void resetLoadmore() {
-        mForceLoadmoreNextTime = true;
-        mListCellCount = 0;
-    }
-
-
-    @Override
-    public void updateProperties(Map<String, Object> props) {
-        super.updateProperties(props);
-        if(props.containsKey(Constants.Name.PADDING)
-                || props.containsKey(Constants.Name.PADDING_LEFT)
-                || props.containsKey(Constants.Name.PADDING_RIGHT)){
-
-            if(mPaddingLeft != getPadding().get(CSSShorthand.EDGE.LEFT)
-                    || mPaddingRight != getPadding().get(CSSShorthand.EDGE.RIGHT)) {
-                updateRecyclerAttr();
-                WXRecyclerView wxRecyclerView = getHostView().getInnerView();
-                wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
-            }
-        }
-    }
-
-
-
-    @Override
-    public void addEvent(String type) {
-        super.addEvent(type);
-        if (ScrollStartEndHelper.isScrollEvent(type)
-                && getHostView() != null
-                && getHostView().getInnerView() != null
-                && !mHasAddScrollEvent) {
-            mHasAddScrollEvent = true;
-            WXRecyclerView innerView = getHostView().getInnerView();
-            innerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
-                private int offsetXCorrection, offsetYCorrection;
-                private boolean mFirstEvent = true;
-
-                @Override
-                public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
-                    super.onScrolled(recyclerView, dx, dy);
-                    RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
-                    if (!layoutManager.canScrollVertically()) {
-                        return;
-                    }
-                    int offsetX = recyclerView.computeHorizontalScrollOffset();
-                    int offsetY = recyclerView.computeVerticalScrollOffset();
-
-                    if (dx == 0 && dy == 0) {
-                        offsetXCorrection = offsetX;
-                        offsetYCorrection = offsetY;
-                        offsetX = 0;
-                        offsetY = 0;
-                    } else {
-                        offsetX = offsetX - offsetXCorrection;
-                        offsetY = offsetY - offsetYCorrection;
-                    }
-                    getScrollStartEndHelper().onScrolled(offsetX, offsetY);
-                    if(!getEvents().contains(Constants.Event.SCROLL)){
-                        return;
-                    }
-                    if (mFirstEvent) {
-                        //skip first event
-                        mFirstEvent = false;
-                        return;
-                    }
-
-                    if (shouldReport(offsetX, offsetY)) {
-                        fireScrollEvent(recyclerView, offsetX, offsetY);
-                    }
-                }
-            });
-        }
-    }
-
-    private void fireScrollEvent(RecyclerView recyclerView, int offsetX, int offsetY) {
-        fireEvent(Constants.Event.SCROLL, getScrollEvent(recyclerView, offsetX, offsetY));
-    }
-
-    public Map<String, Object> getScrollEvent(RecyclerView recyclerView, int offsetX, int offsetY){
-        offsetY = -calcContentOffset(recyclerView);
-        int contentWidth = recyclerView.getMeasuredWidth() + recyclerView.computeHorizontalScrollRange();
-        int contentHeight = calcContentSize();
-
-        Map<String, Object> event = new HashMap<>(3);
-        Map<String, Object> contentSize = new HashMap<>(3);
-        Map<String, Object> contentOffset = new HashMap<>(3);
-
-        contentSize.put(Constants.Name.WIDTH, WXViewUtils.getWebPxByWidth(contentWidth, getInstance().getInstanceViewPortWidth()));
-        contentSize.put(Constants.Name.HEIGHT, WXViewUtils.getWebPxByWidth(contentHeight, getInstance().getInstanceViewPortWidth()));
-
-        contentOffset.put(Constants.Name.X, - WXViewUtils.getWebPxByWidth(offsetX, getInstance().getInstanceViewPortWidth()));
-        contentOffset.put(Constants.Name.Y, - WXViewUtils.getWebPxByWidth(offsetY, getInstance().getInstanceViewPortWidth()));
-        event.put(Constants.Name.CONTENT_SIZE, contentSize);
-        event.put(Constants.Name.CONTENT_OFFSET, contentOffset);
-        event.put(Constants.Name.ISDRAGGING, recyclerView.getScrollState() == RecyclerView.SCROLL_STATE_DRAGGING);
-        return event;
-    }
-
-
-
-    private boolean shouldReport(int offsetX, int offsetY) {
-        if (mLastReport.x == -1 && mLastReport.y == -1) {
-            mLastReport.x = offsetX;
-            mLastReport.y = offsetY;
-            return true;
-        }
-
-        int gapX = Math.abs(mLastReport.x - offsetX);
-        int gapY = Math.abs(mLastReport.y - offsetY);
-
-        if (gapX >= mOffsetAccuracy || gapY >= mOffsetAccuracy) {
-            mLastReport.x = offsetX;
-            mLastReport.y = offsetY;
-            return true;
-        }
-
-        return false;
-    }
-
-
-    /**
-     * Setting refresh view and loading view
-     *
-     * @param child the refresh_view or loading_view
-     */
-    private boolean setRefreshOrLoading(final WXComponent child) {
-        if (child instanceof WXRefresh && getHostView() != null) {
-            getHostView().setOnRefreshListener((WXRefresh) child);
-            getHostView().postDelayed(WXThread.secure(new Runnable() {
-                @Override
-                public void run() {
-                    getHostView().setHeaderView(child);
-                }
-            }), 100);
-            return true;
-        }
-
-        if (child instanceof WXLoading && getHostView() != null) {
-            getHostView().setOnLoadingListener((WXLoading) child);
-            getHostView().postDelayed(WXThread.secure(new Runnable() {
-                @Override
-                public void run() {
-                    getHostView().setFooterView(child);
-                }
-            }), 100);
-            return true;
-        }
-        return false;
-    }
-
-
-    private void removeFooterOrHeader(WXComponent child) {
-        if (child instanceof WXLoading) {
-            getHostView().removeFooterView(child);
-        } else if (child instanceof WXRefresh) {
-            getHostView().removeHeaderView(child);
-        }
-    }
-
-    @Override
-    public ViewGroup.LayoutParams getChildLayoutParams(WXComponent child, View hostView, int width, int height, int left, int right, int top, int bottom) {
-        ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) hostView.getLayoutParams();
-        if (child instanceof WXBaseRefresh && params == null) {
-            params = new LinearLayout.LayoutParams(width, height);
-        } else if (params == null) {
-            params = new RecyclerView.LayoutParams(width, height);
-        } else {
-            params.width = width;
-            params.height = height;
-
-            this.setMarginsSupportRTL(params, left, 0, right, 0);
-        }
-        return params;
-    }
-
-
-    @Override
-    public void destroy() {
-        synchronized (this){
-            if(getHostView() != null){
-                if(mAppearChangeRunnable != null) {
-                    getHostView().removeCallbacks(mAppearChangeRunnable);
-                    mAppearChangeRunnable = null;
-                }
-                getHostView().removeCallbacks(listUpdateRunnable);
-                if(getHostView().getInnerView() != null){
-                    getHostView().getInnerView().setAdapter(null);
-                }
-            }
-            if(cellDataManager.listData != null){
-                cellDataManager.setListData(null);
-            }
-            if(mStickyHelper != null){
-                mStickyHelper = null;
-            }
-            if(mTemplateViewTypes != null){
-                mTemplateViewTypes.clear();
-            }
-            if(mTemplateSources != null){
-                mTemplateSources.clear();
-            }
-            if(mAppearHelpers != null){
-                mAppearHelpers.clear();
-            }
-            if(mDisAppearWatchList != null){
-                mDisAppearWatchList.clear();
-            }
-            super.destroy();
-        }
-    }
-
-
-
-    @Override
-    public void onViewRecycled(TemplateViewHolder holder) {}
-
-    @Override
-    public void onBindViewHolder(final TemplateViewHolder templateViewHolder, int position) {
-        if(templateViewHolder == null){
-            return;
-        }
-        WXCell component = templateViewHolder.getTemplate();
-        if(component == null){
-            return;
-        }
-        if(templateViewHolder.getHolderPosition() >= 0){
-            fireEvent(TemplateDom.DETACH_CELL_SLOT, TemplateDom.findAllComponentRefs(getRef(), position, component));
-        }
-        long start = System.currentTimeMillis();
-        templateViewHolder.setHolderPosition(position);
-        Object data = cellDataManager.listData.get(position);
-        CellRenderState cellRenderState = cellDataManager.getRenderState(position);
-        if((component.getRenderData() == data && (cellRenderState == null || !cellRenderState.isDirty()))){
-            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG){
-                WXLogUtils.d(TAG,  position + " position "+ getTemplateKey(position) + " onBindViewHolder none data update "
-                        + " component " + component.hashCode());
-            }
-            fireEvent(TemplateDom.ATTACH_CELL_SLOT, TemplateDom.findAllComponentRefs(getRef(), position, component));
-            return;  //none update just return
-        }else{
-            List<WXComponent> updates = doRenderTemplate(component, position);
-            Statements.doInitCompontent(updates);
-            component.setRenderData(data);
-            Layouts.doLayoutAsync(templateViewHolder, true);
-            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG){
-                WXLogUtils.d(TAG,  position + " position "+ getTemplateKey(position) + " onBindViewHolder used " + (System.currentTimeMillis() - start)
-                  + " component " + component.hashCode());
-            }
-        }
-    }
-
-    @Override
-    public TemplateViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
-        String template = mTemplateViewTypes.keyAt(viewType);
-        WXCell source = mTemplateSources.get(template);
-        if(source == null){
-            FrameLayout view = new FrameLayout(getContext());
-            view.setLayoutParams(new FrameLayout.LayoutParams(0, 0));
-            return new TemplateViewHolder(this, view, viewType);
-        }
-        WXCell component =  getCellTemplateFromCache(template);
-        boolean cacheHit = true;
-        if(component == null){
-            cacheHit = false;
-            if(!source.isSourceUsed()){
-                source.setSourceUsed(true);
-                renderTemplateCellWithData(source);
-                component = source;
-                if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
-                    WXLogUtils.d(TAG, template + " onCreateViewHolder source");
-                }
-            }
-        }
-        if(component == null) {
-            long start = System.currentTimeMillis();
-            component = (WXCell) copyComponentFromSourceCell(source);
-            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
-                WXLogUtils.d(TAG, template + " onCreateViewHolder copy used " + (System.currentTimeMillis() - start));
-            }
-        }
-        if(component.isLazy() || component.getHostView() == null) {
-            doCreateCellViewBindData(component, template, false);
-            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
-                WXLogUtils.d(TAG, template + " onCreateViewHolder  cache hit " + cacheHit   + " view not idle init");
-            }
-        }else{
-            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
-                WXLogUtils.d(TAG, template + " onCreateViewHolder  cache hit " + cacheHit + " view idle init " + component.hashCode()
-                 + "  " + source.hashCode());
-            }
-        }
-        TemplateViewHolder templateViewHolder = new TemplateViewHolder(this, component, viewType);
-        return  templateViewHolder;
-    }
-
-
-
-    /**
-     * @param position
-     * when template not send, return an invalid id, use empty view holder.
-     * when template has sended, use real template id to refresh view, use real view holder.
-     * */
-    @Override
-    public int getItemViewType(int position) {
-        String template = getTemplateKey(position);
-        int type =  mTemplateViewTypes.indexOfKey(template);
-        if(type < 0){
-            type = mTemplateViewTypes.indexOfKey(EMPTY_HOLDER_TEMPLATE_KEY);
-        }
-        return type;
-    }
-
-
-    /**
-     * create code context for render component and do render
-     * */
-    private List<WXComponent> doRenderTemplate(WXCell cell, int position){
-        this.cellRenderContext.clear();
-        Object item = cellDataManager.listData.get(position);
-        CellRenderState cellRenderState = cellDataManager.getRenderState(position);
-        cellRenderContext.renderState = cellRenderState;
-        cellRenderContext.templateList = this;
-        cellRenderContext.position = position;
-
-        ArrayStack stack = cellRenderContext.stack;
-        Map map = cellRenderContext.map;
-        if(cellDataManager.listData != null){
-            stack.push(map);
-            map.put(listDataKey, cellDataManager.listData);
-            if(!TextUtils.isEmpty(listDataIndexKey)) {
-                map.put(listDataIndexKey, new PositionRef(cellRenderState));
-            }
-            if(!TextUtils.isEmpty(listDataItemKey)) {
-                map.put(listDataItemKey, item);
-            }else{
-                stack.push(item);
-            }
-        }
-        if(cellRenderState.itemId <= 0){
-            getItemId(position);
-        }
-        List<WXComponent> updates = Statements.doRender(cell, this.cellRenderContext);
-        if(cellRenderState.isDirty()){
-            cellRenderState.resetDirty();
-        }
-        return  updates;
-    }
-
-    public ArrayStack copyStack(CellRenderContext context, ArrayStack stack){
-        ArrayStack onceStack = new ArrayStack();
-        for(int index=0;  index <  stack.size(); index++) {
-            Object value = stack.get(index);
-            if(value instanceof  Map){
-                value  = new HashMap((Map) value);
-            }
-            onceStack.push(value);
-        }
-        return onceStack;
-    }
-
-
-    /**
-     * return tepmlate key for position
-     * */
-    public String getTemplateKey(int position){
-        Object data =  safeGetListData(position);
-        return getTemplateKey(data);
-    }
-
-    /**
-     * return template key for position never be null
-     * */
-    public String getTemplateKey(Object data){
-        String template = null;
-        if(data instanceof  JSONObject) {
-            template = ((JSONObject)data).getString(listDataTemplateKey);
-        }
-        if(TextUtils.isEmpty(template)){
-            if(defaultTemplateCell != null){
-                template  = defaultTemplateKey;
-            }else {
-                template = "";
-            }
-        }
-        return  template;
-    }
-
-    /**
-     * get source template
-     * */
-    public WXCell getSourceTemplate(int position){
-        String template = getTemplateKey(position);
-        return mTemplateSources.get(template);
-    }
-
-
-
-    /**
-     * get template key from cell; -1 for  cann't find  type
-     * */
-    private int getCellTemplateItemType(WXCell cell){
-        if(cell == null){
-            return  -1;
-        }
-        if(cell.getAttrs() != null){
-            Object templateId = cell.getAttrs().get(Constants.Name.Recycler.SLOT_TEMPLATE_CASE);
-            String template = WXUtils.getString(templateId, null);
-            if(cell == defaultTemplateCell){
-                template = defaultTemplateKey;
-            }
-            int type =  mTemplateViewTypes.indexOfKey(template);
-            if(type < 0){
-                return -1;
-            }
-            return  type;
-        }
-        return  0;
-    }
-
-    @Override
-    public int getItemCount() {
-        if(!hasLayoutDone){
-            return 0;
-        }
-        if(!hasAppendTreeDone){
-            return 0;
-        }
-        if(cellDataManager.listData == null){
-            return  0;
-        }
-        if(mTemplateViewTypes == null || mTemplateViewTypes.size() <= 1){
-            return 0;
-        }
-        if(mTemplateSources == null || mTemplateSources.size() == 0){
-            return  0;
-        }
-        return cellDataManager.listData.size();
-    }
-
-    @Override
-    public boolean onFailedToRecycleView(TemplateViewHolder holder) {
-        return false;
-    }
-
-
-    /**
-     * @param position
-     * when template not send by javascript, return an invalid id, force  use empty view holder.
-     * when template has sended by javascript, use real template id to refresh view, use real view holder.
-     * */
-    @Override
-    public long getItemId(int position) {
-        CellRenderState renderState = cellDataManager.getRenderState(position);
-        if(renderState.itemId <=  0){
-            String template = getTemplateKey(position);
-            if(TextUtils.isEmpty(template)){
-                return RecyclerView.NO_ID;
-            }
-            Object data = safeGetListData(position);
-            if(data instanceof  JSONObject && ((JSONObject)data).containsKey("keyItemId")){
-                renderState.itemId =  ((JSONObject)data).getLongValue("keyItemId");
-            }else{
-                long id = Math.abs(data.hashCode());
-                long itemId = (id<< 24) + position;
-                renderState.itemId = itemId;
-            }
-        }
-        return renderState.itemId;
-    }
-
-    @Override
-    public void onBeforeScroll(int dx, int dy) {
-        if(mStickyHelper != null){
-            mStickyHelper.onBeforeScroll(dx, dy);
-        }
-    }
-
-    @Override
-    public void onLoadMore(int offScreenY) {
-        try {
-            String offset = getAttrs().getLoadMoreOffset();
-
-            if (TextUtils.isEmpty(offset)) {
-                offset = "0";
-            }
-            float offsetParsed = WXViewUtils.getRealPxByWidth(Integer.parseInt(offset),getInstance().getInstanceViewPortWidth());
-
-            if (offScreenY <= offsetParsed && cellDataManager.listData != null) {
-                if (mListCellCount != cellDataManager.listData.size()
-                        || mForceLoadmoreNextTime) {
-                    fireEvent(Constants.Event.LOADMORE);
-                    mListCellCount = cellDataManager.listData.size();
-                    mForceLoadmoreNextTime = false;
-                }
-            }
-        } catch (Exception e) {
-            if (WXEnvironment.isApkDebugable()){
-                WXLogUtils.d(TAG + " onLoadMore : ", e);
-            }
-        }
-    }
-
-    /**
-     *
-     * first fire appear event.
-     * */
-    @Override
-    public void notifyAppearStateChange(int firstVisible, int lastVisible, int directionX, int directionY) {
-        if(mAppearHelpers == null
-                || mAppearHelpers.size() <= 0){
-            return;
-        }
-        if(mAppearChangeRunnable != null) {
-            getHostView().removeCallbacks(mAppearChangeRunnable);
-            mAppearChangeRunnable = null;
-        }
-        String direction = directionY > 0 ? Constants.Value.DIRECTION_UP :
-                directionY < 0 ? Constants.Value.DIRECTION_DOWN : null;
-        if (getOrientation() == Constants.Orientation.HORIZONTAL && directionX != 0) {
-            direction = directionX > 0 ? Constants.Value.DIRECTION_LEFT : Constants.Value.DIRECTION_RIGHT;
-        }
-        RecyclerView recyclerView = getHostView().getInnerView();
-        for(int position=firstVisible; position<=lastVisible; position++){
-            int type = getItemViewType(position);
-            List<AppearanceHelper> helpers = mAppearHelpers.get(type);
-            if(helpers == null){
-                continue;
-            }
-            for(AppearanceHelper helper : helpers){
-                if(!helper.isWatch()){
-                    continue;
-                }
-                TemplateViewHolder itemHolder = (TemplateViewHolder) recyclerView.findViewHolderForAdapterPosition(position);
-                if(itemHolder == null || itemHolder.getComponent() == null){
-                    break;
-                }
-                List<WXComponent> childListeners = findChildListByRef(itemHolder.getComponent(), helper.getAwareChild().getRef());
-                if(childListeners == null || childListeners.size() == 0){
-                    break;
-                }
-
-                Map<String, Map<Integer, List<Object>>> disAppearList = mDisAppearWatchList.get(position);
-                if(disAppearList == null){
-                    disAppearList = new ArrayMap<>();
-                    mDisAppearWatchList.put(position, disAppearList);
-                }
-
-                Map<Integer, List<Object>> componentDisAppearList = disAppearList.get(helper.getAwareChild().getRef());
-                if(componentDisAppearList == null){
-                    componentDisAppearList = new ArrayMap<>();
-                    disAppearList.put(helper.getAwareChild().getRef(), componentDisAppearList);
-                }
-
-                for(int m=0; m<childListeners.size(); m++){
-                    WXComponent childLisener = childListeners.get(m);
-                    if(childLisener.getHostView() == null){
-                        continue;
-                    }
-                    boolean appear = helper.isViewVisible(childLisener.getHostView());
-                    int key = childLisener.getHostView().hashCode();
-                    if(appear){
-                        if(!componentDisAppearList.containsKey(key)){
-                            childLisener.notifyAppearStateChange(Constants.Event.APPEAR, direction);
-                            List<Object> eventArgs = null;
-                            if(childLisener.getEvents() != null
-                                    && childLisener.getEvents().getEventBindingArgsValues() != null
-                                    && childLisener.getEvents().getEventBindingArgsValues().get(Constants.Event.DISAPPEAR) != null){
-                                eventArgs = childLisener.getEvents().getEventBindingArgsValues().get(Constants.Event.DISAPPEAR);
-                            }
-                            componentDisAppearList.put(key, eventArgs);
-                        }
-                    }else{
-                        if(componentDisAppearList.containsKey(key)){
-                            childLisener.notifyAppearStateChange(Constants.Event.DISAPPEAR, direction);
-                            componentDisAppearList.remove(key);
-                        }
-                    }
-                }
-            }
-        }
-
-        //handle disappear event, out of position
-        int count = getItemCount();
-        for (int position=0; position<count; position++){
-            if(position >= firstVisible && position <= lastVisible){
-                position = lastVisible + 1;
-                continue;
-            }
-            Map<String, Map<Integer, List<Object>>> map = mDisAppearWatchList.get(position);
-            if(map == null){
-                continue;
-            }
-            WXCell template = mTemplateSources.get(getTemplateKey(position));
-            if(template == null){
-                return;
-            }
-            Set<Map.Entry<String, Map<Integer, List<Object>>>> cellWatcherEntries = map.entrySet();
-            for(Map.Entry<String,Map<Integer, List<Object>>> cellWatcherEntry : cellWatcherEntries){
-                String ref = cellWatcherEntry.getKey();
-                WXComponent component = findChildByRef(template, ref);
-                if(component == null){
-                    continue;
-                }
-                Map<Integer, List<Object>> eventWatchers = cellWatcherEntry.getValue();
-                if(eventWatchers == null || eventWatchers.size() == 0){
-                    continue;
-                }
-                WXEvent events = component.getEvents();
-                Set<Map.Entry<Integer, List<Object>>> eventWatcherEntries = eventWatchers.entrySet();
-                for(Map.Entry<Integer, List<Object>> eventWatcherEntry : eventWatcherEntries){
-                    events.putEventBindingArgsValue(Constants.Event.DISAPPEAR, eventWatcherEntry.getValue());
-                    component.notifyAppearStateChange(Constants.Event.DISAPPEAR, direction);
-                }
-                eventWatchers.clear();
-            }
-            mDisAppearWatchList.remove(position);
-        }
-    }
-
-
-    private Object safeGetListData(int position){
-        try{
-            return cellDataManager.listData.get(position);
-        }catch (Exception e){return  JSONObject.parseObject("{}");}
-    }
-
-    public void  notifyUpdateList(){
-        if(getHostView() == null
-                || getHostView().getInnerView() == null
-                || listUpdateRunnable == null){
-            return;
-        }
-        if(Looper.getMainLooper().getThread().getId() != Thread.currentThread().getId()){
-            getHostView().removeCallbacks(listUpdateRunnable);
-            getHostView().post(listUpdateRunnable);
-        }else{
-            listUpdateRunnable.run();
-        }
-    }
-
-    private int calcContentSize() {
-        int totalHeight = 0;
-        if(cellDataManager.listData == null){
-            return totalHeight;
-        }
-        for (int i = 0; i < cellDataManager.listData.size(); i++) {
-            WXCell child = getSourceTemplate(i);
-            if (child != null) {
-                totalHeight += child.getLayoutHeight();
-            }
-        }
-        return totalHeight;
-    }
-
-    public int calcContentOffset(RecyclerView recyclerView) {
-        RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
-        if (layoutManager instanceof LinearLayoutManager) {
-            int firstVisibleItemPosition = ((LinearLayoutManager) layoutManager).findFirstVisibleItemPosition();
-            int offset = 0;
-            for (int i=0;i<firstVisibleItemPosition;i++) {
-                WXCell cell = getSourceTemplate(i);
-                if(cell == null){
-                    continue;
-                }
-                offset -= cell.getLayoutHeight();
-            }
-
-            if (layoutManager instanceof GridLayoutManager) {
-                int spanCount = ((GridLayoutManager) layoutManager).getSpanCount();
-                offset = offset / spanCount;
-            }
-            View firstVisibleView = layoutManager.findViewByPosition(firstVisibleItemPosition);
-            if(firstVisibleView != null) {
-                offset += firstVisibleView.getTop();
-            }
-            return offset;
-        } else if (layoutManager instanceof StaggeredGridLayoutManager) {
-            int spanCount = ((StaggeredGridLayoutManager) layoutManager).getSpanCount();
-            int firstVisibleItemPosition = ((StaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(null)[0];
-            int offset = 0;
-            for (int i=0;i<firstVisibleItemPosition;i++) {
-                WXCell cell = getSourceTemplate(i);
-                if(cell == null){
-                    continue;
-                }
-                offset -= cell.getLayoutHeight();
-            }
-            offset = offset / spanCount;
-
-            View firstVisibleView = layoutManager.findViewByPosition(firstVisibleItemPosition);
-            if(firstVisibleView != null) {
-                offset += firstVisibleView.getTop();
-            }
-            return offset;
-        }
-        return -1;
-    }
-
-    /**
-     * find certain class type parent
-     * */
-    public WXComponent findParentType(WXComponent component, Class type){
-        if(type.isAssignableFrom(component.getClass())){
-            return component;
-        }
-        if(component.getParent() != null) {
-            findTypeParent(component.getParent(), type);
-        }
-        return  null;
-    }
-
-
-    /**
-     * find child by ref
-     * */
-    public WXComponent findChildByRef(WXComponent component, String ref){
-        if(ref.equals(component.getRef())){
-            return component;
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            for(int i=0; i<container.getChildCount(); i++){
-                WXComponent child = findChildByRef(container.getChild(i), ref);
-                if(child != null){
-                    return  child;
-                }
-            }
-        }
-        return  null;
-    }
-
-    /**
-     * find child list, has same ref
-     * */
-    public List<WXComponent> findChildListByRef(WXComponent component, String ref){
-        WXComponent child = findChildByRef(component, ref);
-        if(child == null){
-            return  null;
-        }
-        List<WXComponent> componentList = new ArrayList<>();
-        WXVContainer container = child.getParent();
-        if(container != null && (!(container instanceof WXRecyclerTemplateList))){
-            for(int i=0; i<container.getChildCount(); i++){
-                WXComponent element = container.getChild(i);
-                if(ref.equals(element.getRef())){
-                    componentList.add(element);
-                }
-            }
-        }else{
-            componentList.add(child);
-        }
-        return  componentList;
-    }
-
-
-
-    /**
-     * find child by ref
-     * */
-    public WXComponent findChildByAttrsRef(WXComponent component, String ref){
-        if(component.getAttrs() != null && ref.equals(component.getAttrs().get(TemplateDom.ATTRS_KEY_REF))){
-            return component;
-        }
-        if(component instanceof WXVContainer){
-            WXVContainer container = (WXVContainer) component;
-            for(int i=0; i<container.getChildCount(); i++){
-                WXComponent child = findChildByAttrsRef(container.getChild(i), ref);
-                if(child != null){
-                    return  child;
-                }
-            }
-        }
-        return  null;
-    }
-
-
-
-    /**
-     * @param  template  template name
-     * get cell template component from cache, if cell component not load
-     * start load cell template
-     * */
-    private WXCell getCellTemplateFromCache(final String template){
-        TemplateCache cache = mTemplatesCache.get(template);
-        WXCell component =  null;
-        if(cache != null && cache.cells != null && cache.cells.size() > 0){
-            component = cache.cells.poll();
-        }
-        if(cache == null ||  !cache.isLoadIng){
-            if(cache == null){
-                cache = new TemplateCache();
-                mTemplatesCache.put(template, cache);
-            }
-            cache.isLoadIng = true;
-            WXCell source = mTemplateSources.get(template);
-            if(source != null){
-                boolean allowPreload = WXUtils.getBoolean(source.getAttrs().get("preload"), true);
-                if(allowPreload) {
-                    AsyncCellLoadTask asyncCellLoadTask = new AsyncCellLoadTask(template, source, this);
-                    asyncCellLoadTask.startTask();
-                }
-            }
-        }
-        return  component;
-    }
-
-    /**
-     * copy cell component from source, init render data, and return source
-     * if none data, return null
-     * */
-    public WXComponent copyComponentFromSourceCell(WXCell cell){
-        renderTemplateCellWithData(cell);
-        WXCell component = (WXCell) Statements.copyComponentTree(cell);
-        return component;
-    }
-
-    /**
-     *  render  init with  cell with one data,
-     *  if template has already render with data, done nothing
-     *  @param  cell
-     * */
-    private synchronized void renderTemplateCellWithData(WXCell cell){
-        if(cell.getRenderData() == null){
-            if(cellDataManager.listData != null && cellDataManager.listData.size() > 0){
-                synchronized (this){
-                    if(cell.getRenderData() == null){
-                        Statements.parseStatementsToken(cell);
-                        for(int i = 0; i< cellDataManager.listData.size(); i++){
-                            if(cell == getSourceTemplate(i)){
-                                Object data = cellDataManager.listData.get(i);
-                                doRenderTemplate(cell, i);
-                                Layouts.doLayoutSync(cell, getLayoutWidth(), getLayoutHeight());
-                                cell.setRenderData(data);
-                                break;
-                            }
-                        }
-                    }
-                }
-            }
-        }
-    }
-
-
-    /**
-     * create view for lazy cell and bind data
-     * */
-    public static void doCreateCellViewBindData(WXCell component, String template, boolean inPreload){
-        if(component.isLazy() || component.getHostView() == null){
-            long start = System.currentTimeMillis();
-            Statements.initLazyComponent(component, null);
-            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
-                WXLogUtils.d(TAG, " doCreateCellViewBindData " + template + " in preload "+ inPreload + " used " + (System.currentTimeMillis() - start));
-            }
-        }
-    }
-
-    public ScrollStartEndHelper getScrollStartEndHelper() {
-        if(mScrollStartEndHelper == null){
-            mScrollStartEndHelper = new ScrollStartEndHelper(this);
-        }
-        return mScrollStartEndHelper;
-    }
-
-    public int getTemplateCacheSize() {
-        return templateCacheSize;
-    }
-
-    public ConcurrentHashMap<String, TemplateCache> getTemplatesCache() {
-        if(mTemplatesCache == null){
-            mTemplatesCache = new ConcurrentHashMap<>();
-        }
-        return mTemplatesCache;
-    }
-
-
-    public CellDataManager getCellDataManager() {
-        return cellDataManager;
-    }
-
-
-    private JSONArray parseListDataToJSONArray(Object value){
-        try{
-            if(value instanceof  JSONArray){
-                return (JSONArray) value;
-            }
-            if(value instanceof String){
-                JSONArray array = JSONArray.parseArray(getAttrs().get(Constants.Name.Recycler.LIST_DATA).toString());
-                return array;
-            }
-        }catch (Exception e){
-            WXLogUtils.e(TAG, "parseListDataException" + e.getMessage());
-        }
-        return new JSONArray();
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/jni/NativeRenderLayoutDirection.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/jni/NativeRenderLayoutDirection.java
deleted file mode 100644
index 443dcf6..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/jni/NativeRenderLayoutDirection.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template.jni;
-
-public class NativeRenderLayoutDirection {
-    public static final int inherit = 0;
-    public static final int ltr = 1;
-    public static final int rtl = 2;
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/jni/NativeRenderObjectUtils.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/jni/NativeRenderObjectUtils.java
deleted file mode 100644
index 12f125a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/list/template/jni/NativeRenderObjectUtils.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list.template.jni;
-
-import android.util.Log;
-
-import com.taobao.weex.base.CalledByNative;
-import com.taobao.weex.ui.component.WXComponent;
-
-/**
- * Created by furture on 2018/5/3.
- */
-
-public class NativeRenderObjectUtils {
-
-
-    /**
-     * getRenderObject
-     * */
-    public static native long nativeGetRenderObject(String instanceId, String ref);
-
-    /**
-     * render object layout
-     * */
-    public static native void nativeUpdateRenderObjectStyle(long ptr, String key, String value);
-    public static native void nativeUpdateRenderObjectAttr(long ptr, String key, String value);
-
-    /**
-     * copy render object
-     * */
-    public static native long nativeCopyRenderObject(long ptr);
-
-    /**
-     * layout render object
-     * */
-    public static native int nativeLayoutRenderObject(long ptr, float width, float height);
-
-    public static native int nativeRenderObjectGetLayoutDirectionFromPathNode(long ptr);
-    /**
-     * get child length
-     * */
-    public static native void nativeAddChildRenderObject(long parent, long child);
-
-    /**
-     * get component, tranverse child and update component
-     * */
-    public static native boolean nativeRenderObjectHasNewLayout(long ptr);
-    public static native int nativeRenderObjectChildCount(long ptr);
-    public static native long nativeRenderObjectGetChild(long ptr, int index);
-    public static native void nativeRenderObjectUpdateComponent(long ptr, WXComponent component);
-    public static native void nativeRenderObjectChildWaste(long ptr, boolean waster);
-
-
-    /**
-     * component size
-     * */
-    @CalledByNative
-    public static void updateComponentSize(WXComponent component, float top, float bottom, float left, float right, float height, float width){
-        component.updateDemission(top, bottom, left, right, height, width);
-        component.applyLayoutOnly();
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/OnActivePseudoListner.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/OnActivePseudoListner.java
deleted file mode 100644
index 961e3b8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/OnActivePseudoListner.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.pesudo;
-
-/**
- * Created by sospartan on 05/01/2017.
- */
-public interface OnActivePseudoListner {
-  void updateActivePseudo(boolean isSet);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/PesudoStatus.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/PesudoStatus.java
deleted file mode 100644
index 04e5fee..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/PesudoStatus.java
+++ /dev/null
@@ -1,131 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.pesudo;
-
-import android.support.annotation.Nullable;
-import android.support.v4.util.ArrayMap;
-
-import com.taobao.weex.common.Constants;
-
-import java.util.Map;
-
-/**
- * Created by sospartan on 05/01/2017.
- */
-
-public class PesudoStatus {
-
-  /**
-   * See {@link Constants.PSEUDO}
-   */
-  private int[] mStatuses = new int[4];
-
-  private static final int UNSET = 0;
-  private static final int SET = 1;
-
-  static final int CLASS_ACTIVE = 0;
-  static final int CLASS_FOCUS = 1;
-  static final int CLASS_ENABLED = 2;
-  static final int CLASS_DISABLED = 3;
-
-  public PesudoStatus(){
-    for (int i = 0; i < mStatuses.length; i++) {
-        mStatuses[i] = UNSET;
-    }
-  }
-
-  /**
-   *
-   * @param clzName See {@link Constants.PSEUDO}
-   * @param status
-   */
-  public void setStatus(String clzName,boolean status){
-    switch (clzName){
-      case Constants.PSEUDO.ACTIVE:
-        setStatus(PesudoStatus.CLASS_ACTIVE,status);
-        break;
-      case Constants.PSEUDO.DISABLED:
-        setStatus(PesudoStatus.CLASS_DISABLED,status);
-        break;
-      case Constants.PSEUDO.ENABLED:
-        setStatus(PesudoStatus.CLASS_ENABLED,status);
-        break;
-      case Constants.PSEUDO.FOCUS:
-        setStatus(PesudoStatus.CLASS_FOCUS,status);
-        break;
-    }
-  }
-
-  void setStatus(int clz,boolean status){
-    mStatuses[clz] = status?SET:UNSET;
-  }
-
-  public boolean isSet(int clz){
-    return mStatuses[clz] == SET;
-  }
-
-  public @Nullable String getStatuses(){
-    StringBuilder sb = new StringBuilder();
-    if(isSet(CLASS_ACTIVE)){
-      sb.append(Constants.PSEUDO.ACTIVE);
-    }
-    if(isSet(CLASS_DISABLED)){
-      sb.append(Constants.PSEUDO.DISABLED);
-    }
-    //enabled is ignored
-
-    if(isSet(CLASS_FOCUS) && !isSet(CLASS_DISABLED)){
-      sb.append(Constants.PSEUDO.FOCUS);
-    }
-    return sb.length()==0?null:sb.toString();
-  }
-
-  public Map<String,Object> updateStatusAndGetUpdateStyles(String clzName,
-                                                           boolean status,
-                                                           Map<String, Map<String,Object>> pesudoStyles,
-                                                           Map<String,Object> originalStyles){
-    String prevStatusesStr = getStatuses();//before change
-    setStatus(clzName,status);
-    String statusesStr = getStatuses();//after change
-
-    Map<String,Object> updateStyles = pesudoStyles.get(statusesStr);
-    Map<String,Object> prevUpdateStyles = pesudoStyles.get(prevStatusesStr);
-
-    /**
-     * NEW INSTANCE, DO NOT USE MAP OBJECT FROM pesudoStyles
-     */
-    Map<String,Object> resultStyles = new ArrayMap<>();
-    if(prevUpdateStyles != null){
-      resultStyles.putAll(prevUpdateStyles);
-    }
-
-    //reset
-    for (String key : resultStyles.keySet()) {
-      resultStyles.put(key, originalStyles.containsKey(key) ? originalStyles.get(key) : "");
-    }
-
-    //apply new update
-    if(updateStyles != null) {
-      for (Map.Entry<String, Object> entry : updateStyles.entrySet()) {
-        resultStyles.put(entry.getKey(), entry.getValue());
-      }
-    }
-    return resultStyles;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/TouchActivePseudoListener.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/TouchActivePseudoListener.java
deleted file mode 100644
index 1834675..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/pesudo/TouchActivePseudoListener.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.pesudo;
-
-import android.annotation.SuppressLint;
-import android.view.MotionEvent;
-import android.view.View;
-
-/**
- * Created by sospartan on 05/01/2017.
- */
-public class TouchActivePseudoListener implements View.OnTouchListener {
-  private OnActivePseudoListner mOnActivePseudoListner;
-  private boolean mIsConsumeOnTouch;
-
-  public TouchActivePseudoListener(OnActivePseudoListner l, boolean consumeInTouch) {
-    mOnActivePseudoListner = l;
-    mIsConsumeOnTouch = consumeInTouch;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouch(View v, MotionEvent event) {
-    int action = event.getAction();
-    if (mOnActivePseudoListner != null) {
-      if (action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_POINTER_DOWN) {
-        mOnActivePseudoListner.updateActivePseudo(true);
-      } else if (action == MotionEvent.ACTION_CANCEL || action == MotionEvent.ACTION_UP || action == MotionEvent.ACTION_POINTER_UP) {
-        mOnActivePseudoListner.updateActivePseudo(false);
-      }
-    }
-    return mIsConsumeOnTouch;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/WXRichText.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/WXRichText.java
deleted file mode 100755
index 06357a6..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/WXRichText.java
+++ /dev/null
@@ -1,159 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext;
-
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.text.Spannable;
-import android.text.SpannableStringBuilder;
-import android.text.Spanned;
-import android.text.SpannedString;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.layout.measurefunc.TextContentBoxMeasurement;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXText;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.component.richtext.node.RichTextNode;
-import com.taobao.weex.ui.component.richtext.node.RichTextNodeManager;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-
-public class WXRichText extends WXText {
-  private List<RichTextNode> nodes = new LinkedList<>();
-
-  static class RichTextContentBoxMeasurement extends TextContentBoxMeasurement {
-
-    public RichTextContentBoxMeasurement(WXComponent component) {
-      super(component);
-    }
-
-    @NonNull
-    @Override
-    protected Spanned createSpanned(String text) {
-      if(!TextUtils.isEmpty(text)) {
-        if (mComponent.getInstance() != null & mComponent.getInstance().getUIContext() != null &&
-                !TextUtils.isEmpty(mComponent.getInstanceId())) {
-          Spannable spannable = RichTextNode.parse(
-                  mComponent.getInstance().getUIContext(),
-                  mComponent.getInstanceId(),
-                  mComponent.getRef(),
-                  text);
-          updateSpannable(spannable, RichTextNode.createSpanFlag(0));
-          return spannable;
-        } else {
-          return new SpannedString("");
-        }
-      }
-      else {
-        Spannable spannable = ((WXRichText)mComponent).toSpan();
-        updateSpannable(spannable, RichTextNode.createSpanFlag(0));
-        return spannable;
-        }
-    }
-  }
-
-  public static class Creator implements ComponentCreator {
-
-    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-      return new WXRichText(instance, parent, basicComponentData);
-    }
-  }
-
-  public WXRichText(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-    setContentBoxMeasurement(new RichTextContentBoxMeasurement(this));
-  }
-  public void AddChildNode(String ref, String nodeType,String parentRef, Map<String,String> styles,Map<String,String> attrs) {
-    if(getInstance() != null && getInstance().getUIContext() != null && !TextUtils.isEmpty(getInstanceId()) &&
-            !TextUtils.isEmpty(ref) && !TextUtils.isEmpty(nodeType)) {
-      RichTextNode child = RichTextNodeManager.createRichTextNode(getInstance().getUIContext(), getInstanceId(), getRef(), ref, nodeType, styles, attrs);
-      if (TextUtils.isEmpty(parentRef)) {
-        nodes.add(child);
-      } else {
-        RichTextNode parent = findRichNode(parentRef);
-        if (parent != null) {
-          parent.addChildNode(child);
-        }
-      }
-    }
-  }
-  private Spannable toSpan(){
-    SpannableStringBuilder spannableStringBuilder = new SpannableStringBuilder();
-    if(nodes != null && !nodes.isEmpty()){
-      for(RichTextNode node:nodes){
-        spannableStringBuilder.append(node.toSpan(1));
-      }
-    }
-    return spannableStringBuilder;
-  }
-
-  public void removeChildNode(String parentRef,String ref) {
-    if (nodes != null && !nodes.isEmpty()) {
-      if (parentRef.equals("")) {
-        for (RichTextNode node : nodes) {
-          if (TextUtils.equals(node.getRef(), ref)) {
-            nodes.remove(node);
-          }
-        }
-      } else {
-        RichTextNode parent = findRichNode(parentRef);
-        if (parent != null) {
-          parent.removeChildNode(ref);
-        }
-      }
-    }
-  }
-  public void updateChildNodeStyles(String ref,Map<String,Object> styles){
-    RichTextNode node = findRichNode(ref);
-    if(node != null){
-      node.updateStyles(styles);
-    }
-  }
-  public void updateChildNodeAttrs(String ref,Map<String,Object> attrs){
-    RichTextNode node = findRichNode(ref);
-    if(node != null){
-      node.updateAttrs(attrs);
-    }
-  }
-  private RichTextNode findRichNode(String ref){
-    if(!TextUtils.isEmpty(ref)) {
-      RichTextNode theNode;
-      if (nodes != null && !nodes.isEmpty()) {
-        for (RichTextNode node : nodes) {
-          if ((theNode = node.findRichNode(ref)) != null)
-            return theNode;
-        }
-      }
-    }
-    return null;
-  }
-
-  @Override
-  protected WXRichTextView initComponentHostView(@NonNull Context context) {
-    return new WXRichTextView(context);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/WXRichTextView.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/WXRichTextView.java
deleted file mode 100644
index 4605201..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/WXRichTextView.java
+++ /dev/null
@@ -1,116 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.graphics.drawable.Drawable;
-import android.text.Layout;
-import android.text.Selection;
-import android.text.Spannable;
-import android.text.Spanned;
-import android.text.style.ClickableSpan;
-import android.view.MotionEvent;
-import android.widget.TextView;
-
-import com.taobao.weex.ui.component.richtext.span.ImgSpan;
-import com.taobao.weex.ui.view.WXTextView;
-
-public class WXRichTextView extends WXTextView {
-
-  public WXRichTextView(Context context) {
-    super(context);
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent event) {
-    boolean superResult = super.onTouchEvent(event);
-    boolean handled = false;
-    if (isEnabled() && getTextLayout() != null && getText() instanceof Spannable) {
-      Spannable spannable = (Spannable) getText();
-      handled = updateSelection(event, spannable);
-    }
-    return handled || superResult;
-  }
-
-  @Override
-  protected boolean verifyDrawable(Drawable who) {
-    super.verifyDrawable(who);
-    return true;
-  }
-
-  @Override
-  public void setTextLayout(Layout layout) {
-    super.setTextLayout(layout);
-    if (layout.getText() instanceof Spanned) {
-      Spanned spanned = (Spanned) layout.getText();
-      ImgSpan[] imgSpan = spanned.getSpans(0, spanned.length(), ImgSpan.class);
-      if (imgSpan != null) {
-        for (ImgSpan span : imgSpan) {
-          span.setView(this);
-        }
-      }
-    }
-  }
-
-  /**
-   * Mostly copied from
-   * {@link android.text.method.LinkMovementMethod#onTouchEvent(TextView, Spannable, MotionEvent)}.
-   */
-  private boolean updateSelection(MotionEvent event, Spannable buffer) {
-    int action = event.getActionMasked();
-
-    if (action == MotionEvent.ACTION_UP ||
-        action == MotionEvent.ACTION_DOWN) {
-      int x = (int) event.getX();
-      int y = (int) event.getY();
-
-      x -= getPaddingLeft();
-      y -= getPaddingTop();
-
-      x += getScrollX();
-      y += getScrollY();
-
-      Layout layout = getTextLayout();
-      int line = layout.getLineForVertical(y);
-      int off = layout.getOffsetForHorizontal(line, x);
-
-      ClickableSpan[] link = buffer.getSpans(off, off, ClickableSpan.class);
-
-      if (link.length != 0) {
-        if (action == MotionEvent.ACTION_UP) {
-          link[0].onClick(this);
-        } else {
-          Selection.setSelection(buffer,
-                                 buffer.getSpanStart(link[0]),
-                                 buffer.getSpanEnd(link[0]));
-        }
-
-        return true;
-      } else {
-        Selection.removeSelection(buffer);
-      }
-    }
-
-    return false;
-  }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/ANode.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/ANode.java
deleted file mode 100755
index b657188..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/ANode.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.node;
-
-import android.content.Context;
-import android.support.v4.util.ArrayMap;
-import android.text.SpannableStringBuilder;
-
-import com.taobao.weex.ui.component.richtext.span.ASpan;
-import com.taobao.weex.ui.component.richtext.span.ItemClickSpan;
-
-import java.util.ArrayList;
-import java.util.Map;
-
-class ANode extends RichTextNode {
-
-  static class ANodeCreator implements RichTextNodeCreator<ANode> {
-
-    @Override
-    public ANode createRichTextNode(Context context, String instanceId, String componentRef) {
-      return new ANode(context, instanceId, componentRef);
-    }
-    @Override
-    public ANode createRichTextNode(Context context,String instanceId,String componentRef,String ref,
-                                      Map<String,Object> styles, Map<String,Object> attrs){
-      return new ANode(context,instanceId,componentRef,ref,styles,attrs);
-    }
-
-  }
-
-  public static final String NODE_TYPE = "a";
-  public static final String HREF = "href";
-
-  private ANode(Context context, String instanceId, String componentRef) {
-    super(context, instanceId, componentRef);
-  }
-  private ANode(Context context, String instanceId, String componentRef, String ref, Map<String,Object> styles, Map<String,Object> attrs) {
-    super(context, instanceId, componentRef, ref, styles, attrs);
-  }
-
-  @Override
-  public String toString() {
-    return "";
-  }
-
-  @Override
-  protected boolean isInternalNode() {
-    return true;
-  }
-
-  @Override
-  protected void updateSpans(SpannableStringBuilder spannableStringBuilder, int level) {
-    super.updateSpans(spannableStringBuilder, level);
-      if (attr != null && attr.containsKey(RichTextNode.PSEUDO_REF)) {
-          ItemClickSpan itemClickSpan = new ItemClickSpan(mInstanceId, mComponentRef, attr.get(RichTextNode.PSEUDO_REF).toString());
-          spannableStringBuilder.setSpan(itemClickSpan, 0, spannableStringBuilder.length(),
-                  createSpanFlag(level));
-      } else if (attr != null && attr.containsKey(HREF)) {
-          ASpan aSpan = new ASpan(mInstanceId, attr.get(HREF).toString());
-          spannableStringBuilder.setSpan(aSpan, 0, spannableStringBuilder.length(),
-                  createSpanFlag(level));
-      }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/ImgNode.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/ImgNode.java
deleted file mode 100755
index 69f66ee..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/ImgNode.java
+++ /dev/null
@@ -1,123 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.node;
-
-import static com.taobao.weex.utils.WXViewUtils.getRealPxByWidth;
-
-import android.content.Context;
-import android.graphics.drawable.Drawable;
-import android.net.Uri;
-import android.support.annotation.NonNull;
-import android.support.v4.util.ArrayMap;
-import android.text.SpannableStringBuilder;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.DrawableStrategy;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.component.richtext.span.ImgSpan;
-import com.taobao.weex.ui.component.richtext.span.ItemClickSpan;
-import com.taobao.weex.utils.ImgURIUtil;
-import com.taobao.weex.utils.WXUtils;
-
-import java.util.ArrayList;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-
-class ImgNode extends RichTextNode {
-
-  static class ImgNodeCreator implements RichTextNodeCreator<ImgNode> {
-
-    @Override
-    public ImgNode createRichTextNode(Context context, String instanceId, String componentRef) {
-      return new ImgNode(context, instanceId, componentRef);
-    }
-    @Override
-    public ImgNode createRichTextNode(Context context,String instanceId,String componentRef,String ref,
-                                       Map<String,Object> styles, Map<String,Object> attrs){
-      return new ImgNode(context,instanceId,componentRef,ref,styles,attrs);
-    }
-  }
-
-  public static final String NODE_TYPE = "image";
-
-  private ImgNode(Context context, String instanceId, String componentRef) {
-    super(context, instanceId, componentRef);
-  }
-  private ImgNode(Context context, String instanceId, String componentRef, String ref, Map<String,Object> styles, Map<String,Object> attrs) {
-    super(context, instanceId, componentRef, ref, styles, attrs);
-  }
-
-  @Override
-  public String toString() {
-    return "\uFEFF";
-  }
-
-  @Override
-  protected boolean isInternalNode() {
-    return false;
-  }
-
-  @Override
-  protected void updateSpans(SpannableStringBuilder spannableStringBuilder, int level) {
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
-    if (WXSDKEngine.getDrawableLoader() != null &&
-        style.containsKey(Constants.Name.WIDTH) &&
-        style.containsKey(Constants.Name.HEIGHT) &&
-        attr.containsKey(Constants.Name.SRC) &&
-        instance != null) {
-      List<Object> spans = new LinkedList<>();
-      spans.add(createImgSpan(instance));
-
-      if (attr.containsKey(RichTextNode.PSEUDO_REF)) {
-        spans.add(new ItemClickSpan(mInstanceId, mComponentRef,
-            attr.get(RichTextNode.PSEUDO_REF).toString()));
-      }
-
-      for (Object span : spans) {
-        spannableStringBuilder.setSpan(
-            span, 0, spannableStringBuilder.length(), createSpanFlag(level));
-      }
-    }
-  }
-
-  @NonNull
-  private ImgSpan createImgSpan(WXSDKInstance instance) {
-    int width = (int) getRealPxByWidth(WXUtils.getFloat(style.get(Constants.Name.WIDTH)),
-        instance.getInstanceViewPortWidth());
-    int height = (int) getRealPxByWidth(WXUtils.getFloat(style.get(Constants.Name.HEIGHT)),
-        instance.getInstanceViewPortWidth());
-    ImgSpan imageSpan = new ImgSpan(width, height);
-
-    String url = attr.get(Constants.Name.SRC).toString();
-    Uri rewrited = instance.rewriteUri(Uri.parse(url), URIAdapter.IMAGE);
-    if (Constants.Scheme.LOCAL.equals(rewrited.getScheme())) {
-      Drawable localDrawable = ImgURIUtil.getDrawableFromLoaclSrc(mContext, rewrited);
-      imageSpan.setDrawable(localDrawable, false);
-    } else {
-      DrawableStrategy drawableStrategy = new DrawableStrategy();
-      drawableStrategy.width = width;
-      drawableStrategy.height = height;
-      WXSDKEngine.getDrawableLoader().setDrawable(rewrited.toString(), imageSpan, drawableStrategy);
-    }
-    return imageSpan;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNode.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNode.java
deleted file mode 100755
index 036940b..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNode.java
+++ /dev/null
@@ -1,291 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.node;
-
-import static com.taobao.weex.dom.WXStyle.UNSET;
-
-import android.content.Context;
-import android.graphics.Color;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v4.util.ArrayMap;
-import android.text.Spannable;
-import android.text.SpannableString;
-import android.text.SpannableStringBuilder;
-import android.text.Spanned;
-import android.text.TextUtils;
-import android.text.style.AbsoluteSizeSpan;
-import android.text.style.BackgroundColorSpan;
-import android.text.style.ForegroundColorSpan;
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.WXCustomStyleSpan;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXResourceUtils;
-import java.util.ArrayList;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-
-public abstract class RichTextNode {
-
-    public static final String TYPE = "type";
-    public static final String STYLE = "style";
-    public static final String ATTR = "attr";
-    public static final String CHILDREN = "children";
-    public static final String VALUE = Constants.Name.VALUE;
-    public static final String ITEM_CLICK="itemclick";
-    public static final String PSEUDO_REF="pseudoRef";
-    private static final int MAX_LEVEL = Spanned.SPAN_PRIORITY >> Spanned.SPAN_PRIORITY_SHIFT;
-
-    protected final Context mContext;
-    protected final String mInstanceId;
-    protected final String mComponentRef;
-    protected final String mRef;
-    protected Map<String, Object> style;
-    protected Map<String, Object> attr;
-    protected List<RichTextNode> children;
-
-    protected RichTextNode(Context context, String instanceId, String componentRef) {
-        mContext = context;
-        mInstanceId = instanceId;
-        mComponentRef = componentRef;
-        mRef = null;
-    }
-    protected RichTextNode(Context context, String instanceId, String componentRef, String ref, Map<String,Object> styles, Map<String,Object> attrs) {
-        mContext = context;
-        mInstanceId = instanceId;
-        mComponentRef = componentRef;
-        mRef = ref;
-        if(styles != null){
-            style = styles;
-        }
-        else {
-            style = new ArrayMap<>(0);
-        }
-        if (attrs != null) {
-            attr = attrs;
-        } else {
-            attr = new ArrayMap<>(0);
-        }
-        children = new LinkedList<>();
-    }
-
-    public static
-    @NonNull
-    Spannable parse(@NonNull Context context, @NonNull String instanceId, @NonNull String componentRef, String json) {
-        JSONArray jsonArray = JSON.parseArray(json);
-        JSONObject jsonObject;
-        List<RichTextNode> nodes;
-        RichTextNode node;
-        if (jsonArray != null && !jsonArray.isEmpty()) {
-            nodes = new ArrayList<>(jsonArray.size());
-            for (int i = 0; i < jsonArray.size(); i++) {
-                jsonObject = jsonArray.getJSONObject(i);
-                if (jsonObject != null) {
-                    node = RichTextNodeManager.createRichTextNode(context, instanceId, componentRef, jsonObject);
-                    if (node != null) {
-                        nodes.add(node);
-                    }
-                }
-            }
-            return parse(nodes);
-        }
-        return new SpannableString("");
-    }
-
-    public static int createSpanFlag(int level) {
-        return createPriorityFlag(level) | Spanned.SPAN_INCLUSIVE_EXCLUSIVE;
-    }
-
-    @Override
-    public abstract String toString();
-
-    protected abstract boolean isInternalNode();
-
-    public String getRef(){
-        return mRef;
-    }
-
-    final void parse(@NonNull Context context, @NonNull String instanceId, @NonNull String componentRef, JSONObject jsonObject) {
-        JSONObject jsonStyle, jsonAttr, child;
-        JSONArray jsonChildren;
-        RichTextNode node;
-        if ((jsonStyle = jsonObject.getJSONObject(STYLE)) != null) {
-            style = new ArrayMap<>();
-            style.putAll(jsonStyle);
-        } else {
-            style = new ArrayMap<>(0);
-        }
-
-        if ((jsonAttr = jsonObject.getJSONObject(ATTR)) != null) {
-            attr = new ArrayMap<>(jsonAttr.size());
-            attr.putAll(jsonAttr);
-        } else {
-            attr = new ArrayMap<>(0);
-        }
-
-        if ((jsonChildren=jsonObject.getJSONArray(CHILDREN))!=null) {
-            children = new ArrayList<>(jsonChildren.size());
-            for (int i = 0; i < jsonChildren.size(); i++) {
-                child = jsonChildren.getJSONObject(i);
-                node = RichTextNodeManager.createRichTextNode(context, instanceId, componentRef, child);
-                if (node != null) {
-                    children.add(node);
-                }
-            }
-        } else {
-            children = new ArrayList<>(0);
-        }
-    }
-    public void addChildNode(RichTextNode child){
-        if(children == null){
-            children = new LinkedList<>();
-        }
-        if(child != null && isInternalNode()){
-            children.add(child);
-        }
-    }
-    public void removeChildNode(String ref){
-        if(children != null && !children.isEmpty() && !TextUtils.isEmpty(ref)){
-            try {
-                for (RichTextNode child : children) {
-                    if (TextUtils.equals(child.mRef, ref)) {
-                        children.remove(child);
-                    }
-                }
-            }catch(Exception e){
-                WXLogUtils.getStackTrace(e);
-            }
-        }
-    }
-    public void updateStyles(Map<String,Object> styles){
-        if(styles != null && !styles.isEmpty()){
-            style.putAll(styles);
-        }
-    }
-    public void updateAttrs(Map<String,Object> attrs){
-        if(attr != null && !attrs.isEmpty()){
-            attr.putAll(attrs);
-        }
-    }
-
-    protected void updateSpans(SpannableStringBuilder spannableStringBuilder, int level) {
-        WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
-        if (style != null && instance != null) {
-            List<Object> spans = new LinkedList<>();
-
-            WXCustomStyleSpan customStyleSpan = createCustomStyleSpan();
-            if (customStyleSpan != null) {
-                spans.add(customStyleSpan);
-            }
-
-            if (style.containsKey(Constants.Name.FONT_SIZE)) {
-                spans.add(new AbsoluteSizeSpan(WXStyle.getFontSize(style, instance.getInstanceViewPortWidth())));
-            }
-
-            if (style.containsKey(Constants.Name.BACKGROUND_COLOR)) {
-                int color = WXResourceUtils.getColor(style.get(Constants.Name.BACKGROUND_COLOR).toString(),
-                    Color.TRANSPARENT);
-                if (color != Color.TRANSPARENT) {
-                    spans.add(new BackgroundColorSpan(color));
-                }
-            }
-
-            if (style.containsKey(Constants.Name.COLOR)) {
-                spans.add(new ForegroundColorSpan(WXResourceUtils.getColor(WXStyle.getTextColor(style))));
-            }
-
-            int spanFlag = createSpanFlag(level);
-            for (Object span : spans) {
-                spannableStringBuilder.setSpan(span, 0, spannableStringBuilder.length(), spanFlag);
-            }
-        }
-    }
-
-    private static int createPriorityFlag(int level) {
-        return level <= MAX_LEVEL ?
-            (MAX_LEVEL - level) << Spanned.SPAN_PRIORITY_SHIFT :
-            MAX_LEVEL << Spanned.SPAN_PRIORITY_SHIFT;
-    }
-
-
-    private static
-    @NonNull
-    Spannable parse(@NonNull List<RichTextNode> list) {
-        SpannableStringBuilder spannableStringBuilder = new SpannableStringBuilder();
-        for (RichTextNode richTextNode : list) {
-            spannableStringBuilder.append(richTextNode.toSpan(1));
-        }
-        return spannableStringBuilder;
-    }
-
-    public Spannable toSpan(int level) {
-        SpannableStringBuilder spannableStringBuilder = new SpannableStringBuilder();
-        spannableStringBuilder.append(toString());
-        if (isInternalNode() && children != null) {
-            for (RichTextNode child : children) {
-                spannableStringBuilder.append(child.toSpan(level + 1));
-            }
-        }
-        updateSpans(spannableStringBuilder, level);
-        return spannableStringBuilder;
-    }
-
-    private
-    @Nullable
-    WXCustomStyleSpan createCustomStyleSpan() {
-        int fontWeight = UNSET, fontStyle = UNSET;
-        String fontFamily = null;
-        if (style.containsKey(Constants.Name.FONT_WEIGHT)) {
-            fontWeight = WXStyle.getFontWeight(style);
-        }
-        if (style.containsKey(Constants.Name.FONT_STYLE)) {
-            fontStyle = WXStyle.getFontStyle(style);
-        }
-        if (style.containsKey(Constants.Name.FONT_FAMILY)) {
-            fontFamily = WXStyle.getFontFamily(style);
-        }
-        if (fontWeight != UNSET
-            || fontStyle != UNSET
-            || fontFamily != null) {
-            return new WXCustomStyleSpan(fontStyle, fontWeight, fontFamily);
-        } else {
-            return null;
-        }
-    }
-    public RichTextNode findRichNode(String ref){
-        RichTextNode theNode;
-        if(mRef != null && TextUtils.equals(mRef,ref)){
-            return this;
-        }
-        if(children != null && !children.isEmpty()){
-            for (RichTextNode child:children) {
-                if((theNode = child.findRichNode(ref)) != null)
-                    return theNode;
-            }
-        }
-        return null;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNodeCreator.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNodeCreator.java
deleted file mode 100755
index faaf6ca..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNodeCreator.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.node;
-
-import android.content.Context;
-
-import java.util.Map;
-
-public interface RichTextNodeCreator<T extends RichTextNode> {
-
-  T createRichTextNode(Context context, String instanceId, String componentRef);
-  T createRichTextNode(Context context,String instanceId,String componentRef,String ref,Map<String,Object> styles, Map<String,Object> attrs);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNodeManager.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNodeManager.java
deleted file mode 100755
index d47cabc..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/RichTextNodeManager.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.node;
-
-import android.content.Context;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.v4.util.ArrayMap;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.Map;
-
-public class RichTextNodeManager {
-
-  private final static Map<String, RichTextNodeCreator>
-      registeredTextNodes = new ArrayMap<>();
-
-  static {
-    registeredTextNodes.put(SpanNode.NODE_TYPE, new SpanNode.SpanNodeCreator());
-    registeredTextNodes.put(ImgNode.NODE_TYPE, new ImgNode.ImgNodeCreator());
-    registeredTextNodes.put(ANode.NODE_TYPE, new ANode.ANodeCreator());
-  }
-
-  public static void registerTextNode(String text, RichTextNodeCreator type) {
-    registeredTextNodes.put(text, type);
-  }
-
-  @Nullable
-  static RichTextNode createRichTextNode(@NonNull Context context, @NonNull String instanceId,
-      @NonNull String componentRef, @Nullable JSONObject jsonObject) {
-    RichTextNode instance = null;
-    try {
-      if (jsonObject != null) {
-        instance = registeredTextNodes.get(jsonObject.getString(RichTextNode.TYPE))
-            .createRichTextNode(context, instanceId, componentRef);
-        instance.parse(context, instanceId, componentRef, jsonObject);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("Richtext", WXLogUtils.getStackTrace(e));
-      instance = null;
-    }
-    return instance;
-  }
-  public static RichTextNode createRichTextNode(Context context,String instanceId,String componentRef,String ref,
-                                         String nodeType,Map<String,String> styles,Map<String,String> attrs){
-    RichTextNode instance;
-    try{
-      instance = registeredTextNodes.get(nodeType).createRichTextNode(context,instanceId,componentRef,ref,styles,attrs);
-    }catch (Exception e){
-      WXLogUtils.e("Richtext", WXLogUtils.getStackTrace(e));
-      instance = null;
-    }
-    return instance;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/SpanNode.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/SpanNode.java
deleted file mode 100755
index dc48c1e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/node/SpanNode.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.node;
-
-import android.content.Context;
-import android.support.v4.util.ArrayMap;
-import android.text.SpannableStringBuilder;
-
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.TextDecorationSpan;
-import com.taobao.weex.dom.WXStyle;
-
-import java.util.ArrayList;
-import java.util.Map;
-
-class SpanNode extends RichTextNode {
-
-  static class SpanNodeCreator implements RichTextNodeCreator<SpanNode> {
-
-    @Override
-    public SpanNode createRichTextNode(Context context, String instanceId, String componentRef) {
-      return new SpanNode(context, instanceId, componentRef);
-    }
-
-    @Override
-    public SpanNode createRichTextNode(Context context,String instanceId,String componentRef,String ref,
-                                       Map<String,Object> styles, Map<String,Object> attrs){
-      return new SpanNode(context,instanceId,componentRef,ref,styles,attrs);
-    }
-  }
-
-  public static final String NODE_TYPE = "span";
-
-  private SpanNode(Context context, String instanceId, String componentRef) {
-    super(context, instanceId, componentRef);
-  }
-  private SpanNode(Context context, String instanceId, String componentRef, String ref, Map<String,Object> styles,Map<String,Object> attrs) {
-    super(context, instanceId, componentRef, ref, styles, attrs);
-  }
-
-  @Override
-  public String toString() {
-    if (attr == null || !attr.containsKey(Constants.Name.VALUE)) {
-      return "";
-    } else {
-      return attr.get(Constants.Name.VALUE).toString();
-    }
-  }
-
-  @Override
-  protected boolean isInternalNode() {
-    return true;
-  }
-
-  @Override
-  protected void updateSpans(SpannableStringBuilder spannableStringBuilder, int level) {
-    super.updateSpans(spannableStringBuilder, level);
-    spannableStringBuilder.setSpan(new TextDecorationSpan(WXStyle.getTextDecoration(style)), 0,
-        spannableStringBuilder.length(), createSpanFlag(level));
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ASpan.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ASpan.java
deleted file mode 100644
index 8f5dd72..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ASpan.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.span;
-
-import android.text.TextPaint;
-import android.text.style.ClickableSpan;
-import android.view.View;
-import com.taobao.weex.utils.ATagUtil;
-
-public class ASpan extends ClickableSpan {
-
-  private String mInstanceId, mURL;
-
-  public ASpan(String instanceId, String url) {
-    mInstanceId = instanceId;
-    mURL = url;
-  }
-
-  @Override
-  public void onClick(View widget) {
-    ATagUtil.onClick(widget, mInstanceId, mURL);
-  }
-
-  /**
-   Override super method and do nothing. As no default color or text-decoration is needed.
-   */
-  @Override
-  public void updateDrawState(TextPaint ds) {
-
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ImgSpan.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ImgSpan.java
deleted file mode 100644
index f3bdc3c..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ImgSpan.java
+++ /dev/null
@@ -1,96 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.span;
-
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.drawable.Drawable;
-import android.text.style.ReplacementSpan;
-import android.view.View;
-
-import com.taobao.weex.adapter.IDrawableLoader;
-
-
-public class ImgSpan extends ReplacementSpan implements IDrawableLoader.StaticTarget {
-
-  private int width, height;
-  private Drawable mDrawable;
-  private View mView;
-
-  public ImgSpan(int width, int height) {
-    this.width = width;
-    this.height = height;
-  }
-
-  /**
-   * Mostly copied from
-   *
-   * {@link android.text.style.DynamicDrawableSpan#getSize(Paint, CharSequence, int, int, Paint.FontMetricsInt)},
-   * but not use Drawable to calculate size;
-   */
-  @Override
-  public int getSize(Paint paint, CharSequence text, int start, int end, Paint.FontMetricsInt fm) {
-    if (fm != null) {
-      fm.ascent = -height;
-      fm.descent = 0;
-
-      fm.top = fm.ascent;
-      fm.bottom = 0;
-    }
-    return width;
-  }
-
-  /**
-   * Mostly copied from
-   * {@link android.text.style.DynamicDrawableSpan#draw(Canvas, CharSequence, int, int, float, int, int, int, Paint)},
-   * except for vertical alignment.
-   */
-  @Override
-  public void draw(Canvas canvas, CharSequence text, int start, int end, float x, int top, int y, int bottom, Paint paint) {
-    if (mDrawable != null) {
-      canvas.save();
-      int transY = bottom - mDrawable.getBounds().bottom;
-      transY -= paint.getFontMetricsInt().descent;
-      canvas.translate(x, transY);
-      mDrawable.draw(canvas);
-      canvas.restore();
-    }
-  }
-
-  @Override
-  public void setDrawable(Drawable drawable, boolean resetBounds) {
-    mDrawable = drawable;
-    if(resetBounds) {
-      mDrawable.setBounds(0, 0, width, height);
-    }
-    setCallback();
-    mDrawable.invalidateSelf();
-  }
-
-  public void setView(View view) {
-    mView = view;
-    setCallback();
-  }
-
-  private void setCallback() {
-    if (mDrawable != null && mView != null) {
-      mDrawable.setCallback(mView);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ItemClickSpan.java b/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ItemClickSpan.java
deleted file mode 100644
index c7146da..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/component/richtext/span/ItemClickSpan.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.richtext.span;
-
-
-import android.text.style.ClickableSpan;
-import android.view.View;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.ui.component.richtext.node.RichTextNode;
-import com.taobao.weex.utils.WXDataStructureUtil;
-import java.util.Map;
-
-public class ItemClickSpan extends ClickableSpan {
-
-  private final String mPseudoRef;
-  private final String mInstanceId;
-  private final String mComponentRef;
-
-  public ItemClickSpan(String instanceId, String componentRef, String pseudoRef) {
-    this.mPseudoRef = pseudoRef;
-    this.mInstanceId = instanceId;
-    this.mComponentRef = componentRef;
-  }
-
-  @Override
-  public void onClick(View widget) {
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
-    if (instance != null && !instance.isDestroy()) {
-      Map<String, Object> param = WXDataStructureUtil.newHashMapWithExpectedSize(1);
-      param.put(RichTextNode.PSEUDO_REF, mPseudoRef);
-      instance.fireEvent(mComponentRef, RichTextNode.ITEM_CLICK, param);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/config/AutoScanConfigRegister.java b/android/sdk/src/main/java/com/taobao/weex/ui/config/AutoScanConfigRegister.java
deleted file mode 100644
index a6cbae0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/config/AutoScanConfigRegister.java
+++ /dev/null
@@ -1,143 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.config;
-
-import android.content.res.AssetManager;
-import android.text.TextUtils;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.JavascriptInvokable;
-import com.taobao.weex.utils.WXFileUtils;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.io.IOException;
-import java.util.concurrent.ConcurrentLinkedQueue;
-
-/**
- * Created by furture on 2018/2/7.
- */
-
-public class AutoScanConfigRegister {
-
-    private static long scanDelay = 0;
-
-    public static final  String TAG  = "WeexScanConfigRegister";
-
-
-    /**
-     * auto scan config files and do auto config from files, none need center register
-     * */
-    public static void doScanConfig(){
-        if(scanDelay > 0){
-            WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(new Runnable() {
-                @Override
-                public void run() {
-                    doScanConfigAsync();
-                }
-            }, scanDelay);
-        }else{
-            doScanConfigAsync();
-        }
-    }
-
-    public static void doScanConfigAsync(){
-        Thread thread = new Thread(new Runnable() {
-            @Override
-            public void run() {
-                doScanConfigSync();
-            }
-        });
-        thread.setName("AutoScanConfigRegister");
-        thread.start();
-    }
-
-    private static void doScanConfigSync(){
-        if(WXEnvironment.sApplication == null){
-            return;
-        }
-        try{
-            AssetManager assetManager = WXEnvironment.sApplication.getApplicationContext().getAssets();
-
-            String[] configFiles = new String[0];
-            try {
-                configFiles = assetManager.list("");
-            } catch (IOException e) {
-                WXLogUtils.e(TAG, e);
-            }
-            if(configFiles == null || configFiles.length == 0){
-                return;
-            }
-            for(String configFile : configFiles){
-                if(TextUtils.isEmpty(configFile)){
-                    continue;
-                }
-                if(configFile.startsWith("weex_config_") && configFile.endsWith(".json")){
-                    String name = configFile;
-                    if(TextUtils.isEmpty(name)){
-                        return;
-                    }
-                    try {
-                        String config = WXFileUtils.loadAsset(name, WXEnvironment.getApplication());
-                        if (TextUtils.isEmpty(config)) {
-                            continue;
-                        }
-                        if (WXEnvironment.isApkDebugable()) {
-                            WXLogUtils.d(TAG, configFile + " find config " + config);
-                        }
-                        JSONObject object = JSON.parseObject(config);
-                        if (object.containsKey("modules")) {
-                            JSONArray array = object.getJSONArray("modules");
-                            for (int i = 0; i < array.size(); i++) {
-                                ConfigModuleFactory configModuleFactory = ConfigModuleFactory.fromConfig(array.getJSONObject(i));
-                                if (configModuleFactory == null) {
-                                    continue;
-                                }
-                                WXSDKEngine.registerModule(configModuleFactory.getName(), configModuleFactory, false);
-                            }
-                        }
-
-                        if (object.containsKey("components")) {
-                            JSONArray array = object.getJSONArray("components");
-                            for (int i = 0; i < array.size(); i++) {
-                                ConfigComponentHolder configComponentHolder = ConfigComponentHolder.fromConfig(array.getJSONObject(i));
-                                if (configComponentHolder == null) {
-                                    return;
-                                }
-                                WXSDKEngine.registerComponent(configComponentHolder, configComponentHolder.isAppendTree(), configComponentHolder.getType());
-                            }
-                        }
-                    }catch (Throwable e){
-                        WXLogUtils.e(TAG, e);
-                    }
-                }
-            }
-        }catch (Exception eout){
-            WXLogUtils.e(TAG, eout);
-        }
-    }
-
-    public static void setScanDelay(long scanDelay) {
-        AutoScanConfigRegister.scanDelay = scanDelay;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/config/ConfigComponentHolder.java b/android/sdk/src/main/java/com/taobao/weex/ui/config/ConfigComponentHolder.java
deleted file mode 100644
index 7a9948d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/config/ConfigComponentHolder.java
+++ /dev/null
@@ -1,161 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.config;
-
-import android.text.TextUtils;
-import android.util.Pair;
-
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.ui.ComponentCreator;
-import com.taobao.weex.ui.IFComponentHolder;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.Map;
-
-/**
- * Created by furture on 2018/2/7.
- */
-public class ConfigComponentHolder implements IFComponentHolder {
-
-
-    public static final String TAG = AutoScanConfigRegister.TAG;
-    private Map<String, Invoker> mPropertyInvokers;
-    private Map<String, Invoker> mMethodInvokers;
-
-    private ClassLoader mClassLoader;
-
-    private String mType;
-    private boolean mAppendTree;
-    private String mClassName;
-    private String[] methods;
-    private Class mClass;
-
-    public ConfigComponentHolder(String mType, boolean mAppendTree, String mClassName, String[] methods) {
-        this.mType = mType;
-        this.mAppendTree = mAppendTree;
-        this.mClassName = mClassName;
-        this.methods = methods;
-    }
-
-    @Override
-    public void loadIfNonLazy() {
-    }
-
-    private synchronized boolean generate(){
-        if(mClass == null){
-            return false;
-        }
-
-        Pair<Map<String, Invoker>, Map<String, Invoker>> methodPair = SimpleComponentHolder.getMethods(mClass);
-        mPropertyInvokers = methodPair.first;
-        mMethodInvokers = methodPair.second;
-        return true;
-    }
-
-
-
-    @Override
-    public synchronized WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-        if(mClass == null || mClassLoader != instance.getContext().getClassLoader()){
-            mClass = WXSDKManager.getInstance().getClassLoaderAdapter().getComponentClass(mType, mClassName, instance);
-            mClassLoader = instance.getContext().getClassLoader();
-        }
-        ComponentCreator creator = new SimpleComponentHolder.ClazzComponentCreator(mClass);
-        WXComponent component = creator.createInstance(instance, parent, basicComponentData);
-
-        component.bindHolder(this);
-        return component;
-    }
-
-    @Override
-    public synchronized Invoker getPropertyInvoker(String name){
-        if (mPropertyInvokers == null && !generate()) {
-            return null;
-        }
-
-        return mPropertyInvokers.get(name);
-    }
-
-    @Override
-    public Invoker getMethodInvoker(String name) {
-        if(mMethodInvokers == null && !generate()){
-            return null;
-        }
-        return mMethodInvokers.get(name);
-    }
-
-    @Override
-    public String[] getMethods() {
-        if(methods == null){
-            //generate failed
-            return new String[0];
-        }
-        return methods;
-    }
-
-
-    public static final ConfigComponentHolder fromConfig(JSONObject config){
-        if(config == null){
-            return null;
-        }
-        try{
-            String type = config.getString("name");
-            boolean appendTree  = config.getBooleanValue("appendTree");
-            String className = config.getString("className");
-            JSONArray methods =  null;
-            if(config.containsKey("methods")) {
-                methods = config.getJSONArray("methods");
-            }
-            if(TextUtils.isEmpty(type) || TextUtils.isEmpty(className)){
-                return null;
-            }
-            String[]  arrays = new String[0];
-            if(methods != null){
-                arrays = new String[methods.size()];
-                methods.toArray(arrays);
-            }
-            if(WXEnvironment.isApkDebugable()){
-                WXLogUtils.d(TAG, "resolve component " + type + " className " + className +  " methods " + methods);
-            }
-            return new ConfigComponentHolder(type, appendTree, className, arrays);
-        }catch (Exception e){
-            WXLogUtils.e(TAG, e);
-            return null;
-        }
-
-    }
-
-    public boolean isAppendTree() {
-        return mAppendTree;
-    }
-
-    public String getType() {
-        return mType;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/config/ConfigModuleFactory.java b/android/sdk/src/main/java/com/taobao/weex/ui/config/ConfigModuleFactory.java
deleted file mode 100644
index 4b8f973..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/config/ConfigModuleFactory.java
+++ /dev/null
@@ -1,155 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.config;
-
-import android.text.TextUtils;
-
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.bridge.MethodInvoker;
-import com.taobao.weex.bridge.ModuleFactory;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.common.WXModuleAnno;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.lang.annotation.Annotation;
-import java.lang.reflect.Method;
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by furture on 2018/2/7.
- */
-
-public class ConfigModuleFactory<T extends WXModule> implements ModuleFactory<T> {
-
-    public static final String TAG = AutoScanConfigRegister.TAG;
-
-    private String mName;
-    private String mClassName;
-    private String[] methods;
-    private Class<T> mClazz;
-    private Map<String, Invoker> mMethodMap;
-
-    private ClassLoader mClassLoader;
-
-    public ConfigModuleFactory(String mName, String mClassName, String[] methods) {
-        this.mName = mName;
-        this.mClassName = mClassName;
-        this.methods = methods;
-    }
-
-    @Override
-    public String[] getMethods() {
-        if(methods == null){
-            return new String[0];
-        }
-        return methods;
-    }
-
-    @Override
-    public Invoker getMethodInvoker(String name) {
-        if (mMethodMap == null) {
-            generateMethodMap();
-        }
-        return mMethodMap.get(name);
-    }
-
-    @Override
-    public T buildInstance() throws IllegalAccessException, InstantiationException {
-        if(mClazz == null){
-            mClazz = (Class<T>) WXSDKManager.getInstance().getClassLoaderAdapter().getModuleClass(mName, mClassName, WXEnvironment.getApplication().getApplicationContext());
-        }
-        return mClazz.newInstance();
-    }
-
-    public T buildInstance(WXSDKInstance instance) throws IllegalAccessException, InstantiationException {
-        if(instance == null){
-            return buildInstance();
-        }
-        if(mClazz == null || mClassLoader != instance.getContext().getClassLoader()){
-            mClazz = (Class<T>) WXSDKManager.getInstance().getClassLoaderAdapter().getModuleClass(mName, mClassName, instance.getContext());
-            mClassLoader = instance.getContext().getClassLoader();
-        }
-        return mClazz.newInstance();
-    }
-
-
-    private void generateMethodMap() {
-        if(WXEnvironment.isApkDebugable()) {
-             WXLogUtils.d(TAG, "extractMethodNames:" + mClazz.getSimpleName());
-        }
-        HashMap<String, Invoker> methodMap = new HashMap<>();
-        try {
-            for (Method method : mClazz.getMethods()) {
-                // iterates all the annotations available in the method
-                for (Annotation anno : method.getDeclaredAnnotations()) {
-                    if (anno != null) {
-                        if(anno instanceof JSMethod) {
-                            JSMethod methodAnnotation = (JSMethod) anno;
-                            String name = JSMethod.NOT_SET.equals(methodAnnotation.alias())? method.getName():methodAnnotation.alias();
-                            methodMap.put(name, new MethodInvoker(method, methodAnnotation.uiThread()));
-                            break;
-                        }else if(anno instanceof WXModuleAnno) {
-                            WXModuleAnno methodAnnotation = (WXModuleAnno)anno;
-                            methodMap.put(method.getName(), new MethodInvoker(method,methodAnnotation.runOnUIThread()));
-                            break;
-                        }
-                    }
-                }
-            }
-        } catch (Throwable e) {
-            WXLogUtils.e("[WXModuleManager] extractMethodNames:", e);
-        }
-        mMethodMap = methodMap;
-    }
-
-
-    public static ConfigModuleFactory fromConfig(JSONObject config){
-        try{
-            if(config == null){
-                return null;
-            }
-
-            String name = config.getString("name");
-            String className = config.getString("className");
-            JSONArray methods = config.getJSONArray("methods");
-            if(TextUtils.isEmpty(name) || TextUtils.isEmpty(className)){
-                return null;
-            }
-            String[]  arrays = new String[methods.size()];
-            if(WXEnvironment.isApkDebugable()){
-                WXLogUtils.d(TAG, " resolve module " + name + " className " + className +  " methods " + methods);
-            }
-            return new ConfigModuleFactory(name, className, methods.toArray(arrays));
-        }catch (Exception e){
-             WXLogUtils.e(TAG, e);
-             return null;
-        }
-    }
-
-    public String getName() {
-        return mName;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/flat/FlatComponent.java b/android/sdk/src/main/java/com/taobao/weex/ui/flat/FlatComponent.java
deleted file mode 100644
index 823da47..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/flat/FlatComponent.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.flat;
-
-
-import android.support.annotation.NonNull;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-
-import com.taobao.weex.ui.flat.widget.Widget;
-
-@RestrictTo(Scope.LIBRARY)
-public interface FlatComponent<T extends Widget> {
-
-  boolean promoteToView(boolean checkAncestor);
-
-  @NonNull
-  T getOrCreateFlatWidget();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/flat/FlatGUIContext.java b/android/sdk/src/main/java/com/taobao/weex/ui/flat/FlatGUIContext.java
deleted file mode 100644
index 16f1d62..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/flat/FlatGUIContext.java
+++ /dev/null
@@ -1,146 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.flat;
-
-
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-import android.view.View;
-
-import com.taobao.weex.common.Constants.Name;
-import com.taobao.weex.common.Destroyable;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.flat.widget.AndroidViewWidget;
-import com.taobao.weex.ui.flat.widget.Widget;
-
-import java.util.Map;
-import java.util.Map.Entry;
-
-//TODO The constructor of FlatGUIContext should have a flag decide whether to enable flagGUI.
-
-@RestrictTo(Scope.LIBRARY)
-public class FlatGUIContext implements Destroyable {
-
-  private Map<WXComponent, WidgetContainer> mWidgetRegistry = new ArrayMap<>();
-  private Map<WXComponent, AndroidViewWidget> mViewWidgetRegistry = new ArrayMap<>();
-  private Map<Widget, WXComponent> widgetToComponent = new ArrayMap<>();
-
-  public boolean isFlatUIEnabled(WXComponent component) {
-    return false;
-  }
-
-  public void register(@NonNull WXComponent descendant, @NonNull WidgetContainer ancestor) {
-    if (!(ancestor instanceof FlatComponent) ||
-            ((FlatComponent) ancestor).promoteToView(true)) {
-      mWidgetRegistry.put(descendant, ancestor);
-    }
-  }
-
-  public void register(@NonNull WXComponent component, @NonNull AndroidViewWidget viewWidget) {
-    mViewWidgetRegistry.put(component, viewWidget);
-  }
-
-  public void register(@NonNull Widget widget, @NonNull WXComponent component) {
-    widgetToComponent.put(widget, component);
-  }
-
-  public
-  @Nullable
-  WidgetContainer getFlatComponentAncestor(@NonNull WXComponent flatWidget) {
-    return mWidgetRegistry.get(flatWidget);
-  }
-
-  public
-  @Nullable
-  AndroidViewWidget getAndroidViewWidget(@NonNull WXComponent component) {
-    return mViewWidgetRegistry.get(component);
-  }
-
-  public boolean promoteToView(@NonNull WXComponent component, boolean checkAncestor,
-                               @NonNull Class<? extends WXComponent<?>> expectedClass) {
-    return !isFlatUIEnabled(component) ||
-            !expectedClass.equals(component.getClass()) ||
-            TextUtils.equals(component.getRef(), WXComponent.ROOT) ||
-            (checkAncestor && getFlatComponentAncestor(component) == null) ||
-            checkComponent(component);
-  }
-
-  public
-  @Nullable
-  View getWidgetContainerView(Widget widget) {
-    WXComponent component, ancestor;
-    View ret = null;
-    if ((component = getComponent(widget)) != null) {
-      if ((ancestor = getFlatComponentAncestor(component)) != null) {
-        ret = ancestor.getHostView();
-      }
-    }
-    return ret;
-  }
-
-  @Override
-  @RestrictTo(Scope.LIBRARY)
-  public void destroy() {
-    widgetToComponent.clear();
-
-    for (Entry<WXComponent, AndroidViewWidget> entry : mViewWidgetRegistry.entrySet()) {
-      entry.getValue().destroy();
-    }
-    mViewWidgetRegistry.clear();
-
-    for (Entry<WXComponent, WidgetContainer> entry : mWidgetRegistry.entrySet()) {
-      entry.getValue().unmountFlatGUI();
-    }
-    mWidgetRegistry.clear();
-  }
-
-  private @Nullable
-  WXComponent getComponent(@NonNull Widget widget) {
-    return widgetToComponent.get(widget);
-  }
-
-  private boolean checkComponent(@NonNull WXComponent component) {
-    boolean ret = false;
-    if (component != null) {
-      WXStyle style = component.getStyles();
-      WXAttr attr = component.getAttrs();
-      if (style.containsKey(Name.OPACITY) ||
-              style.containsKey(Name.TRANSFORM) ||
-              style.containsKey(Name.VISIBILITY) ||
-              attr.containsKey(Name.ELEVATION) ||
-              attr.containsKey(Name.ARIA_HIDDEN) ||
-              attr.containsKey(Name.ARIA_LABEL) ||
-              attr.containsKey(WXComponent.PROP_FIXED_SIZE) ||
-              attr.containsKey(Name.DISABLED) ||
-              style.isFixed() ||
-              style.isSticky() ||
-              !style.getPesudoStyles().isEmpty() ||
-              component.getEvents().size() > 0) {
-        ret = true;
-      }
-    }
-    return ret;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/flat/WidgetContainer.java b/android/sdk/src/main/java/com/taobao/weex/ui/flat/WidgetContainer.java
deleted file mode 100644
index 0946800..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/flat/WidgetContainer.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.flat;
-
-
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.util.Pair;
-import android.view.ViewGroup;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.ui.action.BasicComponentData;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.ui.flat.widget.AndroidViewWidget;
-import com.taobao.weex.ui.flat.widget.Widget;
-
-import java.util.LinkedList;
-import java.util.List;
-
-@RestrictTo(Scope.LIBRARY)
-public abstract class WidgetContainer<T extends ViewGroup> extends WXVContainer<T> {
-
-  protected List<Widget> widgets;
-
-  public WidgetContainer(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
-    super(instance, parent, basicComponentData);
-  }
-
-  protected abstract void mountFlatGUI();
-
-  protected abstract void unmountFlatGUI();
-
-  public boolean intendToBeFlatContainer() {
-    return false;
-  }
-
-  @Override
-  public void createChildViewAt(int index) {
-    if (intendToBeFlatContainer()) {
-      Pair<WXComponent, Integer> ret = rearrangeIndexAndGetChild(index);
-      if (ret.first != null) {
-        WXComponent child = ret.first;
-        Widget flatChild;
-        FlatGUIContext uiImp = getInstance().getFlatUIContext();
-        WidgetContainer parent = uiImp.getFlatComponentAncestor(this);
-        if (parent == null || uiImp.getAndroidViewWidget(this) != null) {
-          parent = this;
-        }
-        uiImp.register(child, parent);
-
-        if (child instanceof FlatComponent && !((FlatComponent) child).promoteToView(false)) {
-          flatChild = ((FlatComponent) child).getOrCreateFlatWidget();
-        } else {
-          flatChild = new AndroidViewWidget(uiImp);
-          uiImp.register(child, (AndroidViewWidget) flatChild);
-          child.createView();
-          ((AndroidViewWidget) flatChild).setContentView(child.getHostView());
-          //TODO Use a sort algorithm to decide the childIndex of AndroidViewWidget
-          parent.addSubView(child.getHostView(), -1);
-        }
-        uiImp.register(flatChild, child);
-        addFlatChild(flatChild, ret.second);
-      }
-    } else {
-      super.createChildViewAt(index);
-    }
-  }
-
-  private void addFlatChild(Widget widget, int index) {
-    if(widgets == null){
-      widgets = new LinkedList<>();
-    }
-    if (index >= widgets.size()) {
-      widgets.add(widget);
-    } else {
-      widgets.add(index, widget);
-    }
-    //TODO do a partial update, not mount the whole flatContainer.
-    mountFlatGUI();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/AndroidViewWidget.java b/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/AndroidViewWidget.java
deleted file mode 100644
index ad72054..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/AndroidViewWidget.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.flat.widget;
-
-
-import android.graphics.Canvas;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.view.View;
-
-import com.taobao.weex.common.Destroyable;
-import com.taobao.weex.ui.flat.FlatGUIContext;
-
-@RestrictTo(Scope.LIBRARY)
-public class AndroidViewWidget extends BaseWidget implements Destroyable {
-
-  private @Nullable
-  View mView;
-
-  public AndroidViewWidget(@NonNull FlatGUIContext context) {
-    super(context);
-  }
-
-  public void setContentView(@Nullable View view) {
-    this.mView = view;
-  }
-
-  @Override
-  public void setContentBox(int leftOffset, int topOffset, int rightOffset, int bottomOffset) {
-    if (mView != null) {
-      mView.setPadding(leftOffset, topOffset, rightOffset, bottomOffset);
-      invalidate();
-    }
-  }
-
-  @Override
-  public void onDraw(@NonNull Canvas canvas) {
-    if (mView != null) {
-      mView.draw(canvas);
-    }
-  }
-
-  @Override
-  public void invalidate() {
-    super.invalidate();
-    if (mView != null) {
-      mView.invalidate();
-    }
-  }
-
-  public @Nullable
-  View getView() {
-    return mView;
-  }
-
-  @Override
-  public void destroy() {
-    if (mView != null) {
-      mView = null;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/BaseWidget.java b/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/BaseWidget.java
deleted file mode 100644
index 09cd14a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/BaseWidget.java
+++ /dev/null
@@ -1,130 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.flat.widget;
-
-
-import android.graphics.Canvas;
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.graphics.drawable.Drawable;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.view.View;
-import com.taobao.weex.ui.flat.FlatGUIContext;
-import com.taobao.weex.ui.view.border.BorderDrawable;
-import com.taobao.weex.utils.WXViewUtils;
-
-@RestrictTo(Scope.LIBRARY)
-abstract class BaseWidget implements Widget {
-
-  //TODO Reconsider the field parameter in this class and the operation during draw(); Make a CPU/Memory balance.
-  //TODO use float to avoid 1px problem
-  private BorderDrawable backgroundBorder;
-  private int leftOffset, topOffset, rightOffset, bottomOffset;
-  private Rect borderBox = new Rect();
-  private Point offsetOfContainer = new Point();
-  private final @NonNull
-  FlatGUIContext context;
-
-  BaseWidget(@NonNull FlatGUIContext context){
-    this.context = context;
-  }
-
-  @Override
-  public void setLayout(int width, int height, int left, int right, int top, int bottom, Point offset) {
-    this.offsetOfContainer = offset;
-    borderBox.set(left, top, left + width, top + height);
-    if (backgroundBorder != null) {
-      setBackgroundAndBorder(backgroundBorder);
-    }
-    invalidate();
-  }
-
-  @Override
-  public void setContentBox(int leftOffset, int topOffset, int rightOffset, int bottomOffset) {
-    this.leftOffset = leftOffset;
-    this.topOffset = topOffset;
-    this.rightOffset = rightOffset;
-    this.bottomOffset = bottomOffset;
-    invalidate();
-  }
-
-  @Override
-  public void setBackgroundAndBorder(@NonNull BorderDrawable backgroundBorder) {
-    //TODO Change the code of BorderDrawable is more appropriate as it draws the borderLine from (0,0) not from getBounds
-    //TODO If the above is finished, no more traslate in draw in needed, only clip is enough.
-    this.backgroundBorder = backgroundBorder;
-    Rect backgroundBox = new Rect(borderBox);
-    backgroundBox.offset(-borderBox.left, -borderBox.top);
-    backgroundBorder.setBounds(backgroundBox);
-    setCallback(backgroundBorder);
-    invalidate();
-  }
-
-  @NonNull
-  @Override
-  public final Point getLocInFlatContainer() {
-    return offsetOfContainer;
-  }
-
-  @Nullable
-  @Override
-  public final BorderDrawable getBackgroundAndBorder() {
-    return backgroundBorder;
-  }
-
-  @NonNull
-  @Override
-  public final Rect getBorderBox() {
-    return borderBox;
-  }
-
-  @Override
-  public final void draw(@NonNull Canvas canvas) {
-    canvas.save();
-    WXViewUtils.clipCanvasWithinBorderBox(this, canvas);
-    canvas.translate(borderBox.left, borderBox.top);
-    if (backgroundBorder != null) {
-      backgroundBorder.draw(canvas);
-    }
-    canvas.clipRect(leftOffset, topOffset, borderBox.width()-rightOffset, borderBox.height() - bottomOffset);
-    canvas.translate(leftOffset, topOffset);
-    onDraw(canvas);
-    canvas.restore();
-  }
-
-  protected void invalidate() {
-    Rect dirtyRegion = new Rect(borderBox);
-    dirtyRegion.offset(offsetOfContainer.x, offsetOfContainer.y);
-    View widgetContainer;
-    if (context != null && (widgetContainer = context.getWidgetContainerView(this)) != null) {
-      widgetContainer.invalidate(dirtyRegion);
-    }
-  }
-
-  protected void setCallback(@NonNull Drawable drawable) {
-    View widgetContainer;
-    if (context != null && (widgetContainer = context.getWidgetContainerView(this)) != null) {
-      drawable.setCallback(widgetContainer);
-    }
-  }
-}
-
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/TextWidget.java b/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/TextWidget.java
deleted file mode 100644
index fee01b9..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/TextWidget.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.flat.widget;
-
-
-import android.graphics.Canvas;
-import android.support.annotation.NonNull;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import android.text.Layout;
-
-import com.taobao.weex.ui.flat.FlatGUIContext;
-
-@RestrictTo(Scope.LIBRARY)
-public class TextWidget extends BaseWidget {
-
-  private Layout mLayout;
-
-  public TextWidget(@NonNull FlatGUIContext context) {
-    super(context);
-  }
-
-  @Override
-  public void onDraw(@NonNull Canvas canvas) {
-    if (mLayout != null) {
-      mLayout.draw(canvas);
-    }
-  }
-
-  public void updateTextDrawable(Layout layout) {
-    this.mLayout = layout;
-    invalidate();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/Widget.java b/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/Widget.java
deleted file mode 100644
index ac9eb6f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/Widget.java
+++ /dev/null
@@ -1,55 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.flat.widget;
-
-
-import android.graphics.Canvas;
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-
-import com.taobao.weex.ui.view.border.BorderDrawable;
-
-@RestrictTo(Scope.LIBRARY)
-public interface Widget {
-
-  public static final String TAG = "Widget";
-
-  void draw(@NonNull Canvas canvas);
-
-  void onDraw(@NonNull Canvas canvas);
-
-  void setBackgroundAndBorder(@NonNull BorderDrawable backgroundBorder);
-
-  void setLayout(int width, int height, int left, int right, int top, int bottom, Point offset);
-
-  void setContentBox(int leftOffset, int topOffset, int rightOffset, int bottomOffset);
-
-  @NonNull
-  Point getLocInFlatContainer();
-
-  @Nullable
-  BorderDrawable getBackgroundAndBorder();
-
-  @NonNull
-  Rect getBorderBox();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/WidgetGroup.java b/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/WidgetGroup.java
deleted file mode 100644
index 942a4b1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/flat/widget/WidgetGroup.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.flat.widget;
-
-
-import android.graphics.Canvas;
-import android.support.annotation.NonNull;
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-
-import com.taobao.weex.ui.flat.FlatGUIContext;
-
-import java.util.LinkedList;
-import java.util.List;
-
-@RestrictTo(Scope.LIBRARY)
-public class WidgetGroup extends BaseWidget {
-
-  private List<Widget> mChildren = new LinkedList<>();
-
-  public WidgetGroup(@NonNull FlatGUIContext context) {
-    super(context);
-  }
-
-  public void replaceAll(@NonNull List<Widget> widgets) {
-    mChildren = widgets;
-    invalidate();
-  }
-
-  public List<Widget> getChildren() {
-    return mChildren;
-  }
-
-  @Override
-  public void onDraw(@NonNull Canvas canvas) {
-    for (Widget child : mChildren) {
-      child.draw(canvas);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/module/ConsoleLogModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/module/ConsoleLogModule.java
deleted file mode 100644
index 3db7cef..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/module/ConsoleLogModule.java
+++ /dev/null
@@ -1,86 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import android.support.annotation.Nullable;
-import android.support.v4.util.ArrayMap;
-import android.text.TextUtils;
-import android.util.Log;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.utils.LogLevel;
-import java.util.Map;
-
-
-public class ConsoleLogModule extends WXModule {
-
-  @JSMethod(uiThread = false)
-  public void switchLogLevel(@Nullable String logLevel, @Nullable JSCallback callback) {
-    LogLevel logLevelEnum = getLogLevel(logLevel);
-    Map<String, String> ret = new ArrayMap<>();
-    if (logLevelEnum != null) {
-      WXEnvironment.sLogLevel = logLevelEnum;
-      WXBridgeManager.getInstance().setLogLevel(WXEnvironment.sLogLevel.getValue(),WXEnvironment.isPerf());
-      ret.put("status", "success");
-    } else {
-      ret.put("status", "failure");
-    }
-
-    if (callback != null) {
-      callback.invoke(ret);
-    }
-
-  }
-
-  @JSMethod(uiThread = false)
-  public void setPerfMode(@Nullable String on) {
-    WXEnvironment.isPerf = "true".equals(on);
-    WXBridgeManager.getInstance().setLogLevel(WXEnvironment.sLogLevel.getValue(),WXEnvironment.isPerf());
-  }
-
-  private @Nullable LogLevel getLogLevel(@Nullable String logLevel) {
-    LogLevel logLevelEnum = null;
-    if(!TextUtils.isEmpty(logLevel)){
-      switch (logLevel){
-        case "off":
-          logLevelEnum = LogLevel.OFF;
-          break;
-        case "error":
-          logLevelEnum = LogLevel.ERROR;
-          break;
-        case "warning":
-          logLevelEnum = LogLevel.WARN;
-          break;
-        case "info":
-          logLevelEnum = LogLevel.INFO;
-          break;
-        case "debug":
-          logLevelEnum = LogLevel.DEBUG;
-          break;
-      }
-    }
-    return logLevelEnum;
-  }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXDeviceInfoModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/module/WXDeviceInfoModule.java
deleted file mode 100644
index 02392c6..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXDeviceInfoModule.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.util.HashMap;
-
-public class WXDeviceInfoModule extends WXModule {
-    
-    @JSMethod(uiThread = false)
-    public void enableFullScreenHeight(final JSCallback callback,JSONObject extend){
-        if(mWXSDKInstance != null) {
-            mWXSDKInstance.setEnableFullScreenHeight(true);
-            if(callback != null) {
-                long fullScreenHeight = WXViewUtils.getScreenHeight(mWXSDKInstance.getInstanceId());
-                HashMap<String, String> ret = new HashMap();
-                ret.put("fullScreenHeight", String.valueOf(fullScreenHeight));
-                callback.invoke(ret);
-            }
-
-        }
-
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXDomModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/module/WXDomModule.java
deleted file mode 100644
index 08ce054..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXDomModule.java
+++ /dev/null
@@ -1,207 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import android.support.annotation.RestrictTo;
-import android.support.annotation.RestrictTo.Scope;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.dom.binding.JSONUtils;
-import com.taobao.weex.ui.action.ActionAddRule;
-import com.taobao.weex.ui.action.ActionGetComponentRect;
-import com.taobao.weex.ui.action.ActionGetLayoutDirection;
-import com.taobao.weex.ui.action.ActionInvokeMethod;
-import com.taobao.weex.ui.action.GraphicActionBatchBegin;
-import com.taobao.weex.ui.action.GraphicActionBatchEnd;
-import com.taobao.weex.ui.action.GraphicActionScrollToElement;
-import com.taobao.weex.ui.action.UpdateComponentDataAction;
-import com.taobao.weex.utils.WXLogUtils;
-
-/**
- * <p>
- * Module class for dom operation.
- * </p>
- * <p>
- *   This module is work different with other regular module, method is invoked directly, without reflection.
- * </p>
- *
- * <p>
- *  This class is for internal purpose,
- *  please don't use it directly unless you know what you are doing.
- * </p>
- */
-@RestrictTo(Scope.LIBRARY_GROUP)
-public class WXDomModule extends WXModule {
-
-  /** package **/
-  public static final String SCROLL_TO_ELEMENT = "scrollToElement";
-  public static final String ADD_RULE = "addRule";
-  public static final String GET_COMPONENT_RECT = "getComponentRect";
-  public static final String GET_COMPONENT_DIRECTION = "getLayoutDirection";
-  public static final String WXDOM = "dom";
-  public static final String INVOKE_METHOD = "invokeMethod";
-
-  public static final String UPDATE_COMPONENT_DATA = "updateComponentData";
-
-  public static final String BATCH_BEGIN = "beginBatchMark";
-  public static final String BATCH_END = "endBatchMark";
-
-  /**
-   * Methods expose to js. Every method which will be called in js should add to this array.
-   */
-  public static final String[] METHODS = {SCROLL_TO_ELEMENT, ADD_RULE, GET_COMPONENT_RECT,
-      INVOKE_METHOD, GET_COMPONENT_DIRECTION, BATCH_BEGIN, BATCH_END};
-
-  public WXDomModule(WXSDKInstance instance){
-    mWXSDKInstance = instance;
-  }
-
-  public void callDomMethod(JSONObject task, long... parseNanos) {
-    if (task == null) {
-      return;
-    }
-    String method = (String) task.get(WXBridgeManager.METHOD);
-    JSONArray args = (JSONArray) task.get(WXBridgeManager.ARGS);
-    callDomMethod(method,args,parseNanos);
-  }
-
-  public Object callDomMethod(String method, JSONArray args, long... parseNanos) {
-
-    if (method == null) {
-      return null;
-    }
-
-    try {
-      switch (method) {
-        case GET_COMPONENT_DIRECTION: {
-          if(args == null){
-            return null;
-          }
-          new ActionGetLayoutDirection(mWXSDKInstance, args.getString(0), args.getString(1))
-                  .executeActionOnRender();
-          break;
-        }
-        case SCROLL_TO_ELEMENT:{
-          if (args == null) {
-            return null;
-          }
-          String ref = args.size() >= 1 ? args.getString(0) : null;
-          JSONObject options = args.size() >= 2 ? args.getJSONObject(1) : null;
-          new GraphicActionScrollToElement(mWXSDKInstance, ref, options)
-                  .executeActionOnRender();
-          break;
-        }
-        case ADD_RULE:{
-          if (args == null) {
-            return null;
-          }
-          new ActionAddRule(mWXSDKInstance.getInstanceId(), args.getString(0), args.getJSONObject(1))
-                  .executeAction();
-          break;
-        }
-        case GET_COMPONENT_RECT:{
-            if(args == null){
-                return null;
-            }
-            new ActionGetComponentRect(mWXSDKInstance, args.getString(0), args.getString(1))
-                    .executeActionOnRender();
-            break;
-        }
-        case INVOKE_METHOD: {
-          if(args == null){
-            return null;
-          }
-          // todo：no sure where the request com from
-          new ActionInvokeMethod(mWXSDKInstance.getInstanceId(), args.getString(0), args.getString(1), args.getJSONArray(2))
-                  .executeAction();
-          break;
-        }
-        case UPDATE_COMPONENT_DATA:
-          if(args == null || args.size() < 3){
-            return null;
-          }
-          new UpdateComponentDataAction(mWXSDKInstance, args.getString(0), JSONUtils.toJSON(args.get(1)), args.getString(2)).executeAction();
-          break;
-        case BATCH_BEGIN: {
-          if(args == null){
-            return null;
-          }
-          String ref = args.size() >= 1 ? args.getString(0) : null;
-          new GraphicActionBatchBegin(mWXSDKInstance, ref).executeActionOnRender();
-          break;
-        }
-        case BATCH_END: {
-          String ref = args.size() >= 1 ? args.getString(0) : null;
-          new GraphicActionBatchEnd(mWXSDKInstance, ref).executeActionOnRender();
-          break;
-        }
-        default:
-          WXLogUtils.e("Unknown dom action.");
-          break;
-      }
-
-      // todo TraceableAction
-//      if (WXTracing.isAvailable() && action instanceof TraceableAction) {
-//        String ref = null;
-//        String type = null;
-//        if (args.size() > 0) {
-//          if (args.size() >= 1) {
-//            if (args.get(0) instanceof String) {
-//              ref = args.getString(0);
-//            } else if (args.get(0) instanceof JSONObject) {
-//              ref = ((JSONObject) args.get(0)).getString("ref");
-//              type = ((JSONObject) args.get(0)).getString("type");
-//            }
-//          }
-//
-//          if (args.size() >= 2) {
-//            if (args.get(1) instanceof JSONObject) {
-//              ref = ((JSONObject) args.get(1)).getString("ref");
-//              type = ((JSONObject) args.get(1)).getString("type");
-//            }
-//          }
-//        }
-//        if (parseNanos != null && parseNanos.length == 1) {
-//          ((TraceableAction) action).mParseJsonNanos = parseNanos[0];
-//          ((TraceableAction) action).mStartMillis -= Stopwatch.nanosToMillis(parseNanos[0]);
-//        }
-//        ((TraceableAction) action).onStartDomExecute(mWXSDKInstance.getInstanceId(), method, ref, type, args.toJSONString());
-//      }
-    } catch (IndexOutOfBoundsException e) {
-      // no enougn args
-      e.printStackTrace();
-      WXLogUtils.e("Dom module call miss arguments.");
-    } catch (ClassCastException cce) {
-      WXLogUtils.e("Dom module call arguments format error!!");
-    }
-    return null;
-  }
-
-  public void invokeMethod(String ref, String method, JSONArray args){
-    if(ref == null || method == null){
-      return;
-    }
-
-    new ActionInvokeMethod(mWXSDKInstance.getInstanceId(), ref, method, args)
-            .executeAction();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXLocaleModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/module/WXLocaleModule.java
deleted file mode 100644
index 41a0c55..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXLocaleModule.java
+++ /dev/null
@@ -1,112 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import android.content.Context;
-import android.content.res.Configuration;
-import android.content.res.Resources;
-import android.os.Build;
-import android.os.LocaleList;
-import android.text.TextUtils;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.common.WXModule;
-
-import java.util.Arrays;
-import java.util.List;
-import java.util.Locale;
-
-/**
- * Created by moxun on 2017/9/26.
- * <p>
- * Ref: https://tools.ietf.org/html/bcp47
- */
-
-public class WXLocaleModule extends WXModule {
-
-  @JSMethod(uiThread = false)
-  public String getLanguageSync() {
-    return getLanguageImpl();
-  }
-
-  @JSMethod(uiThread = false)
-  public void getLanguage(JSCallback callback) {
-    callback.invoke(getLanguageImpl());
-  }
-
-  private String getLanguageImpl() {
-    Locale locale;
-    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
-      locale = LocaleList.getDefault().get(0);
-    } else locale = Locale.getDefault();
-
-    String language = locale.getLanguage() + "-" + locale.getCountry();
-    return language;
-  }
-
-  @JSMethod(uiThread = false)
-  public List<String> getLanguages() {
-    String[] tags = getLanguageTags().split(",");
-    return Arrays.asList(tags);
-  }
-
-  @JSMethod(uiThread = false)
-  public void getLanguages(JSCallback callback) {
-    callback.invoke(getLanguageTags().split(","));
-  }
-
-  private String getLanguageTags() {
-    Context application = WXEnvironment.getApplication();
-    if (application != null) {
-      Resources res = application.getResources();
-      if (res != null) {
-        Configuration configuration = res.getConfiguration();
-        if (configuration != null) {
-          if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
-            LocaleList localeList = configuration.getLocales();
-            return localeList.toLanguageTags();
-          } else {
-            Locale local = configuration.locale;
-            if (local != null) {
-              return toLanguageTag(local);
-            }
-          }
-        }
-      }
-    }
-    return "";
-  }
-
-  private String toLanguageTag(Locale locale) {
-    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-      return locale.toLanguageTag();
-    } else {
-      StringBuilder sb = new StringBuilder();
-      String language = locale.getLanguage();
-      String region = locale.getCountry();
-      sb.append(language);
-      if (!TextUtils.isEmpty(region)) {
-        sb.append("-").append(region);
-      }
-      return sb.toString();
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXMetaModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/module/WXMetaModule.java
deleted file mode 100644
index 04bb8e4..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXMetaModule.java
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import android.app.Application;
-import android.content.Context;
-import android.content.pm.ApplicationInfo;
-import android.text.TextUtils;
-import android.widget.Toast;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import java.net.URLDecoder;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Created by zhengshihan on 16/12/20.
- */
-
-public class WXMetaModule extends WXModule {
-
-    public static final String WIDTH = "width";
-    public static final String DEVICE_WIDTH = "device-width";
-
-    @JSMethod(uiThread = false)
-    public void setViewport(String param) {
-        if (!TextUtils.isEmpty(param)) {
-            try {
-                param = URLDecoder.decode(param, "utf-8");
-                JSONObject jsObj = JSON.parseObject(param);
-                Context cxt = mWXSDKInstance.getContext();
-                // todo maybe getString(WIDTH) is "device-height"
-                if (DEVICE_WIDTH.endsWith(jsObj.getString(WIDTH))) {
-                    int width = (int)(WXViewUtils.getScreenWidth(cxt)/WXViewUtils.getScreenDensity(cxt));
-                    mWXSDKInstance.setInstanceViewPortWidth(width,true);
-                    WXLogUtils.d("[WXMetaModule] setViewport success[device-width]=" + width);
-                } else {
-                    int width = jsObj.getInteger(WIDTH);
-                    if (width > 0) {
-                        mWXSDKInstance.setInstanceViewPortWidth(width,true);
-                    }
-                    WXLogUtils.d("[WXMetaModule] setViewport success[width]=" + width);
-                }
-            } catch (Exception e) {
-                WXLogUtils.e("[WXMetaModule] alert param parse error ", e);
-            }
-        }
-    }
-
-    @JSMethod(uiThread = true)
-    public void openLog(String open) {
-        Application application = WXEnvironment.getApplication();
-        if(application == null){
-            return;
-        }
-        ApplicationInfo info = application.getApplicationInfo();
-        if((info.flags & ApplicationInfo.FLAG_DEBUGGABLE)!= 0){
-            if(WXUtils.getBoolean(open, true)) {
-                WXEnvironment.setApkDebugable(true);
-                if(mWXSDKInstance != null) {
-                    Toast.makeText(mWXSDKInstance.getContext(), "log open success", Toast.LENGTH_SHORT).show();
-                }
-            }else{
-                WXEnvironment.setApkDebugable(false);
-                if(mWXSDKInstance != null) {
-                    Toast.makeText(mWXSDKInstance.getContext(), "log close success", Toast.LENGTH_SHORT).show();
-                }
-            }
-        }
-    }
-
-    @JSMethod(uiThread = false)
-    public void getPageInfo(JSCallback callback) {
-        if(callback == null){
-            return;
-        }
-        List<WXSDKInstance> instances = WXSDKManager.getInstance().getWXRenderManager().getAllInstances();
-        Map<String,Object> map = new HashMap<>(4);
-        for(WXSDKInstance instance : instances){
-            if(TextUtils.isEmpty(instance.getBundleUrl())){
-                continue;
-            }
-            map.put(instance.getBundleUrl(), instance.getTemplateInfo());
-        }
-        callback.invoke(map);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXModalUIModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/module/WXModalUIModule.java
deleted file mode 100644
index a158dcc..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXModalUIModule.java
+++ /dev/null
@@ -1,264 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import android.annotation.SuppressLint;
-import android.app.Activity;
-import android.app.AlertDialog;
-import android.app.Dialog;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnClickListener;
-import android.text.TextUtils;
-import android.view.Gravity;
-import android.widget.EditText;
-import android.widget.Toast;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.utils.WXLogUtils;
-import java.util.HashMap;
-import java.util.Map;
-
-
-/**
- * WXModalUIModule module provide toast、alert、confirm、prompt to display the message.
- * for example(weex JS):
- * this.$call('modal','toast',{'message':'test toast','duration': 2.0});
- */
-public class WXModalUIModule extends WXSDKEngine.DestroyableModule {
-
-  public static final String OK = "OK";
-  public static final String CANCEL = "Cancel";
-  public static final String RESULT = "result";
-  public static final String DATA = "data";
-  public static final String MESSAGE = "message";
-  public static final String DURATION = "duration";
-  public static final String OK_TITLE = "okTitle";
-  public static final String CANCEL_TITLE = "cancelTitle";
-  public static final String DEFAULT = "default";
-  private Toast toast;
-  private Dialog activeDialog;
-
-  @SuppressLint("ShowToast")
-  @JSMethod(uiThread = true)
-  public void toast(JSONObject jsObj) {
-    if(mWXSDKInstance.getContext() == null){
-      return;
-    }
-    String message = "";
-    int duration = Toast.LENGTH_SHORT;
-    if (jsObj != null) {
-      try {
-        message = jsObj.getString(MESSAGE);
-        if(jsObj.containsKey(DURATION)) {
-          duration = jsObj.getInteger(DURATION);
-        }
-      } catch (Exception e) {
-        WXLogUtils.e("[WXModalUIModule] alert param parse error ", e);
-      }
-    }
-    if (TextUtils.isEmpty(message)) {
-      WXLogUtils.e("[WXModalUIModule] toast param parse is null ");
-      return;
-    }
-
-    if (duration > 3) {
-      duration = Toast.LENGTH_LONG;
-    } else {
-      duration = Toast.LENGTH_SHORT;
-    }
-    if (toast == null) {
-      toast = Toast.makeText(mWXSDKInstance.getContext(), message, duration);
-    } else {
-      toast.setDuration(duration);
-      toast.setText(message);
-    }
-    toast.setGravity(Gravity.CENTER, 0, 0);
-    toast.show();
-  }
-
-  @JSMethod(uiThread = true)
-  public void alert(JSONObject jsObj, final JSCallback callback) {
-
-    if (mWXSDKInstance.getContext() instanceof Activity) {
-
-      String message = "";
-      String okTitle = OK;
-      if (jsObj != null) {
-        try {
-          message = jsObj.getString(MESSAGE);
-          okTitle = jsObj.getString(OK_TITLE);
-        } catch (Exception e) {
-          WXLogUtils.e("[WXModalUIModule] alert param parse error ", e);
-        }
-      }
-      if (TextUtils.isEmpty(message)) {
-        message = "";
-      }
-      AlertDialog.Builder builder = new AlertDialog.Builder(mWXSDKInstance.getContext());
-      builder.setMessage(message);
-
-      final String okTitle_f = TextUtils.isEmpty(okTitle) ? OK : okTitle;
-      builder.setPositiveButton(okTitle_f, new OnClickListener() {
-        @Override
-        public void onClick(DialogInterface dialog, int which) {
-          if (callback != null) {
-            callback.invoke(okTitle_f);
-          }
-        }
-      });
-      AlertDialog alertDialog = builder.create();
-      alertDialog.setCanceledOnTouchOutside(false);
-      alertDialog.show();
-      tracking(alertDialog);
-    } else {
-      WXLogUtils.e("[WXModalUIModule] when call alert mWXSDKInstance.getContext() must instanceof Activity");
-    }
-  }
-
-  @JSMethod(uiThread = true)
-  public void confirm(JSONObject jsObj, final JSCallback callback) {
-
-    if (mWXSDKInstance.getContext() instanceof Activity) {
-      String message = "";
-      String okTitle = OK;
-      String cancelTitle = CANCEL;
-
-      if (jsObj != null) {
-        try {
-          message = jsObj.getString(MESSAGE);
-          okTitle = jsObj.getString(OK_TITLE);
-          cancelTitle = jsObj.getString(CANCEL_TITLE);
-        } catch (Exception e) {
-          WXLogUtils.e("[WXModalUIModule] confirm param parse error ", e);
-        }
-      }
-      if (TextUtils.isEmpty(message)) {
-        message = "";
-      }
-      AlertDialog.Builder builder = new AlertDialog.Builder(mWXSDKInstance.getContext());
-      builder.setMessage(message);
-
-      final String okTitleFinal = TextUtils.isEmpty(okTitle) ? OK : okTitle;
-      final String cancelTitleFinal = TextUtils.isEmpty(cancelTitle) ? CANCEL : cancelTitle;
-
-      builder.setPositiveButton(okTitleFinal, new OnClickListener() {
-        @Override
-        public void onClick(DialogInterface dialog, int which) {
-          if (callback != null) {
-            callback.invoke(okTitleFinal);
-          }
-        }
-      });
-      builder.setNegativeButton(cancelTitleFinal, new OnClickListener() {
-        @Override
-        public void onClick(DialogInterface dialog, int which) {
-          if (callback != null) {
-            callback.invoke(cancelTitleFinal);
-          }
-        }
-      });
-      AlertDialog alertDialog = builder.create();
-      alertDialog.setCanceledOnTouchOutside(false);
-      alertDialog.show();
-      tracking(alertDialog);
-    } else {
-      WXLogUtils.e("[WXModalUIModule] when call confirm mWXSDKInstance.getContext() must instanceof Activity");
-    }
-  }
-
-  @JSMethod(uiThread = true)
-  public void prompt(JSONObject jsObj, final JSCallback callback) {
-    if (mWXSDKInstance.getContext() instanceof Activity) {
-      String message = "";
-      String defaultValue = "";
-      String okTitle = OK;
-      String cancelTitle = CANCEL;
-
-      if (jsObj != null) {
-        try {
-          message = jsObj.getString(MESSAGE);
-          okTitle = jsObj.getString(OK_TITLE);
-          cancelTitle = jsObj.getString(CANCEL_TITLE);
-          defaultValue = jsObj.getString(DEFAULT);
-        } catch (Exception e) {
-          WXLogUtils.e("[WXModalUIModule] confirm param parse error ", e);
-        }
-      }
-
-      if (TextUtils.isEmpty(message)) {
-        message = "";
-      }
-      AlertDialog.Builder builder = new AlertDialog.Builder(mWXSDKInstance.getContext());
-      builder.setMessage(message);
-
-      final EditText editText = new EditText(mWXSDKInstance.getContext());
-      editText.setText(defaultValue);
-      builder.setView(editText);
-      final String okTitleFinal = TextUtils.isEmpty(okTitle) ? OK : okTitle;
-      final String cancelTitleFinal = TextUtils.isEmpty(cancelTitle) ? CANCEL : cancelTitle;
-      builder.setPositiveButton(okTitleFinal, new OnClickListener() {
-        @Override
-        public void onClick(DialogInterface dialog, int which) {
-          if (callback != null) {
-            Map<String, Object> result = new HashMap<String, Object>();
-            result.put(RESULT, okTitleFinal);
-            result.put(DATA, editText.getText().toString());
-            callback.invoke(result);
-          }
-        }
-      }).setNegativeButton(cancelTitleFinal, new OnClickListener() {
-        @Override
-        public void onClick(DialogInterface dialog, int which) {
-          if (callback != null) {
-            Map<String, Object> result = new HashMap<String, Object>();
-            result.put(RESULT, cancelTitleFinal);
-            result.put(DATA, editText.getText().toString());
-            callback.invoke(result);
-          }
-
-        }
-      });
-      AlertDialog alertDialog = builder.create();
-      alertDialog.setCanceledOnTouchOutside(false);
-      alertDialog.show();
-      tracking(alertDialog);
-    } else {
-      WXLogUtils.e("when call prompt mWXSDKInstance.getContext() must instanceof Activity");
-    }
-  }
-
-  private void tracking(Dialog dialog) {
-    activeDialog = dialog;
-    dialog.setOnDismissListener(new DialogInterface.OnDismissListener() {
-      @Override
-      public void onDismiss(DialogInterface dialog) {
-        activeDialog = null;
-      }
-    });
-  }
-
-  @Override
-  public void destroy() {
-    if (activeDialog != null && activeDialog.isShowing()) {
-      activeDialog.dismiss();
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXTimerModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/module/WXTimerModule.java
deleted file mode 100644
index aacd25a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXTimerModule.java
+++ /dev/null
@@ -1,217 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import static com.taobao.weex.bridge.WXBridgeManager.KEY_ARGS;
-import static com.taobao.weex.bridge.WXBridgeManager.KEY_METHOD;
-import static com.taobao.weex.bridge.WXBridgeManager.METHOD_CALLBACK;
-import static com.taobao.weex.bridge.WXBridgeManager.METHOD_CALL_JS;
-import static com.taobao.weex.common.WXJSBridgeMsgType.MODULE_INTERVAL;
-import static com.taobao.weex.common.WXJSBridgeMsgType.MODULE_TIMEOUT;
-
-import android.annotation.SuppressLint;
-import android.os.Handler;
-import android.os.Message;
-import android.support.annotation.FloatRange;
-import android.support.annotation.IntDef;
-import android.support.annotation.IntRange;
-import android.support.annotation.VisibleForTesting;
-import android.util.SparseArray;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.bridge.WXHashMap;
-import com.taobao.weex.bridge.WXJSObject;
-import com.taobao.weex.common.Destroyable;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.utils.WXJsonUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.util.ArrayList;
-import java.util.HashMap;
-import com.taobao.weex.utils.WXUtils;
-
-public class WXTimerModule extends WXModule implements Destroyable, Handler.Callback {
-
-  @IntDef({MODULE_TIMEOUT, MODULE_INTERVAL})
-  @Retention(RetentionPolicy.SOURCE)
-  @interface MessageType {}
-
-  private final static String TAG = "timer";
-  private Handler handler;
-  private SparseArray<Integer> antiIntAutoBoxing;
-
-  @SuppressLint("UseSparseArrays")
-  public WXTimerModule() {
-    handler = new Handler(WXBridgeManager.getInstance().getJSLooper(), this);
-    antiIntAutoBoxing = new SparseArray<>();
-  }
-
-
-  @JSMethod(uiThread = false)
-  public void setTimeout(@IntRange(from = 1) int funcId, @FloatRange(from = 0) float delay) {
-    if(mWXSDKInstance != null) {
-      postOrHoldMessage(MODULE_TIMEOUT, funcId, (int) delay, WXUtils.parseInt(mWXSDKInstance.getInstanceId()));
-      if (null != mWXSDKInstance.getWXPerformance()){
-        mWXSDKInstance.getWXPerformance().timerInvokeCount++;
-      }
-      mWXSDKInstance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_TIMER_NUM,1);
-    }
-  }
-
-  @JSMethod(uiThread = false)
-  public void setInterval(@IntRange(from = 1) int funcId, @FloatRange(from = 0) float interval) {
-    if(mWXSDKInstance != null) {
-      postOrHoldMessage(MODULE_INTERVAL, funcId, (int) interval, WXUtils.parseInt(mWXSDKInstance.getInstanceId()));
-      if (null != mWXSDKInstance.getWXPerformance()){
-        mWXSDKInstance.getWXPerformance().timerInvokeCount++;
-      }
-      mWXSDKInstance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_TIMER_NUM,1);
-    }
-  }
-
-  @JSMethod(uiThread = false)
-  public void clearTimeout(@IntRange(from = 1) int funcId) {
-    if (funcId <= 0) {
-      return;
-    }
-    removeOrHoldMessage(MODULE_TIMEOUT, funcId);
-  }
-
-  @JSMethod(uiThread = false)
-  public void clearInterval(@IntRange(from = 1) int funcId) {
-    if (funcId <= 0) {
-      return;
-    }
-    removeOrHoldMessage(MODULE_INTERVAL, funcId);
-  }
-
-  @Override
-  public void destroy() {
-    if (handler != null) {
-      if(WXEnvironment.isApkDebugable()) {
-        WXLogUtils.d(TAG, "Timer Module removeAllMessages: ");
-      }
-      handler.removeCallbacksAndMessages(null);
-      antiIntAutoBoxing.clear();
-    }
-  }
-
-  @Override
-  public boolean handleMessage(Message msg) {
-    boolean ret = false;
-    WXJSObject[] args;
-    if (msg != null) {
-      int what = msg.what;
-      if(WXEnvironment.isApkDebugable()) {
-        WXLogUtils.d(TAG, "Timer Module handleMessage : " + msg.what);
-      }
-      switch (what) {
-        case MODULE_TIMEOUT:
-          if (msg.obj == null) {
-            break;
-          }
-          checkIfTimerInBack(msg.arg1);
-          args = createTimerArgs(msg.arg1, (Integer) msg.obj, false);
-          WXBridgeManager.getInstance().invokeExecJS(String.valueOf(msg.arg1), null, METHOD_CALL_JS, args, true);
-          ret = true;
-          break;
-        case MODULE_INTERVAL:
-          if (msg.obj == null) {
-            break;
-          }
-          checkIfTimerInBack(msg.arg1);
-          postMessage(MODULE_INTERVAL, (Integer) msg.obj, msg.arg2, msg.arg1);
-          args = createTimerArgs(msg.arg1, (Integer) msg.obj, true);
-          WXBridgeManager.getInstance().invokeExecJS(String.valueOf(msg.arg1), null, METHOD_CALL_JS, args, true);
-          ret = true;
-          break;
-        default:
-          break;
-      }
-    }
-    return ret;
-  }
-
-  private void checkIfTimerInBack(int instanceId){
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(String.valueOf(instanceId));
-    if (null == instance){
-      return;
-    }
-    if (instance.isViewDisAppear()){
-      instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_TIMER_BACK_NUM,1);
-    }
-  }
-
-  @VisibleForTesting
-  void setHandler(Handler handler) {
-    this.handler = handler;
-  }
-
-  private WXJSObject[] createTimerArgs(int instanceId, int funcId, boolean keepAlive) {
-    ArrayList<Object> argsList = new ArrayList<>();
-    argsList.add(funcId);
-    argsList.add(new HashMap<>());
-    argsList.add(keepAlive);
-    WXHashMap<String, Object> task = new WXHashMap<>();
-    task.put(KEY_METHOD, METHOD_CALLBACK);
-    task.put(KEY_ARGS, argsList);
-    Object[] tasks = {task};
-    return new WXJSObject[]{
-            new WXJSObject(WXJSObject.String, String.valueOf(instanceId)),
-            new WXJSObject(WXJSObject.JSON,
-                    WXJsonUtils.fromObjectToJSONString(tasks))};
-  }
-
-  private void postOrHoldMessage(@MessageType final int what,final int funcId,final int interval,final int instanceId) {
-    if(mWXSDKInstance.isPreRenderMode()) {
-      postMessage(what,funcId,interval,instanceId);
-    } else {
-      postMessage(what,funcId,interval,instanceId);
-    }
-  }
-
-  private void removeOrHoldMessage(@MessageType final int what,final int funcId) {
-    if(mWXSDKInstance.isPreRenderMode()) {
-      handler.removeMessages(what, antiIntAutoBoxing.get(funcId, funcId));
-    } else {
-      handler.removeMessages(what, antiIntAutoBoxing.get(funcId, funcId));
-    }
-  }
-
-  private void postMessage(@MessageType int what,
-                           @IntRange(from = 1) int funcId,
-                           @IntRange(from = 0) int interval, int instanceId) {
-    if (interval < 0 || funcId <= 0) {
-      WXLogUtils.e(TAG, "interval < 0 or funcId <=0");
-    } else {
-      if(antiIntAutoBoxing.get(funcId) == null) {
-        antiIntAutoBoxing.put(funcId, funcId);
-      }
-      Message message = handler
-              .obtainMessage(what, instanceId, interval, antiIntAutoBoxing.get(funcId));
-      handler.sendMessageDelayed(message, interval);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXWebViewModule.java b/android/sdk/src/main/java/com/taobao/weex/ui/module/WXWebViewModule.java
deleted file mode 100644
index 9878c85..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/module/WXWebViewModule.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.common.WXModule;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXWeb;
-
-public class WXWebViewModule extends WXModule{
-
-    private enum Action {
-        reload,
-        goBack,
-        goForward,
-        postMessage
-    }
-
-    @JSMethod(uiThread = true)
-    public void goBack(String ref) {
-        action(Action.goBack, ref);
-    }
-
-    @JSMethod(uiThread = true)
-    public void goForward(String ref) {
-        action(Action.goForward, ref);
-    }
-
-    @JSMethod(uiThread = true)
-    public void reload(String ref) {
-        action(Action.reload, ref);
-    }
-
-    @JSMethod(uiThread = true)
-    public void postMessage(String ref, Object msg) {
-        action(Action.postMessage, ref, msg);
-    }
-
-    private void action(Action action, String ref, Object data) {
-        WXComponent webComponent =
-            WXSDKManager.getInstance()
-                .getWXRenderManager()
-                .getWXComponent(mWXSDKInstance.getInstanceId(), ref);
-        if(webComponent instanceof WXWeb) {
-            ((WXWeb) webComponent).setAction(action.name(), data);
-        }
-    }
-
-    private void action(Action action, String ref) {
-        action(action, ref, null);
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/BaseFrameLayout.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/BaseFrameLayout.java
deleted file mode 100644
index e12d52e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/BaseFrameLayout.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.drawable.Drawable;
-import android.support.annotation.NonNull;
-import android.widget.FrameLayout;
-import com.taobao.weex.ui.flat.widget.Widget;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import java.util.List;
-
-public class BaseFrameLayout extends FrameLayout{
-    private List<Widget> mWidgets;
-
-    public BaseFrameLayout(Context context){
-        super(context);
-    }
-
-    @Override
-    protected void dispatchDraw(Canvas canvas) {
-        try {
-            dispatchDrawInterval(canvas);
-        } catch (Throwable e) {
-            WXLogUtils.e(WXLogUtils.getStackTrace(e));
-        }
-    }
-
-    protected void dispatchDrawInterval(Canvas canvas) {
-        if (mWidgets != null) {
-            canvas.save();
-            canvas.translate(getPaddingLeft(), getPaddingTop());
-            for (Widget widget : mWidgets) {
-                widget.draw(canvas);
-            }
-            canvas.restore();
-        } else {
-            WXViewUtils.clipCanvasWithinBorderBox(this, canvas);
-            super.dispatchDraw(canvas);
-        }
-    }
-    public void mountFlatGUI(List<Widget> widgets){
-        this.mWidgets = widgets;
-        if (mWidgets != null) {
-            setWillNotDraw(true);
-        }
-        invalidate();
-    }
-
-    public void unmountFlatGUI(){
-        mWidgets = null;
-        setWillNotDraw(false);
-        invalidate();
-    }
-
-    @Override
-    protected boolean verifyDrawable(@NonNull Drawable who) {
-        return mWidgets != null || super.verifyDrawable(who);
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/IRenderResult.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/IRenderResult.java
deleted file mode 100644
index dab1106..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/IRenderResult.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-
-import com.taobao.weex.ui.component.WXComponent;
-
-public interface IRenderResult<T extends WXComponent> {
-    T getComponent();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/IRenderStatus.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/IRenderStatus.java
deleted file mode 100644
index f61b0fa..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/IRenderStatus.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.ui.view;
-
-
-import com.taobao.weex.ui.component.WXComponent;
-
-public interface IRenderStatus<T extends WXComponent> {
-
-  public void holdComponent(T component);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/IWXScroller.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/IWXScroller.java
deleted file mode 100644
index 942c7aa..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/IWXScroller.java
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-public interface IWXScroller {
-
-  void destroy();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/IWXTextView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/IWXTextView.java
deleted file mode 100644
index 60b2533..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/IWXTextView.java
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-public interface IWXTextView {
-
-  CharSequence getText();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/IWebView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/IWebView.java
deleted file mode 100644
index b3bc8e7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/IWebView.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.view.View;
-
-import java.util.Map;
-
-public interface IWebView {
-    public View getView();
-    public void destroy();
-    public void loadUrl(String url);
-    public void loadDataWithBaseURL(String source);
-    public void reload();
-    public void goBack();
-    public void goForward();
-    public void postMessage(Object msg);
-    public void setShowLoading(boolean shown);
-    public void setOnErrorListener(OnErrorListener listener);
-    public void setOnPageListener(OnPageListener listener);
-    public void setOnMessageListener(OnMessageListener listener);
-
-    public interface OnErrorListener {
-        public void onError(String type, Object message);
-    }
-
-    public interface OnPageListener {
-        public void onReceivedTitle(String title);
-        public void onPageStart(String url);
-        public void onPageFinish(String url, boolean canGoBack, boolean canGoForward);
-    }
-
-    public interface OnMessageListener {
-        public void onMessage(Map<String, Object> params);
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXBaseCircleIndicator.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXBaseCircleIndicator.java
deleted file mode 100644
index 43264bd..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXBaseCircleIndicator.java
+++ /dev/null
@@ -1,228 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Paint.Style;
-import android.support.v4.view.ViewPager;
-import android.support.v4.view.ViewPager.OnPageChangeListener;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-import android.widget.FrameLayout;
-
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import com.taobao.weex.utils.WXViewUtils;
-
-
-public class WXBaseCircleIndicator extends FrameLayout implements WXGestureObservable {
-
-  private final Paint mPaintPage = new Paint();
-  private final Paint mPaintFill = new Paint();
-  private WXGesture wxGesture;
-  private WXCircleViewPager mCircleViewPager;
-
-  /**
-   * Radius of the circle
-   */
-  private float radius;
-  /**
-   * Padding of the circle
-   */
-  private float circlePadding;
-  /**
-   * Fill color of unselected circle
-   */
-  private int pageColor = Color.LTGRAY;
-  /**
-   * Fill color of the selected circle
-   */
-  private int fillColor = Color.DKGRAY;
-  private int realCurrentItem;
-
-  private OnPageChangeListener mListener;
-
-
-  public WXBaseCircleIndicator(Context context) {
-    super(context);
-    init();
-  }
-
-  private void init() {
-    radius = WXViewUtils.dip2px(5);
-    circlePadding = WXViewUtils.dip2px(5);
-    pageColor = Color.LTGRAY;
-    fillColor = Color.DKGRAY;
-
-    mPaintFill.setStyle(Style.FILL);
-    mPaintFill.setAntiAlias(true);
-    mPaintPage.setAntiAlias(true);
-    mPaintPage.setColor(pageColor);
-    mPaintFill.setStyle(Style.FILL);
-    mPaintFill.setColor(fillColor);
-    this.setWillNotDraw(false);
-
-  }
-
-  /**
-   * @param context
-   * @param attrs
-   */
-  public WXBaseCircleIndicator(Context context, AttributeSet attrs) {
-    super(context, attrs);
-    init();
-  }
-
-  /**
-   * @param viewPager the mCircleViewPager to set
-   */
-  public void setCircleViewPager(WXCircleViewPager viewPager) {
-    mCircleViewPager = viewPager;
-    if (mCircleViewPager != null) {
-      if (mListener == null) {
-        mListener = new ViewPager.SimpleOnPageChangeListener() {
-          @Override
-          public void onPageSelected(int position) {
-            realCurrentItem = mCircleViewPager.getRealCurrentItem();
-            invalidate();
-          }
-        };
-      }
-      this.mCircleViewPager.addOnPageChangeListener(mListener);
-      this.realCurrentItem = mCircleViewPager.getRealCurrentItem();
-      if (realCurrentItem < 0) {
-        realCurrentItem = 0;
-      }
-    }
-    requestLayout();
-  }
-
-  /**
-   * @param radius the radius to set
-   */
-  public void setRadius(float radius) {
-    this.radius = radius;
-  }
-
-  /**
-   * @param fillColor the fillColor to set
-   */
-  public void setFillColor(int fillColor) {
-    this.fillColor = fillColor;
-    mPaintFill.setColor(fillColor);
-  }
-
-  public void setPageColor(int pageColor) {
-    this.pageColor = pageColor;
-    mPaintPage.setColor(pageColor);
-  }
-
-  /**
-   * @return the realCurrentItem
-   */
-  public int getRealCurrentItem() {
-    return realCurrentItem;
-  }
-
-  /**
-   * @param realCurrentItem the realCurrentItem to set
-   */
-  public void setRealCurrentItem(int realCurrentItem) {
-    this.realCurrentItem = realCurrentItem;
-    invalidate();
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  @Override
-  public boolean dispatchTouchEvent(MotionEvent event) {
-    boolean result = super.dispatchTouchEvent(event);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, event);
-    }
-    return result;
-  }
-
-  @Override
-  protected void onDraw(Canvas canvas) {
-    super.onDraw(canvas);
-
-    float dotWidth = (circlePadding + radius) * 2;
-
-    float firstCenterX = getWidth() / 2 - (dotWidth * (getCount() - 1) / 2);
-    float firstCenterY = getHeight() / 2 + getPaddingTop();
-
-    for (int i = 0; i < getCount(); i++) {
-      float dx = firstCenterX + dotWidth * i;
-      float dy = firstCenterY;
-      if (i != realCurrentItem) {
-        canvas.drawCircle(dx, dy, radius, mPaintPage);
-      } else {
-        canvas.drawCircle(dx, dy, radius, mPaintFill);
-      }
-    }
-  }
-
-  @Override
-  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
-
-    int viewWidth;
-    int viewHeight;
-
-    int widthMode = MeasureSpec.getMode(widthMeasureSpec);
-    int widthSize = MeasureSpec.getSize(widthMeasureSpec);
-    int heightMode = MeasureSpec.getMode(heightMeasureSpec);
-    int heightSize = MeasureSpec.getSize(heightMeasureSpec);
-
-    if (widthMode == MeasureSpec.EXACTLY) {
-      viewWidth = widthSize;
-    } else {
-      viewWidth = (int) (getPaddingLeft() + radius * 2 * getCount() + circlePadding * (getCount() - 1) + getPaddingRight()) + 1;
-    }
-
-    if (heightMode == MeasureSpec.EXACTLY) {
-      viewHeight = heightSize;
-    } else {
-      viewHeight = (int) (getPaddingTop() + radius * 2 + getPaddingBottom()) + 1;
-    }
-    setMeasuredDimension(viewWidth, viewHeight);
-  }
-
-  /**
-   * @return the count
-   */
-  public int getCount() {
-    if (mCircleViewPager == null || mCircleViewPager.getAdapter() == null) {
-      return 0;
-    }
-    return mCircleViewPager.getRealCount();
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXBaseRefreshLayout.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXBaseRefreshLayout.java
deleted file mode 100644
index ff45491..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXBaseRefreshLayout.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.content.Context;
-
-public class WXBaseRefreshLayout extends WXFrameLayout {
-
-  public WXBaseRefreshLayout(Context context) {
-    super(context);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCircleIndicator.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCircleIndicator.java
deleted file mode 100644
index b3acdb7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCircleIndicator.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.content.Context;
-
-public class WXCircleIndicator extends WXBaseCircleIndicator {
-
-  public WXCircleIndicator(Context context) {
-    super(context);
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCirclePageAdapter.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCirclePageAdapter.java
deleted file mode 100644
index 1b5b219..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCirclePageAdapter.java
+++ /dev/null
@@ -1,203 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.support.v4.view.PagerAdapter;
-import android.view.View;
-import android.view.ViewGroup;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.List;
-
-public class WXCirclePageAdapter extends PagerAdapter {
-
-  /**
-   * Subviews
-   */
-  private List<View> views = new ArrayList<>();
-  private List<View> shadow = new ArrayList<>();
-  private boolean needLoop = true;
-
-  public boolean isRTL = false;
-  private List<View> originalViews = new ArrayList<>();
-
-  public WXCirclePageAdapter(List<View> views, boolean needLoop) {
-    super();
-    this.views = new ArrayList<>(views);
-    this.originalViews = new ArrayList<>(views);
-    this.needLoop = needLoop;
-  }
-
-  public void setLayoutDirectionRTL(boolean isRTL) {
-    if (isRTL == this.isRTL) return;
-    this.isRTL = isRTL;
-    this.views = new ArrayList<>(this.originalViews);
-    if (isRTL) {
-      Collections.reverse(this.views);
-    }
-    ensureShadow();
-  }
-
-  public WXCirclePageAdapter() {
-    this(true);
-  }
-
-  public WXCirclePageAdapter(boolean needLoop) {
-    super();
-    this.needLoop = needLoop;
-  }
-
-  public void addPageView(View view) {
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("onPageSelected >>>> addPageView");
-    }
-
-    originalViews.add(view);
-    if (this.isRTL) {
-      views.add(0, view);
-    } else {
-      views.add(view);
-    }
-    ensureShadow();
-  }
-
-  public void removePageView(View view) {
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("onPageSelected >>>> removePageView");
-    }
-    views.remove(view);
-    originalViews.remove(view);
-    ensureShadow();
-  }
-
-  public void replacePageView(View oldView, View newView) {
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("onPageSelected >>>> replacePageView");
-    }
-
-    int index = views.indexOf(oldView);
-    views.remove(index);
-    views.add(index, newView);
-    ensureShadow();
-
-    index = originalViews.indexOf(oldView);
-    originalViews.remove(index);
-    originalViews.add(index, newView);
-  }
-
-  @Override
-  public int getCount() {
-    return shadow.size();
-  }
-
-  public int getRealCount() {
-    return views.size();
-  }
-
-  @Override
-  public Object instantiateItem(ViewGroup container, int position) {
-    View pageView = null;
-    try {
-      pageView = shadow.get(position);
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.d("onPageSelected >>>> instantiateItem >>>>> position:" + position + ",position % getRealCount()" + position % getRealCount());
-      }
-      if (pageView.getParent() == null) {
-        container.addView(pageView);
-      } else {
-        ((ViewGroup) pageView.getParent()).removeView(pageView);
-        container.addView(pageView);
-      }
-    } catch (Exception e) {
-      WXLogUtils.e("[CirclePageAdapter] instantiateItem: ", e);
-    }
-    return pageView;
-  }
-
-  @Override
-  public void destroyItem(ViewGroup container, int position, Object object) {
-    if (WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("onPageSelected >>>> destroyItem >>>>> position:" + position);
-    }
-    // container.removeView((View) object);
-  }
-
-  @Override
-  public boolean isViewFromObject(View view, Object object) {
-    return view == object;
-  }
-
-  @Override
-  public int getItemPosition(Object object) {
-    return POSITION_NONE;
-  }
-
-  public int getPagePosition(View page) {
-    return views.indexOf(page);
-  }
-
-  public int getItemIndex(Object object) {
-    if (object instanceof View) {
-      return views.indexOf(object);
-    } else {
-      return -1;
-    }
-  }
-
-  public List<View> getViews(){
-    return views;
-  }
-
-  private void ensureShadow() {
-    List<View> temp = new ArrayList<>();
-    if (needLoop && views.size() > 2) {
-      temp.add(0, views.get(views.size() - 1));
-      for (View view : views) {
-        temp.add(view);
-      }
-      temp.add(views.get(0));
-    } else {
-      temp.addAll(views);
-    }
-    shadow.clear();
-    notifyDataSetChanged();
-    shadow.addAll(temp);
-    notifyDataSetChanged();
-  }
-
-  public int getRealPosition(int shadowPosition) {
-    if (shadowPosition < 0 || shadowPosition >= shadow.size()) {
-      return -1;
-    } else {
-      return getItemIndex(shadow.get(shadowPosition));
-    }
-  }
-
-  public int getFirst() {
-    if (needLoop && views.size() > 2) {
-      return 1;
-    } else {
-      return 0;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCircleViewPager.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCircleViewPager.java
deleted file mode 100644
index fc48fe4..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXCircleViewPager.java
+++ /dev/null
@@ -1,341 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.os.Handler;
-import android.os.Looper;
-import android.os.Message;
-import android.support.v4.view.PagerAdapter;
-import android.support.v4.view.ViewPager;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.animation.Interpolator;
-
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.lang.reflect.Field;
-
-/**
- */
-@SuppressLint("HandlerLeak")
-public class WXCircleViewPager extends ViewPager implements WXGestureObservable {
-
-  private final int SCROLL_TO_NEXT = 1;
-  private WXGesture wxGesture;
-  private boolean isAutoScroll;
-  private long intervalTime = 3 * 1000;
-  private WXSmoothScroller mScroller;
-  private boolean needLoop = true;
-  private boolean scrollable = true;
-  private int mState = ViewPager.SCROLL_STATE_IDLE;
-  private Handler mAutoScrollHandler = new Handler(Looper.getMainLooper()) {
-    @Override
-    public void handleMessage(Message msg) {
-      if (msg.what == SCROLL_TO_NEXT) {
-        WXLogUtils.d("[CircleViewPager] trigger auto play action");
-        showNextItem();
-        this.sendEmptyMessageDelayed(SCROLL_TO_NEXT, intervalTime);
-        return;
-      }
-      super.handleMessage(msg);
-    }
-  };
-
-  @SuppressLint("NewApi")
-  public WXCircleViewPager(Context context) {
-    super(context);
-    init();
-  }
-
-  private void init() {
-    setOverScrollMode(View.OVER_SCROLL_NEVER);
-
-    addOnPageChangeListener(new OnPageChangeListener() {
-      @Override
-      public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
-
-      }
-
-      @Override
-      public void onPageSelected(int position) {
-
-      }
-
-      @Override
-      public void onPageScrollStateChanged(int state) {
-        mState = state;
-        WXCirclePageAdapter adapter = getCirclePageAdapter();
-        int currentItemInternal = WXCircleViewPager.super.getCurrentItem();
-        if (needLoop && state == ViewPager.SCROLL_STATE_IDLE && adapter.getCount() > 1) {
-          if (currentItemInternal == adapter.getCount() - 1) {
-            superSetCurrentItem(1, false);
-          } else if (currentItemInternal == 0) {
-            superSetCurrentItem(adapter.getCount() - 2, false);
-          }
-        }
-      }
-    });
-
-    postInitViewPager();
-  }
-
-  /**
-   * Override the Scroller instance with our own class so we can change the
-   * duration
-   */
-  private void postInitViewPager() {
-    if (isInEditMode()) {
-      return;
-    }
-    try {
-      Field scroller = ViewPager.class.getDeclaredField("mScroller");
-      scroller.setAccessible(true);
-      Field interpolator = ViewPager.class
-              .getDeclaredField("sInterpolator");
-      interpolator.setAccessible(true);
-
-      mScroller = new WXSmoothScroller(getContext(),
-              (Interpolator) interpolator.get(null));
-      scroller.set(this, mScroller);
-    } catch (Exception e) {
-      WXLogUtils.e("[CircleViewPager] postInitViewPager: ", e);
-    }
-  }
-
-  @SuppressLint("NewApi")
-  public WXCircleViewPager(Context context, AttributeSet attrs) {
-    super(context, attrs);
-    init();
-  }
-
-  @Override
-  public int getCurrentItem() {
-    return getRealCurrentItem();
-  }
-
-  public int superGetCurrentItem() {
-    return super.getCurrentItem();
-  }
-
-  @Override
-  public boolean onInterceptTouchEvent(MotionEvent ev) {
-    try {
-      return scrollable && super.onInterceptTouchEvent(ev);
-    } catch (IllegalArgumentException e) {
-      e.printStackTrace();
-    } catch (ArrayIndexOutOfBoundsException e) {
-      e.printStackTrace();
-    }
-    return false;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent ev) {
-    if(!scrollable) {
-      return true;
-    }
-    return super.onTouchEvent(ev);
-  }
-
-  @Override
-  public void scrollTo(int x, int y) {
-    if(scrollable || mState != ViewPager.SCROLL_STATE_DRAGGING) {
-      super.scrollTo(x, y);
-    }
-  }
-
-  /**
-   * Start auto scroll. Must be called after {@link #setAdapter(PagerAdapter)}
-   */
-  public void startAutoScroll() {
-    isAutoScroll = true;
-    mAutoScrollHandler.removeCallbacksAndMessages(null);
-    mAutoScrollHandler.sendEmptyMessageDelayed(SCROLL_TO_NEXT, intervalTime);
-  }
-
-  public void pauseAutoScroll(){
-    mAutoScrollHandler.removeCallbacksAndMessages(null);
-  }
-
-  /**
-   * Stop auto scroll.
-   */
-  public void stopAutoScroll() {
-    isAutoScroll = false;
-    mAutoScrollHandler.removeCallbacksAndMessages(null);
-  }
-
-  public boolean isAutoScroll() {
-    return isAutoScroll;
-  }
-
-  @Override
-  public void setCurrentItem(int item) {
-    setRealCurrentItem(item);
-  }
-
-  /**
-   * @return the circlePageAdapter
-   */
-  public WXCirclePageAdapter getCirclePageAdapter() {
-    return (WXCirclePageAdapter) getAdapter();
-  }
-
-  /**
-   * @param circlePageAdapter the circlePageAdapter to set
-   */
-  public void setCirclePageAdapter(WXCirclePageAdapter circlePageAdapter) {
-    this.setAdapter(circlePageAdapter);
-  }
-
-  /**
-   * Get auto scroll interval. The time unit is micro second.
-   * The default time interval is 3000 micro second
-   * @return the intervalTime
-   */
-  public long getIntervalTime() {
-    return intervalTime;
-  }
-
-  /**
-   * Set auto scroll interval. The time unit is micro second.
-   * The default time interval is 3000 micro second
-   * @param intervalTime the intervalTime to set
-   */
-  public void setIntervalTime(long intervalTime) {
-    this.intervalTime = intervalTime;
-  }
-
-  public void setCircle(boolean circle) {
-    needLoop = circle;
-  }
-
-  @Override
-  public boolean dispatchTouchEvent(MotionEvent ev) {
-    switch (ev.getAction()) {
-      case MotionEvent.ACTION_DOWN:
-      case MotionEvent.ACTION_MOVE:
-        mAutoScrollHandler.removeCallbacksAndMessages(null);
-        break;
-      case MotionEvent.ACTION_UP:
-      case MotionEvent.ACTION_CANCEL:
-        if (isAutoScroll()) {
-          mAutoScrollHandler.sendEmptyMessageDelayed(SCROLL_TO_NEXT, intervalTime);
-        }
-        break;
-    }
-    try{
-      boolean result = super.dispatchTouchEvent(ev);
-      if (wxGesture != null) {
-        result |= wxGesture.onTouch(this, ev);
-      }
-      return result;
-    }catch (Exception e){
-      return  false;
-    }
-  }
-
-  public void destory() {
-    mAutoScrollHandler.removeCallbacksAndMessages(null);
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  public int getRealCurrentItem() {
-    int i = super.getCurrentItem();
-    return ((WXCirclePageAdapter) getAdapter()).getRealPosition(i);
-  }
-
-  private void setRealCurrentItem(int item) {
-    superSetCurrentItem(((WXCirclePageAdapter) getAdapter()).getFirst() + item, false);
-  }
-
-  private void superSetCurrentItem(int item, boolean smooth) {
-    try {
-      super.setCurrentItem(item, smooth);
-    } catch (IllegalStateException e) {
-      WXLogUtils.e(e.toString());
-      if (getAdapter() != null) {
-        getAdapter().notifyDataSetChanged();
-        super.setCurrentItem(item, smooth);
-      }
-    }
-  }
-
-  public int getRealCount() {
-    return ((WXCirclePageAdapter) getAdapter()).getRealCount();
-  }
-
-  @Override
-  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
-    try {
-      super.onMeasure(widthMeasureSpec, heightMeasureSpec);
-    } catch (IllegalStateException e) {
-      WXLogUtils.e(e.toString());
-      if (getAdapter() != null) {
-        getAdapter().notifyDataSetChanged();
-        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
-      }
-    }
-  }
-
-  public boolean isScrollable() {
-    return scrollable;
-  }
-
-  public void setScrollable(boolean scrollable) {
-    this.scrollable = scrollable;
-  }
-
-  private void showNextItem() {
-    if (this.getCirclePageAdapter() != null && this.getCirclePageAdapter().isRTL) {
-      if (!needLoop && superGetCurrentItem() == 0) {
-        return;
-      }
-      if (getRealCount() == 2 && superGetCurrentItem() == 0) {
-        superSetCurrentItem(1, true);
-      } else {
-        superSetCurrentItem(superGetCurrentItem() - 1, true);
-      }
-    } else {
-      if (!needLoop && superGetCurrentItem() == getRealCount() - 1) {
-        return;
-      }
-      if (getRealCount() == 2 && superGetCurrentItem() == 1) {
-        superSetCurrentItem(0, true);
-      } else {
-        superSetCurrentItem(superGetCurrentItem() + 1, true);
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXEditText.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXEditText.java
deleted file mode 100644
index 3607c41..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXEditText.java
+++ /dev/null
@@ -1,156 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.os.Build;
-import android.view.ActionMode;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.MotionEvent;
-import android.view.ViewParent;
-import android.widget.EditText;
-
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-
-/**
- * Wrapper class for editText
- */
-@SuppressLint("AppCompatCustomView")
-public class WXEditText extends EditText implements WXGestureObservable {
-
-  private WXGesture wxGesture;
-  private int mLines = 1;
-  private boolean mAllowDisableMovement = true;
-  private boolean mAllowCopyPaste = true;
-
-  public WXEditText(Context context) {
-    super(context);
-    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
-      setBackground(null);
-    } else {
-      setBackgroundDrawable(null);
-    }
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  @Override
-  public void setLines(int lines) {
-    super.setLines(lines);
-    mLines = lines;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent event) {
-    boolean result = super.onTouchEvent(event);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, event);
-    }
-
-    ViewParent parent = getParent();
-    if(parent != null){
-      switch (event.getAction() & MotionEvent.ACTION_MASK){
-        case MotionEvent.ACTION_DOWN:
-          if(mLines < getLineCount()) {
-            //scrollable
-            parent.requestDisallowInterceptTouchEvent(true);
-          }
-          break;
-        case MotionEvent.ACTION_UP:
-        case MotionEvent.ACTION_CANCEL:
-          parent.requestDisallowInterceptTouchEvent(false);
-          break;
-      }
-    }
-    return result;
-  }
-
-  @Override
-  protected void onSizeChanged(int w, int h, int oldw, int oldh) {
-    super.onSizeChanged(w, h, oldw, oldh);
-    if (getLayout() != null) {
-      int contentH = getLayout().getHeight();
-      //TODO: known issue,set movement to null will make cursor disappear.
-      if (mAllowDisableMovement && h < contentH) {
-        setMovementMethod(null);
-      } else {
-        setMovementMethod(getDefaultMovementMethod());
-      }
-    }
-  }
-
-  public void setAllowDisableMovement(boolean allow) {
-    mAllowDisableMovement = allow;
-  }
-
-  public void setAllowCopyPaste(boolean allow) {
-    mAllowCopyPaste = allow;
-    if (allow) {
-      setLongClickable(true);
-      setCustomSelectionActionModeCallback(null);
-      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
-        setCustomInsertionActionModeCallback(null);
-      }
-    } else {
-      setLongClickable(false);
-      ActionMode.Callback callback = new ActionMode.Callback() {
-        @Override
-        public boolean onCreateActionMode(ActionMode mode, Menu menu) {
-          return false;
-        }
-
-        @Override
-        public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
-          return false;
-        }
-
-        @Override
-        public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
-          return false;
-        }
-
-        @Override
-        public void onDestroyActionMode(ActionMode mode) {
-
-        }
-      };
-      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
-        setCustomInsertionActionModeCallback(callback);
-      }
-      setCustomSelectionActionModeCallback(callback);
-    }
-  }
-
-  @Override
-  public boolean onTextContextMenuItem(int id) {
-    return !mAllowCopyPaste || super.onTextContextMenuItem(id);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXFrameLayout.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXFrameLayout.java
deleted file mode 100644
index 04b8257..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXFrameLayout.java
+++ /dev/null
@@ -1,140 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.support.annotation.Nullable;
-import android.view.MotionEvent;
-import android.view.View;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXDiv;
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import com.taobao.weex.utils.WXExceptionUtils;
-import com.taobao.weex.utils.WXLogUtils;
-import java.lang.ref.WeakReference;
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * FrameLayout wrapper
- *
- */
-public class WXFrameLayout extends BaseFrameLayout implements WXGestureObservable,IRenderStatus<WXDiv>,IRenderResult<WXDiv>{
-
-  private WeakReference<WXDiv> mWeakReference;
-  private WXGesture wxGesture;
-
-
-  public WXFrameLayout(Context context) {
-    super(context);
-  }
-
-  @Nullable
-  @Override
-  public WXDiv getComponent() {
-    return null != mWeakReference ? mWeakReference.get() : null;
-  }
-
-  @Override
-  public void holdComponent(WXDiv component) {
-    mWeakReference = new WeakReference<WXDiv>(component);
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  @Override
-  public boolean dispatchTouchEvent(MotionEvent event) {
-    boolean result = super.dispatchTouchEvent(event);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, event);
-    }
-    return result;
-  }
-  @Override
-  protected void dispatchDraw(Canvas canvas) {
-    try {
-      super.dispatchDrawInterval(canvas);
-    } catch (Throwable e) {
-      if (getComponent() != null) {
-        notifyLayerOverFlow();
-        if (null != getComponent()){
-          WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(getComponent().getInstanceId());
-          if (null != instance && null != instance.getApmForInstance() &&!instance.getApmForInstance().hasReportLayerOverDraw){
-            instance.getApmForInstance().hasReportLayerOverDraw = true;
-            reportLayerOverFlowError();
-          }
-        }
-      }
-      WXLogUtils.e("Layer overflow limit error", WXLogUtils.getStackTrace(e));
-    }
-  }
-  private int reportLayerOverFlowError() {
-    int deep = calLayerDeep(this, 0);
-    if (getComponent() != null) {
-      WXExceptionUtils.commitCriticalExceptionRT(getComponent().getInstanceId(),
-              WXErrorCode.WX_RENDER_ERR_LAYER_OVERFLOW,
-              "draw android view",
-              WXErrorCode.WX_RENDER_ERR_LAYER_OVERFLOW.getErrorMsg() + "Layer overflow limit error: " + deep + " layers!",
-              null);
-    }
-    return deep;
-  }
-  private int calLayerDeep(View view, int deep) {
-    deep++;
-    if (view.getParent() != null && view.getParent() instanceof View) {
-      return calLayerDeep((View) view.getParent(), deep);
-    }
-    return deep;
-  }
-
-  public void notifyLayerOverFlow() {
-    if (getComponent() == null)
-      return;
-
-    WXSDKInstance instance = getComponent().getInstance();
-    if (instance == null)
-      return;
-
-    if (instance.getLayerOverFlowListeners() == null)
-      return;
-
-    for (String ref : instance.getLayerOverFlowListeners()) {
-      WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(instance.getInstanceId(), ref);
-      Map<String, Object> params = new HashMap<>();
-      params.put(Constants.Weex.REF, ref);
-      params.put(Constants.Weex.INSTANCEID, component.getInstanceId());
-      component.fireEvent(Constants.Event.LAYEROVERFLOW, params);
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXHorizontalScrollView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXHorizontalScrollView.java
deleted file mode 100644
index 8ae842d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXHorizontalScrollView.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.graphics.Rect;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-import android.view.View;
-import android.widget.HorizontalScrollView;
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import java.util.List;
-import java.util.concurrent.CopyOnWriteArrayList;
-
-public class WXHorizontalScrollView extends HorizontalScrollView implements IWXScroller, WXGestureObservable {
-
-  private WXGesture wxGesture;
-  private ScrollViewListener mScrollViewListener;
-  private List<ScrollViewListener> mScrollViewListeners;
-  private boolean scrollable = true;
-
-  public WXHorizontalScrollView(Context context) {
-    super(context);
-    init();
-  }
-
-  private void init() {
-    setWillNotDraw(false);
-    setOverScrollMode(View.OVER_SCROLL_NEVER);
-  }
-
-  public WXHorizontalScrollView(Context context, AttributeSet attrs) {
-    super(context, attrs);
-    init();
-  }
-
-  @Override
-  protected void onScrollChanged(int l, int t, int oldl, int oldt) {
-    super.onScrollChanged(l, t, oldl, oldt);
-    if (mScrollViewListener != null) {
-      mScrollViewListener.onScrollChanged(this, l, t, oldl, oldt);
-    }
-    if (mScrollViewListeners != null) {
-      for (ScrollViewListener listener : mScrollViewListeners) {
-        listener.onScrollChanged(this, l, t, oldl, oldt);
-      }
-    }
-  }
-
-  public void setScrollViewListener(ScrollViewListener scrollViewListener) {
-    this.mScrollViewListener = scrollViewListener;
-  }
-
-  @Override
-  public void destroy() {
-
-  }
-
-  public void addScrollViewListener(ScrollViewListener scrollViewListener) {
-    if (mScrollViewListeners == null) {
-      mScrollViewListeners = new CopyOnWriteArrayList<>();
-    }
-    if (!mScrollViewListeners.contains(scrollViewListener)) {
-      mScrollViewListeners.add(scrollViewListener);
-    }
-  }
-
-  public void removeScrollViewListener(ScrollViewListener scrollViewListener) {
-    mScrollViewListeners.remove(scrollViewListener);
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  @Override
-  public boolean dispatchTouchEvent(MotionEvent event) {
-    boolean result = super.dispatchTouchEvent(event);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, event);
-    }
-    return result;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent ev) {
-    if(!scrollable) {
-      return true; // when scrollable is set to false, then eat the touch event
-    }
-    return super.onTouchEvent(ev);
-  }
-
-  public interface ScrollViewListener {
-
-    void onScrollChanged(WXHorizontalScrollView scrollView, int x, int y, int oldx, int oldy);
-  }
-
-  public boolean isScrollable() {
-    return scrollable;
-  }
-
-  public void setScrollable(boolean scrollable) {
-    this.scrollable = scrollable;
-  }
-
-  public Rect getContentFrame() {
-    return new Rect(0, 0, computeHorizontalScrollRange(), computeVerticalScrollRange());
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXImageView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXImageView.java
deleted file mode 100644
index 5ef242f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXImageView.java
+++ /dev/null
@@ -1,262 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ImageView;
-import com.taobao.weex.ui.component.WXImage;
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import com.taobao.weex.utils.ImageDrawable;
-import com.taobao.weex.utils.WXLogUtils;
-import java.lang.ref.WeakReference;
-import java.util.Arrays;
-
-@SuppressLint("AppCompatCustomView")
-public class WXImageView extends ImageView implements WXGestureObservable,
-        IRenderStatus<WXImage>,
-        IRenderResult<WXImage>, WXImage.Measurable {
-
-  private WeakReference<WXImage> mWeakReference;
-  private WXGesture wxGesture;
-  private float[] borderRadius;
-  private boolean gif;
-  private boolean isBitmapReleased = false;
-  private boolean enableBitmapAutoManage = true;
-
-
-  public WXImageView(Context context) {
-    super(context);
-  }
-
-  @Override
-  public void setImageResource(int resId) {
-    Drawable drawable = getResources().getDrawable(resId);
-    setImageDrawable(drawable);
-  }
-
-  public void setImageDrawable(@Nullable Drawable drawable, boolean isGif) {
-    this.gif = isGif;
-    ViewGroup.LayoutParams layoutParams;
-    if ((layoutParams = getLayoutParams()) != null) {
-      Drawable wrapDrawable = ImageDrawable.createImageDrawable(drawable,
-              getScaleType(), borderRadius,
-              layoutParams.width - getPaddingLeft() - getPaddingRight(),
-              layoutParams.height - getPaddingTop() - getPaddingBottom(),
-              isGif);
-      if (wrapDrawable instanceof ImageDrawable) {
-        ImageDrawable imageDrawable = (ImageDrawable) wrapDrawable;
-        if (!Arrays.equals(imageDrawable.getCornerRadii(), borderRadius)) {
-          imageDrawable.setCornerRadii(borderRadius);
-        }
-      }
-      super.setImageDrawable(wrapDrawable);
-      if (mWeakReference != null) {
-        WXImage component = mWeakReference.get();
-        if (component != null) {
-          component.readyToRender();
-        }
-      }
-    }
-  }
-
-  @Override
-  public void setImageDrawable(@Nullable Drawable drawable) {
-    setImageDrawable(drawable, gif);
-  }
-
-  @Override
-  public void setImageBitmap(@Nullable Bitmap bm) {
-    setImageDrawable(bm == null ? null : new BitmapDrawable(getResources(), bm));
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent event) {
-    boolean result = super.onTouchEvent(event);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, event);
-    }
-    return result;
-  }
-
-  public void setBorderRadius(@NonNull float[] borderRadius) {
-    this.borderRadius = borderRadius;
-  }
-
-  @Override
-  protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
-    super.onLayout(changed, left, top, right, bottom);
-    if (changed) {
-      setImageDrawable(getDrawable(), gif);
-    }
-  }
-
-  @Override
-  public void holdComponent(WXImage component) {
-    mWeakReference = new WeakReference<>(component);
-  }
-
-  @Nullable
-  @Override
-  public WXImage getComponent() {
-    return null != mWeakReference ? mWeakReference.get() : null;
-  }
-
-  @Override
-  public int getNaturalWidth() {
-    Drawable drawable = getDrawable();
-    if (drawable != null) {
-      if (drawable instanceof ImageDrawable) {
-        return ((ImageDrawable) drawable).getBitmapWidth();
-      } else if (drawable instanceof BitmapDrawable) {
-        Bitmap bitmap = ((BitmapDrawable) drawable).getBitmap();
-        if (bitmap != null) {
-          return bitmap.getWidth();
-        } else {
-          WXLogUtils.w("WXImageView", "Bitmap on " + drawable.toString() + " is null");
-        }
-      } else {
-        WXLogUtils.w("WXImageView", "Not supported drawable type: " + drawable.getClass().getSimpleName());
-      }
-    }
-    return -1;
-  }
-
-  @Override
-  public int getNaturalHeight() {
-    Drawable drawable = getDrawable();
-    if (drawable != null) {
-      if (drawable instanceof ImageDrawable) {
-        return ((ImageDrawable) drawable).getBitmapHeight();
-      } else if (drawable instanceof BitmapDrawable) {
-        Bitmap bitmap = ((BitmapDrawable) drawable).getBitmap();
-        if (bitmap != null) {
-          return bitmap.getHeight();
-        } else {
-          WXLogUtils.w("WXImageView", "Bitmap on " + drawable.toString() + " is null");
-        }
-      } else {
-        WXLogUtils.w("WXImageView", "Not supported drawable type: " + drawable.getClass().getSimpleName());
-      }
-    }
-    return -1;
-  }
-
-  private boolean mOutWindowVisibilityChangedReally;
-  @Override
-  public void dispatchWindowVisibilityChanged(int visibility) {
-    mOutWindowVisibilityChangedReally = true;
-    super.dispatchWindowVisibilityChanged(visibility);
-    mOutWindowVisibilityChangedReally = false;
-  }
-
-  @Override
-  protected void onWindowVisibilityChanged(int visibility) {
-    super.onWindowVisibilityChanged(visibility);
-    if(mOutWindowVisibilityChangedReally){
-      if(visibility == View.VISIBLE){
-        autoRecoverImage();
-      }else{
-        autoReleaseImage();
-      }
-    }
-  }
-
-
-  @Override
-  protected void onAttachedToWindow() {
-    super.onAttachedToWindow();
-    autoRecoverImage();
-  }
-
-  @Override
-  protected void onDetachedFromWindow() {
-    super.onDetachedFromWindow();
-    autoReleaseImage();
-
-  }
-
-
-  @Override
-  public void onStartTemporaryDetach () {
-    super.onStartTemporaryDetach();
-    autoReleaseImage();
-
-  }
-
-
-  @Override
-  public void onFinishTemporaryDetach () {
-    super.onFinishTemporaryDetach();
-    autoRecoverImage();
-  }
-
-
-  public void setEnableBitmapAutoManage(boolean enableBitmapAutoManage) {
-    this.enableBitmapAutoManage = enableBitmapAutoManage;
-  }
-
-  public void autoReleaseImage(){
-    if(enableBitmapAutoManage) {
-      if (!isBitmapReleased) {
-        isBitmapReleased = true;
-        WXImage image = getComponent();
-        if (image != null) {
-          image.autoReleaseImage();
-        }
-      }
-    }
-  }
-
-  public void autoRecoverImage(){
-    if(enableBitmapAutoManage){
-      if(isBitmapReleased){
-        WXImage image = getComponent();
-        if(image != null){
-          image.autoRecoverImage();
-        }
-        isBitmapReleased = false;
-      }
-    }
-  }
-
-
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXLoadingLayout.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXLoadingLayout.java
deleted file mode 100644
index e4b356d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXLoadingLayout.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.content.Context;
-
-/**
- * Created by lixinke on 16/9/19.
- */
-public class WXLoadingLayout extends WXBaseRefreshLayout {
-
-  public WXLoadingLayout(Context context) {
-    super(context);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXRefreshLayout.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXRefreshLayout.java
deleted file mode 100644
index 427adc5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXRefreshLayout.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.content.Context;
-
-/**
- * Created by lixinke on 16/9/19.
- */
-public class WXRefreshLayout extends WXBaseRefreshLayout {
-
-  public WXRefreshLayout(Context context) {
-    super(context);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXScrollView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXScrollView.java
deleted file mode 100644
index cc5b1c2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXScrollView.java
+++ /dev/null
@@ -1,467 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Rect;
-import android.os.Handler;
-import android.os.Handler.Callback;
-import android.os.Message;
-import android.support.v4.view.NestedScrollingChild;
-import android.support.v4.view.NestedScrollingChildHelper;
-import android.support.v4.view.ViewCompat;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-import android.view.View;
-import android.widget.ScrollView;
-
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXScroller;
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXReflectionUtils;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.Map.Entry;
-
-
-/**
- * Custom-defined scrollView
- */
-public class WXScrollView extends ScrollView implements Callback, IWXScroller,
-        WXGestureObservable,NestedScrollingChild {
-
-  private NestedScrollingChildHelper childHelper;
-  private float ox;
-  private float oy;
-  private int[] consumed = new int[2];
-  private int[] offsetInWindow = new int[2];
-
-  int mScrollX;
-  int mScrollY;
-  private WXGesture wxGesture;
-  private List<WXScrollViewListener> mScrollViewListeners;
-  private WXScroller mWAScroller;
-  //sticky
-  private View mCurrentStickyView;
-  private boolean mRedirectTouchToStickyView;
-  private int mStickyOffset;
-  private boolean mHasNotDoneActionDown = true;
-  @SuppressLint("HandlerLeak")
-  private Handler mScrollerTask;
-  private int mInitialPosition;
-  private int mCheckTime = 100;
-  /**
-   * The location of mCurrentStickyView
-   */
-  private int[] mStickyP = new int[2];
-  /**
-   * Location of the scrollView
-   */
-  private Rect mScrollRect;
-  private int[] stickyScrollerP = new int[2];
-  private int[] stickyViewP = new int[2];
-  private boolean scrollable = true;
-
-  public WXScrollView(Context context) {
-    super(context);
-    mScrollViewListeners = new ArrayList<>();
-    init();
-    try {
-      WXReflectionUtils.setValue(this, "mMinimumVelocity", 5);
-    } catch (Exception e) {
-      WXLogUtils.e("[WXScrollView] WXScrollView: ", e);
-    }
-  }
-
-  private void init() {
-    setWillNotDraw(false);
-    startScrollerTask();
-    setOverScrollMode(View.OVER_SCROLL_NEVER);
-    childHelper = new NestedScrollingChildHelper(this);
-    childHelper.setNestedScrollingEnabled(true);
-  }
-
-  public void startScrollerTask() {
-    if (mScrollerTask == null) {
-      mScrollerTask = new Handler(WXThread.secure(this));
-    }
-    mInitialPosition = getScrollY();
-    mScrollerTask.sendEmptyMessageDelayed(0, mCheckTime);
-  }
-
-  public WXScrollView(Context context, AttributeSet attrs) {
-    super(context, attrs);
-    init();
-  }
-
-  public WXScrollView(Context context, AttributeSet attrs, int defStyle) {
-    super(context, attrs, defStyle);
-    setOverScrollMode(View.OVER_SCROLL_NEVER);
-  }
-
-  /**
-   * Add listener for scrollView.
-   */
-  public void addScrollViewListener(WXScrollViewListener scrollViewListener) {
-    if (!mScrollViewListeners.contains(scrollViewListener)) {
-      mScrollViewListeners.add(scrollViewListener);
-    }
-  }
-
-  public void removeScrollViewListener(WXScrollViewListener scrollViewListener) {
-    mScrollViewListeners.remove(scrollViewListener);
-  }
-
-  @Override
-  public boolean dispatchTouchEvent(MotionEvent ev) {
-    if (ev.getAction() == MotionEvent.ACTION_DOWN) {
-      mRedirectTouchToStickyView = true;
-    }
-
-    if (mRedirectTouchToStickyView) {
-      mRedirectTouchToStickyView = mCurrentStickyView != null;
-
-      if (mRedirectTouchToStickyView) {
-        mRedirectTouchToStickyView = ev.getY() <= mCurrentStickyView.getHeight()
-                && ev.getX() >= mCurrentStickyView.getLeft()
-                && ev.getX() <= mCurrentStickyView.getRight();
-      }
-    }
-
-    if (mRedirectTouchToStickyView) {
-      if (mScrollRect == null) {
-        mScrollRect = new Rect();
-        getGlobalVisibleRect(mScrollRect);
-      }
-      mCurrentStickyView.getLocationOnScreen(stickyViewP);
-      ev.offsetLocation(0, stickyViewP[1] - mScrollRect.top);
-    }
-    boolean result = super.dispatchTouchEvent(ev);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, ev);
-    }
-    return result;
-  }
-
-  @Override
-  protected void dispatchDraw(Canvas canvas) {
-    super.dispatchDraw(canvas);
-    if (mCurrentStickyView != null) {
-      canvas.save();
-      mCurrentStickyView.getLocationOnScreen(mStickyP);
-      int realOffset = (mStickyOffset <= 0 ? mStickyOffset : 0);
-      canvas.translate(mStickyP[0], getScrollY() + realOffset);
-      canvas.clipRect(0, realOffset, mCurrentStickyView.getWidth(),
-              mCurrentStickyView.getHeight());
-      mCurrentStickyView.draw(canvas);
-      canvas.restore();
-    }
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent ev) {
-    if(!scrollable) {
-      return true; // when scrollable is set to false, then eat the touch event
-    }
-    if (mRedirectTouchToStickyView) {
-
-      if (mScrollRect == null) {
-        mScrollRect = new Rect();
-        getGlobalVisibleRect(mScrollRect);
-      }
-      mCurrentStickyView.getLocationOnScreen(stickyViewP);
-      ev.offsetLocation(0, -(stickyViewP[1] - mScrollRect.top));
-    }
-
-    if (ev.getAction() == MotionEvent.ACTION_DOWN) {
-      mHasNotDoneActionDown = false;
-    }
-
-    if (mHasNotDoneActionDown) {
-      MotionEvent down = MotionEvent.obtain(ev);
-      down.setAction(MotionEvent.ACTION_DOWN);
-      mHasNotDoneActionDown = false;
-      down.recycle();
-    }
-
-    if (ev.getAction() == MotionEvent.ACTION_DOWN) {
-      ox = ev.getX();
-      oy = ev.getY();
-      // Dispatch touch event to parent view
-      startNestedScroll(ViewCompat.SCROLL_AXIS_HORIZONTAL | ViewCompat.SCROLL_AXIS_VERTICAL);
-    }
-
-    if (ev.getAction() == MotionEvent.ACTION_UP || ev.getAction() == MotionEvent.ACTION_CANCEL) {
-      mHasNotDoneActionDown = true;
-      // stop nested scrolling dispatch
-      stopNestedScroll();
-    }
-
-    if (ev.getAction() == MotionEvent.ACTION_MOVE) {
-      float clampedX = ev.getX();
-      float clampedY = ev.getY();
-      int dx = (int) (ox - clampedX);
-      int dy = (int) (oy - clampedY);
-
-      if (dispatchNestedPreScroll(dx, dy, consumed, offsetInWindow)) {
-        // sub dx/dy was consumed by parent view!!!
-        ev.setLocation(clampedX+consumed[0],clampedY+consumed[1]);
-      }
-      ox = ev.getX();
-      oy = ev.getY();
-    }
-
-    return super.onTouchEvent(ev);
-  }
-
-  @Override
-  public void setNestedScrollingEnabled(boolean enabled) {
-    childHelper.setNestedScrollingEnabled(enabled);
-  }
-
-  @Override
-  public boolean isNestedScrollingEnabled() {
-    return childHelper.isNestedScrollingEnabled();
-  }
-
-  @Override
-  public boolean startNestedScroll(int axes) {
-    return childHelper.startNestedScroll(axes);
-  }
-
-  @Override
-  public void stopNestedScroll() {
-    childHelper.stopNestedScroll();
-  }
-
-  @Override
-  public boolean hasNestedScrollingParent() {
-    return childHelper.hasNestedScrollingParent();
-  }
-
-  public boolean isScrollable() {
-    return scrollable;
-  }
-
-  public void setScrollable(boolean scrollable) {
-    this.scrollable = scrollable;
-  }
-
-  @Override
-  public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed, int[] offsetInWindow) {
-    return childHelper.dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, offsetInWindow);
-  }
-
-  @Override
-  public boolean dispatchNestedPreScroll(int dx, int dy, int[] consumed, int[] offsetInWindow) {
-    return childHelper.dispatchNestedPreScroll(dx, dy, consumed, offsetInWindow);
-  }
-
-  @Override
-  public boolean dispatchNestedFling(float velocityX, float velocityY, boolean consumed) {
-    return childHelper.dispatchNestedFling(velocityX, velocityY, consumed);
-  }
-
-  @Override
-  public boolean dispatchNestedPreFling(float velocityX, float velocityY) {
-    return childHelper.dispatchNestedPreFling(velocityX, velocityY);
-  }
-
-  @Override
-  public boolean onNestedPreFling(View target, float velocityX,
-                                  float velocityY) {
-    return dispatchNestedPreFling(velocityX, velocityY);
-  }
-
-  @Override
-  public boolean onNestedFling(View target, float velocityX, float velocityY,
-                               boolean consumed) {
-    return dispatchNestedFling(velocityX, velocityY, consumed);
-  }
-
-  @Override
-  public void fling(int velocityY) {
-    super.fling(velocityY);
-    if (mScrollerTask != null) {
-      mScrollerTask.removeMessages(0);
-    }
-    startScrollerTask();
-  }
-
-  @Override
-  protected void onScrollChanged(int x, int y, int oldx, int oldy) {
-    mScrollX = getScrollX();
-    mScrollY = getScrollY();
-    onScroll(WXScrollView.this, mScrollX, mScrollY);
-    View view = getChildAt(getChildCount() - 1);
-    if (view == null) {
-      return;
-    }
-    int d = view.getBottom();
-    d -= (getHeight() + mScrollY);
-    if (d == 0) {
-      onScrollToBottom(mScrollX, mScrollY);
-    }
-    int count = mScrollViewListeners == null ? 0 : mScrollViewListeners.size();
-    for (int i = 0; i < count; ++i) {
-      mScrollViewListeners.get(i).onScrollChanged(this, x, y, oldx, oldy);
-    }
-
-    showStickyView();
-  }
-
-  protected void onScroll(WXScrollView scrollView, int x, int y) {
-    int count = mScrollViewListeners == null ? 0 : mScrollViewListeners.size();
-    for (int i = 0; i < count; ++i) {
-      mScrollViewListeners.get(i).onScroll(this, x, y);
-    }
-  }
-
-  protected void onScrollToBottom(int x, int y) {
-    int count = mScrollViewListeners == null ? 0 : mScrollViewListeners.size();
-    for (int i = 0; i < count; ++i) {
-      mScrollViewListeners.get(i).onScrollToBottom(this, x, y);
-    }
-  }
-
-  private void showStickyView() {
-    if(mWAScroller == null){
-      return;
-    }
-    View curStickyView = procSticky(mWAScroller.getStickMap());
-
-    if (curStickyView != null) {
-      mCurrentStickyView = curStickyView;
-    } else {
-      mCurrentStickyView = null;
-    }
-  }
-
-  private View procSticky(Map<String, Map<String, WXComponent>> mStickyMap) {
-    if (mStickyMap == null) {
-      return null;
-    }
-    Map<String, WXComponent> stickyMap = mStickyMap.get(mWAScroller.getRef());
-    if (stickyMap == null) {
-      return null;
-    }
-
-    Iterator<Entry<String, WXComponent>> iterator = stickyMap.entrySet().iterator();
-    Entry<String, WXComponent> entry = null;
-    WXComponent stickyData;
-    while (iterator.hasNext()) {
-      entry = iterator.next();
-      stickyData = entry.getValue();
-
-      getLocationOnScreen(stickyScrollerP);
-      stickyData.getHostView().getLocationOnScreen(stickyViewP);
-      int parentH = 0;
-      if(stickyData.getParent()!=null && stickyData.getParent().getRealView()!=null){
-        parentH=stickyData.getParent().getRealView().getHeight();
-      }
-      int stickyViewH = stickyData.getHostView().getHeight();
-      int stickyShowPos = stickyScrollerP[1];
-      int stickyStartHidePos = -parentH + stickyScrollerP[1] + stickyViewH;
-      if (stickyViewP[1] <= stickyShowPos && stickyViewP[1] >= (stickyStartHidePos - stickyViewH)) {
-        mStickyOffset = stickyViewP[1] - stickyStartHidePos;
-        stickyData.setStickyOffset(stickyViewP[1]-stickyScrollerP[1]);
-        return stickyData.getHostView();
-      }else{
-        stickyData.setStickyOffset(0);
-      }
-    }
-    return null;
-  }
-
-  @Override
-  public boolean handleMessage(Message msg) {
-    switch (msg.what) {
-      case 0:
-        if (mScrollerTask != null) {
-          mScrollerTask.removeMessages(0);
-        }
-        int newPosition = getScrollY();
-        if (mInitialPosition - newPosition == 0) {//has stopped
-          onScrollStopped(WXScrollView.this, getScrollX(), getScrollY());
-        } else {
-          onScroll(WXScrollView.this, getScrollX(), getScrollY());
-          mInitialPosition = getScrollY();
-          if (mScrollerTask != null) {
-            mScrollerTask.sendEmptyMessageDelayed(0, mCheckTime);
-          }
-        }
-        break;
-      default:
-        break;
-    }
-    return true;
-  }
-
-  protected void onScrollStopped(WXScrollView scrollView, int x, int y) {
-    int count = mScrollViewListeners == null ? 0 : mScrollViewListeners.size();
-    for (int i = 0; i < count; ++i) {
-      mScrollViewListeners.get(i).onScrollStopped(this, x, y);
-    }
-  }
-
-  @Override
-  public void destroy() {
-    if (mScrollerTask != null) {
-      mScrollerTask.removeCallbacksAndMessages(null);
-    }
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  public Rect getContentFrame() {
-    return new Rect(0, 0, computeHorizontalScrollRange(), computeVerticalScrollRange());
-  }
-
-  public interface WXScrollViewListener {
-
-    void onScrollChanged(WXScrollView scrollView, int x, int y, int oldx, int oldy);
-
-    void onScrollToBottom(WXScrollView scrollView, int x, int y);
-
-    void onScrollStopped(WXScrollView scrollView, int x, int y);
-
-    void onScroll(WXScrollView scrollView, int x, int y);
-  }
-
-  public void setWAScroller(WXScroller mWAScroller) {
-    this.mWAScroller = mWAScroller;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXSmoothScroller.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXSmoothScroller.java
deleted file mode 100644
index 4dfed7e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXSmoothScroller.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.view.animation.Interpolator;
-import android.widget.Scroller;
-
-/**
- * modify the scrollFactor
- */
-public class WXSmoothScroller extends Scroller {
-
-  private double mScrollFactor = 1;
-
-  public WXSmoothScroller(Context context) {
-    super(context);
-  }
-
-  public WXSmoothScroller(Context context, Interpolator interpolator) {
-    super(context, interpolator);
-  }
-
-  @SuppressLint("NewApi")
-  public WXSmoothScroller(Context context, Interpolator interpolator, boolean flywheel) {
-    super(context, interpolator, flywheel);
-  }
-
-  /**
-   * Set the factor by which the duration will change
-   */
-  public void setScrollDurationFactor(double scrollFactor) {
-    mScrollFactor = scrollFactor;
-  }
-
-  @Override
-  public void startScroll(int startX, int startY, int dx, int dy, int duration) {
-    super.startScroll(startX, startY, dx, dy, (int) (duration * mScrollFactor));
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXSwitchView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXSwitchView.java
deleted file mode 100644
index dd64e7a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXSwitchView.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.support.v7.widget.SwitchCompat;
-import android.view.Gravity;
-import android.view.MotionEvent;
-
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-
-public class WXSwitchView extends SwitchCompat implements WXGestureObservable {
-
-  private WXGesture wxGesture;
-
-  public WXSwitchView(Context context) {
-    super(context);
-    setShowText(false);
-    setGravity(Gravity.CENTER_VERTICAL);
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent event) {
-    boolean result = super.onTouchEvent(event);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, event);
-    }
-    return result;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXTextView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXTextView.java
deleted file mode 100644
index 73a84c9..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXTextView.java
+++ /dev/null
@@ -1,185 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.ClipData;
-import android.content.ClipboardManager;
-import android.content.Context;
-import android.graphics.Canvas;
-import android.support.annotation.ColorInt;
-import android.support.annotation.Nullable;
-import android.support.v7.widget.PopupMenu;
-import android.text.Layout;
-import android.text.TextUtils;
-import android.view.MenuItem;
-import android.view.MotionEvent;
-import android.view.View;
-import com.taobao.weex.ui.component.WXText;
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import java.lang.ref.WeakReference;
-
-/**
- * TextView wrapper
- */
-public class WXTextView extends View implements WXGestureObservable, IWXTextView,
-        IRenderStatus<WXText>, IRenderResult<WXText> {
-
-  private WeakReference<WXText> mWeakReference;
-  private WXGesture wxGesture;
-  private Layout textLayout;
-  private boolean mIsLabelSet = false;
-
-  public WXTextView(Context context) {
-    super(context);
-  }
-
-  @Override
-  protected void onDraw(Canvas canvas) {
-    super.onDraw(canvas);
-    canvas.save();
-    Layout layout= getTextLayout();
-    if(layout!=null){
-      canvas.translate(getPaddingLeft(),getPaddingTop());
-      layout.draw(canvas);
-    }
-    canvas.restore();
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent event) {
-    boolean result = super.onTouchEvent(event);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, event);
-    }
-    return result;
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  @Override
-  public CharSequence getText() {
-    return textLayout != null ? textLayout.getText() : null;
-  }
-
-  public Layout getTextLayout() {
-    return textLayout;
-  }
-
-  public void setTextLayout(Layout layout) {
-    this.textLayout = layout;
-    if(layout!=null && !mIsLabelSet){
-      setContentDescription(layout.getText());
-    }
-    if (mWeakReference != null) {
-      WXText wxText = mWeakReference.get();
-      if (wxText != null) {
-        wxText.readyToRender();
-      }
-    }
-  }
-
-  public void setAriaLabel(String label){
-    if(!TextUtils.isEmpty(label)){
-      mIsLabelSet = true;
-      setContentDescription(label);
-    }else{
-      mIsLabelSet = false;
-      if(textLayout != null){
-        setContentDescription(textLayout.getText());
-      }
-    }
-
-  }
-
-  /**
-   * Sets the text color for the text layout, it will be invalid
-   * when {@link #setTextLayout(Layout)} happens, and color has to be
-   * reset.
-   *
-   * @see #setTextLayout(Layout)
-   *
-   * @param color A color value in the form 0xAARRGGBB.
-   */
-  public void setTextColor(@ColorInt int color) {
-    Layout layout = getTextLayout();
-    if (layout != null) {
-      layout.getPaint().setColor(color);
-    }
-  }
-
-  @Override
-  public void holdComponent(WXText component) {
-    mWeakReference = new WeakReference<>(component);
-  }
-
-  @Nullable
-  @Override
-  public WXText getComponent() {
-    return null != mWeakReference ? mWeakReference.get() : null;
-  }
-
-  public void enableCopy(boolean enable) {
-    if (enable) {
-      setOnLongClickListener(new OnLongClickListener() {
-        @Override
-        public boolean onLongClick(View v) {
-          PopupMenu popupMenu = new PopupMenu(getContext(), WXTextView.this);
-          String s = "Copy";
-          try {
-            s = getContext().getResources().getString(android.R.string.copy);
-          } catch (Throwable t) {
-            //ignore
-          }
-          final String title = s;
-          popupMenu.getMenu().add(title);
-          popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
-            @Override
-            public boolean onMenuItemClick(MenuItem item) {
-              if (title.equals(item.getTitle())) {
-                String data = getText().toString();
-                ClipboardManager clipboardManager = (ClipboardManager) getContext().getSystemService(Context.CLIPBOARD_SERVICE);
-                if (clipboardManager != null) {
-                  ClipData clipData = ClipData.newPlainText(data, data);
-                  clipboardManager.setPrimaryClip(clipData);
-                }
-                return true;
-              }
-              return false;
-            }
-          });
-          popupMenu.show();
-          return true;
-        }
-      });
-    } else {
-      setOnLongClickListener(null);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXVideoView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXVideoView.java
deleted file mode 100644
index 6b671cb..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXVideoView.java
+++ /dev/null
@@ -1,304 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.graphics.Rect;
-import android.media.MediaPlayer;
-import android.net.Uri;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.util.AttributeSet;
-import android.view.Gravity;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewTreeObserver;
-import android.widget.FrameLayout;
-import android.widget.MediaController;
-import android.widget.ProgressBar;
-import android.widget.VideoView;
-
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import com.taobao.weex.utils.WXResourceUtils;
-
-
-public class WXVideoView extends VideoView implements WXGestureObservable {
-
-  private WXGesture wxGesture;
-  private VideoPlayListener mVideoPauseListener;
-
-  public WXVideoView(Context context) {
-    super(context);
-  }
-
-  @Override
-  public void registerGestureListener(WXGesture wxGesture) {
-    this.wxGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return wxGesture;
-  }
-
-  public void setOnVideoPauseListener(VideoPlayListener listener) {
-    mVideoPauseListener = listener;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent event) {
-    boolean result = super.onTouchEvent(event);
-    if (wxGesture != null) {
-      result |= wxGesture.onTouch(this, event);
-    }
-    return result;
-  }
-
-  @Override
-  public void start() {
-    super.start();
-    if (mVideoPauseListener != null) {
-      mVideoPauseListener.onStart();
-    }
-  }
-
-  @Override
-  public void pause() {
-    super.pause();
-    if (mVideoPauseListener != null) {
-      mVideoPauseListener.onPause();
-    }
-  }
-
-  public interface VideoPlayListener {
-
-    void onPause();
-
-    void onStart();
-  }
-
-
-  public static class Wrapper extends FrameLayout implements ViewTreeObserver.OnGlobalLayoutListener {
-
-    private WXVideoView mVideoView;
-    private ProgressBar mProgressBar;
-    private MediaController mMediaController;
-    private Uri mUri;
-    private MediaPlayer.OnPreparedListener mOnPreparedListener;
-    private MediaPlayer.OnErrorListener mOnErrorListener;
-    private MediaPlayer.OnCompletionListener mOnCompletionListener;
-    private WXVideoView.VideoPlayListener mVideoPlayListener;
-    private boolean mControls = true;
-
-    public Wrapper(Context context) {
-      super(context);
-      init(context);
-    }
-
-    public Wrapper(Context context, AttributeSet attrs) {
-      super(context, attrs);
-      init(context);
-    }
-
-    public Wrapper(Context context, AttributeSet attrs, int defStyleAttr) {
-      super(context, attrs, defStyleAttr);
-      init(context);
-    }
-
-    private void init(Context context) {
-      setBackgroundColor(WXResourceUtils.getColor("#ee000000"));
-      mProgressBar = new ProgressBar(context);
-      FrameLayout.LayoutParams pLayoutParams =
-              new FrameLayout.LayoutParams(FrameLayout.LayoutParams.WRAP_CONTENT,
-                      FrameLayout.LayoutParams.WRAP_CONTENT);
-      mProgressBar.setLayoutParams(pLayoutParams);
-      pLayoutParams.gravity = Gravity.CENTER;
-      addView(mProgressBar);
-
-      getViewTreeObserver().addOnGlobalLayoutListener(this);
-    }
-
-    public ProgressBar getProgressBar() {
-      return mProgressBar;
-    }
-
-    public
-    @Nullable
-    WXVideoView getVideoView() {
-      return mVideoView;
-    }
-
-    /**
-     * Create if not existed. Will cause request focus.
-     *
-     * @return
-     */
-    public
-    @NonNull
-    WXVideoView createIfNotExist() {
-      if (mVideoView == null) {
-        createVideoView();
-      }
-      return mVideoView;
-    }
-
-    public
-    @Nullable
-    MediaController getMediaController() {
-      return mMediaController;
-    }
-
-    public void setVideoURI(Uri uri) {
-      mUri = uri;
-      if (mVideoView != null) {
-        mVideoView.setVideoURI(uri);
-      }
-    }
-
-    public void start() {
-      if (mVideoView != null) {
-        mVideoView.start();
-      }
-    }
-
-    public void pause() {
-      if (mVideoView != null) {
-        mVideoView.pause();
-      }
-    }
-
-    public void stopPlayback() {
-      if (mVideoView != null) {
-        mVideoView.stopPlayback();
-      }
-    }
-
-    public void resume() {
-      if (mVideoView != null) {
-        mVideoView.resume();
-      }
-    }
-
-    public void setOnErrorListener(MediaPlayer.OnErrorListener l) {
-      mOnErrorListener = l;
-      if (mVideoView != null) {
-        mVideoView.setOnErrorListener(l);
-      }
-    }
-
-    public void setOnPreparedListener(MediaPlayer.OnPreparedListener l) {
-      mOnPreparedListener = l;
-      if (mVideoView != null) {
-        mVideoView.setOnPreparedListener(l);
-      }
-
-    }
-
-    public void setOnCompletionListener(MediaPlayer.OnCompletionListener l) {
-      mOnCompletionListener = l;
-      if (mVideoView != null) {
-        mVideoView.setOnCompletionListener(l);
-      }
-    }
-
-    public void setOnVideoPauseListener(VideoPlayListener listener) {
-      mVideoPlayListener = listener;
-      if (mVideoView != null) {
-        mVideoView.setOnVideoPauseListener(listener);
-      }
-    }
-
-    public void setControls(boolean controls) {
-      mControls = controls;
-      if (mVideoView != null && mMediaController != null) {
-        if (!mControls) {
-          mMediaController.setVisibility(View.GONE);
-        } else {
-          mMediaController.setVisibility(View.VISIBLE);
-        }
-      }
-    }
-
-    private synchronized void createVideoView() {
-      if(mVideoView != null){
-        return;
-      }
-      Context context = getContext();
-      WXVideoView video = new WXVideoView(context);
-      FrameLayout.LayoutParams videoLayoutParams =
-              new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT,
-                      FrameLayout.LayoutParams.MATCH_PARENT);
-      videoLayoutParams.gravity = Gravity.CENTER;
-      video.setLayoutParams(videoLayoutParams);
-      addView(video, 0);//first child
-      video.setOnErrorListener(mOnErrorListener);
-      video.setOnPreparedListener(mOnPreparedListener);
-      video.setOnCompletionListener(mOnCompletionListener);
-      video.setOnVideoPauseListener(mVideoPlayListener);
-      MediaController controller = new MediaController(context);
-      controller.setAnchorView(this);
-      video.setMediaController(controller);
-      controller.setMediaPlayer(video);
-      if (!mControls) {
-        controller.setVisibility(View.GONE);
-      } else {
-        controller.setVisibility(View.VISIBLE);
-      }
-      mMediaController = controller;
-      mVideoView = video;
-      mVideoView.setZOrderOnTop(true);
-
-      if(mUri != null) {
-        setVideoURI(mUri);
-      }
-    }
-
-    @SuppressLint("NewApi")
-    private void removeSelfFromViewTreeObserver() {
-      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
-        getViewTreeObserver().removeOnGlobalLayoutListener(this);
-      } else {
-        getViewTreeObserver().removeGlobalOnLayoutListener(this);
-      }
-    }
-
-
-    public boolean createVideoViewIfVisible(){
-      Rect visibleRect = new Rect();
-      if (mVideoView != null) {
-        return true;
-      } else if (getGlobalVisibleRect(visibleRect) && !visibleRect.isEmpty()) {
-        createVideoView();
-        return true;
-      }
-      return false;
-    }
-
-    @Override
-    public void onGlobalLayout() {
-      if(createVideoViewIfVisible()){
-        removeSelfFromViewTreeObserver();
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXWebView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/WXWebView.java
deleted file mode 100644
index 135efc9..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/WXWebView.java
+++ /dev/null
@@ -1,376 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Color;
-import android.net.Uri;
-import android.net.http.SslError;
-import android.os.Build;
-import android.os.Handler;
-import android.os.Message;
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-import android.view.Gravity;
-import android.view.View;
-import android.webkit.JavascriptInterface;
-import android.webkit.JsPromptResult;
-import android.webkit.SslErrorHandler;
-import android.webkit.WebChromeClient;
-import android.webkit.WebResourceError;
-import android.webkit.WebResourceRequest;
-import android.webkit.WebResourceResponse;
-import android.webkit.WebSettings;
-import android.webkit.WebView;
-import android.webkit.WebViewClient;
-import android.widget.FrameLayout;
-import android.widget.ProgressBar;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONException;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.lang.ref.WeakReference;
-import java.util.HashMap;
-import java.util.Map;
-
-public class WXWebView implements IWebView {
-
-    private Context mContext;
-    private String mOrigin;
-    private WebView mWebView;
-    private ProgressBar mProgressBar;
-    private boolean mShowLoading = true;
-    private Handler mMessageHandler;
-    private static final int POST_MESSAGE = 1;
-    private static final String BRIDGE_NAME = "__WEEX_WEB_VIEW_BRIDGE";
-    private static final int SDK_VERSION = Build.VERSION.SDK_INT;
-    // downgraded by CVE-2012-6636(https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2012-6636)
-    private static final boolean DOWNGRADE_JS_INTERFACE = SDK_VERSION < 17;
-
-    private OnErrorListener mOnErrorListener;
-    private OnPageListener mOnPageListener;
-    private OnMessageListener mOnMessageListener;
-
-    public WXWebView(Context context, String origin) {
-        mContext = context;
-        mOrigin = origin;
-    }
-
-    @Override
-    public View getView() {
-        FrameLayout root = new FrameLayout(mContext);
-        root.setBackgroundColor(Color.WHITE);
-
-        mWebView = new WebView(mContext);//mContext.getApplicationContext();
-        FrameLayout.LayoutParams wvLayoutParams =
-                new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT,
-                        FrameLayout.LayoutParams.MATCH_PARENT);
-        wvLayoutParams.gravity = Gravity.CENTER;
-        mWebView.setLayoutParams(wvLayoutParams);
-        root.addView(mWebView);
-        initWebView(mWebView);
-
-        mProgressBar = new ProgressBar(mContext);
-        showProgressBar(false);
-        FrameLayout.LayoutParams pLayoutParams =
-                new FrameLayout.LayoutParams(FrameLayout.LayoutParams.WRAP_CONTENT,
-                        FrameLayout.LayoutParams.WRAP_CONTENT);
-        mProgressBar.setLayoutParams(pLayoutParams);
-        pLayoutParams.gravity = Gravity.CENTER;
-        root.addView(mProgressBar);
-
-        mMessageHandler = new MessageHandler(this);
-
-        return root;
-    }
-
-    @Override
-    public void destroy() {
-        if (getWebView() != null) {
-            getWebView().removeAllViews();
-            getWebView().destroy();
-            mWebView = null;
-        }
-    }
-
-    @Override
-    public void loadUrl(String url) {
-        if(getWebView() == null)
-            return;
-        getWebView().loadUrl(url);
-    }
-
-    @Override
-    public void loadDataWithBaseURL(String source) {
-        if(getWebView() == null)
-            return;
-        getWebView().loadDataWithBaseURL(mOrigin, source, "text/html", "utf-8", null);
-    }
-
-    @Override
-    public void reload() {
-        if(getWebView() == null)
-            return;
-        getWebView().reload();
-    }
-
-    @Override
-    public void goBack() {
-        if(getWebView() == null)
-            return;
-        getWebView().goBack();
-    }
-
-    @Override
-    public void goForward() {
-        if(getWebView() == null)
-            return;
-        getWebView().goForward();
-    }
-
-    @Override
-    public void postMessage(Object msg) {
-        if (getWebView() == null) return;
-
-        try {
-            JSONObject initData = new JSONObject();
-            initData.put("type", "message");
-            initData.put("data", msg);
-            initData.put("origin", mOrigin);
-            evaluateJS("javascript:(function () {"
-                + "var initData = " + initData.toString() + ";"
-                + "try {"
-                + "var event = new MessageEvent('message', initData);"
-                + "window.dispatchEvent(event);"
-                + "} catch (e) {}"
-                + "})();");
-        } catch (JSONException e) {
-            throw new RuntimeException(e);
-        }
-    }
-
-    /*@Override
-    public void setVisibility(int visibility) {
-        if (mRootView != null) {
-            mRootView.setVisibility(visibility);
-        }
-    }*/
-
-    @Override
-    public void setShowLoading(boolean shown) {
-        mShowLoading = shown;
-    }
-
-    @Override
-    public void setOnErrorListener(OnErrorListener listener) {
-        mOnErrorListener = listener;
-    }
-
-    @Override
-    public void setOnPageListener(OnPageListener listener) {
-        mOnPageListener = listener;
-    }
-
-    @Override
-    public void setOnMessageListener(OnMessageListener listener) {
-        mOnMessageListener = listener;
-    }
-
-    private void showProgressBar(boolean shown) {
-        if (mShowLoading) {
-            mProgressBar.setVisibility(shown ? View.VISIBLE : View.GONE);
-        }
-    }
-
-    private void showWebView(boolean shown) {
-        mWebView.setVisibility(shown ? View.VISIBLE : View.INVISIBLE);
-    }
-
-    private @Nullable WebView getWebView() {
-        //TODO: remove this, duplicate with getView semantically.
-        return mWebView;
-    }
-
-    @SuppressLint({"SetJavaScriptEnabled", "AddJavascriptInterface"})
-    private void initWebView(WebView wv) {
-        WebSettings settings = wv.getSettings();
-        settings.setJavaScriptEnabled(true);
-        settings.setAppCacheEnabled(true);
-        settings.setUseWideViewPort(true);
-        settings.setDomStorageEnabled(true);
-        settings.setSupportZoom(false);
-        settings.setBuiltInZoomControls(false);
-        settings.setAllowFileAccess(false);
-        wv.setWebViewClient(new WebViewClient() {
-
-            @Override
-            public boolean shouldOverrideUrlLoading(WebView view, String url) {
-                view.loadUrl(url);
-                WXLogUtils.v("tag", "onPageOverride " + url);
-                return true;
-            }
-
-            @Override
-            public void onPageStarted(WebView view, String url, Bitmap favicon) {
-                super.onPageStarted(view, url, favicon);
-                WXLogUtils.v("tag", "onPageStarted " + url);
-                if (mOnPageListener != null) {
-                    mOnPageListener.onPageStart(url);
-                }
-            }
-
-            @Override
-            public void onPageFinished(WebView view, String url) {
-                super.onPageFinished(view, url);
-                WXLogUtils.v("tag", "onPageFinished " + url);
-                if (mOnPageListener != null) {
-                    mOnPageListener.onPageFinish(url, view.canGoBack(), view.canGoForward());
-                }
-                if (mOnMessageListener != null) {
-                    evaluateJS("javascript:(window.postMessage = function(message, targetOrigin) {"
-                        + "if (message == null || !targetOrigin) return;"
-                        + (DOWNGRADE_JS_INTERFACE
-                        ? "prompt('" + BRIDGE_NAME + "://postMessage?message=' + JSON.stringify(message) + '&targetOrigin=' + targetOrigin)"
-                        : BRIDGE_NAME + ".postMessage(JSON.stringify(message), targetOrigin);")
-                        + "})");
-                }
-            }
-
-            @Override
-            public void onReceivedError(WebView view, WebResourceRequest request, WebResourceError error) {
-                super.onReceivedError(view, request, error);
-                if (mOnErrorListener != null) {
-                    //mOnErrorListener.onError("error", "page error code:" + error.getErrorCode() + ", desc:" + error.getDescription() + ", url:" + request.getUrl());
-                    mOnErrorListener.onError("error", "page error");
-                }
-            }
-
-            @Override
-            public void onReceivedHttpError(WebView view, WebResourceRequest request, WebResourceResponse errorResponse) {
-                super.onReceivedHttpError(view, request, errorResponse);
-                if (mOnErrorListener != null) {
-                    mOnErrorListener.onError("error", "http error");
-                }
-            }
-
-            @Override
-            public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
-                super.onReceivedSslError(view, handler, error);
-                if (mOnErrorListener != null) {
-                    mOnErrorListener.onError("error", "ssl error");
-                }
-            }
-        });
-        wv.setWebChromeClient(new WebChromeClient() {
-            @Override
-            public void onProgressChanged(WebView view, int newProgress) {
-                super.onProgressChanged(view, newProgress);
-                showWebView(newProgress == 100);
-                showProgressBar(newProgress != 100);
-                WXLogUtils.v("tag", "onPageProgressChanged " + newProgress);
-            }
-
-            @Override
-            public void onReceivedTitle(WebView view, String title) {
-                super.onReceivedTitle(view, title);
-                if (mOnPageListener != null) {
-                    mOnPageListener.onReceivedTitle(view.getTitle());
-                }
-            }
-
-            @Override
-            public boolean onJsPrompt(WebView view, String url, String text, String defaultValue, JsPromptResult result) {
-                Uri uri = Uri.parse(text);
-                String scheme = uri.getScheme();
-                if (TextUtils.equals(scheme, BRIDGE_NAME)) {
-                    if (TextUtils.equals(uri.getAuthority(), "postMessage")) {
-                        String message = uri.getQueryParameter("message");
-                        String targetOrigin = uri.getQueryParameter("targetOrigin");
-                        onMessage(message, targetOrigin);
-                        result.confirm("success");
-                    } else {
-                        result.confirm("fail");
-                    }
-                    return true;
-                }
-                return super.onJsPrompt(view, url, text, defaultValue, result);
-            }
-        });
-        if (!DOWNGRADE_JS_INTERFACE) {
-            wv.addJavascriptInterface(new Object() {
-                @JavascriptInterface
-                public void postMessage(String message, String targetOrigin) {
-                    onMessage(message, targetOrigin);
-                }
-            }, BRIDGE_NAME);
-        }
-    }
-
-    private void onMessage(String message, String targetOrigin) {
-        if (message != null && targetOrigin != null && mOnMessageListener != null) {
-            try {
-                Map<String, Object> initData = new HashMap<>();
-                initData.put("data", JSON.parse(message));
-                initData.put("origin", targetOrigin);
-                initData.put("type", "message");
-                Message threadMessage = new Message();
-                threadMessage.what = POST_MESSAGE;
-                threadMessage.obj = initData;
-                mMessageHandler.sendMessage(threadMessage);
-            } catch (JSONException e) {
-                throw new RuntimeException(e);
-            }
-        }
-    }
-
-    private void evaluateJS(String jsStr) {
-        if (SDK_VERSION < 19) {
-            mWebView.loadUrl(jsStr);
-        } else {
-            mWebView.evaluateJavascript(jsStr, null);
-        }
-    }
-
-    private static class MessageHandler extends Handler {
-        private final WeakReference<WXWebView> mWv;
-
-        private MessageHandler(WXWebView wv) {
-            mWv = new WeakReference<>(wv);
-        }
-
-        @Override
-        @SuppressWarnings("unchecked")
-        public void handleMessage(Message msg) {
-            super.handleMessage(msg);
-            switch (msg.what) {
-                case POST_MESSAGE:
-                    if (mWv.get() != null && mWv.get().mOnMessageListener != null) {
-                        mWv.get().mOnMessageListener.onMessage((Map<String, Object>) msg.obj);
-                    }
-                    break;
-                default:
-                    break;
-            }
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderCorner.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderCorner.java
deleted file mode 100644
index 918d2f0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderCorner.java
+++ /dev/null
@@ -1,202 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.PointF;
-import android.graphics.RectF;
-import android.os.Build.VERSION;
-import android.os.Build.VERSION_CODES;
-import android.support.annotation.NonNull;
-import com.taobao.weex.base.FloatUtil;
-
-abstract class BorderCorner {
-
-  final static float SWEEP_ANGLE = 45;
-  private float mCornerRadius = 0.0f;
-  private float mPreBorderWidth = 0.0f;
-  private float mPostBorderWidth = 0.0f;
-  private RectF mBorderBox;
-  protected float mAngleBisector;
-
-  /**
-   * Tell whether this corner has a rounded inner corner.
-   * If a corner has a rounded inner corner, it has an outer corner as well.
-   */
-  private boolean hasInnerCorner = false;
-
-  /**
-   * Tell whether this corner has a rounded outer corner.
-   */
-  private boolean hasOuterCorner = false;
-
-  private float mOvalLeft, mOvalTop, mOvalRight, mOvalBottom;
-
-  private float mRoundCornerStartX, mRoundCornerStartY;
-  private float mRoundCornerEndX, mRoundCornerEndY;
-
-  BorderCorner() {
-  }
-
-  final void set(float cornerRadius, float preBorderWidth, float postBorderWidth,
-                 @NonNull RectF borderBox, float angleBisector) {
-    boolean dirty = !FloatUtil.floatsEqual(mCornerRadius, cornerRadius)
-        || !FloatUtil.floatsEqual(mPreBorderWidth, preBorderWidth)
-        || !FloatUtil.floatsEqual(mPostBorderWidth, postBorderWidth)
-        || !FloatUtil.floatsEqual(mAngleBisector, angleBisector)
-        || (null != mBorderBox && mBorderBox.equals(borderBox));
-
-    if (dirty) {
-      mCornerRadius = cornerRadius;
-      mPreBorderWidth = preBorderWidth;
-      mPostBorderWidth = postBorderWidth;
-      mBorderBox = borderBox;
-      mAngleBisector = angleBisector;
-
-      hasOuterCorner = mCornerRadius > 0 && !FloatUtil.floatsEqual(0, mCornerRadius);
-
-      hasInnerCorner = (hasOuterCorner
-          && (getPreBorderWidth() >= 0)
-          && (getPostBorderWidth() >= 0)
-          && (getOuterCornerRadius() > getPreBorderWidth())
-          && (getOuterCornerRadius() > getPostBorderWidth()));
-
-      if (hasOuterCorner) {
-        prepareOval();
-      }
-      prepareRoundCorner();
-    }
-  }
-
-  /** Build oval data */
-  abstract protected void prepareOval();
-
-  /** Build corner data */
-  abstract protected void prepareRoundCorner();
-
-  public final void drawRoundedCorner(@NonNull Canvas canvas, @NonNull Paint paint, float startAngle) {
-    if (this.hasOuterCorner()) {
-      /*Due to the problem of hardware-acceleration, border-radius in some case will not
-       be rendered if Path.addArc used instead and the following condition met.
-       1. hardware-acceleration enabled
-       2. System version is Android 4.1
-       3. Screen width is 720px.
-       http://dotwe.org/weex/421b9ad09fde51c0b49bb56b37fcf955
-      */
-      if (VERSION.SDK_INT >= VERSION_CODES.LOLLIPOP) {
-        canvas.drawArc(mOvalLeft, mOvalTop, mOvalRight, mOvalBottom, startAngle, BorderCorner.SWEEP_ANGLE, false,
-            paint);
-      } else {
-        canvas.drawArc(new RectF(mOvalLeft, mOvalTop, mOvalRight, mOvalBottom), startAngle, BorderCorner.SWEEP_ANGLE,
-            false, paint);
-      }
-    } else {
-      canvas.drawLine(getRoundCornerStartX(), getRoundCornerStartY(), getRoundCornerEndX(), getRoundCornerEndY(),
-          paint);
-    }
-  }
-
-
-  public final float getRoundCornerStartX() {
-    return mRoundCornerStartX;
-  }
-
-  final void setRoundCornerStartX(float roundCornerStartX) {
-    this.mRoundCornerStartX = roundCornerStartX;
-  }
-
-  public final float getRoundCornerStartY() {
-    return mRoundCornerStartY;
-  }
-
-  final void setRoundCornerStartY(float roundCornerStartY) {
-    this.mRoundCornerStartY = roundCornerStartY;
-  }
-
-  public final float getRoundCornerEndX() {
-    return mRoundCornerEndX;
-  }
-
-  final void setRoundCornerEndX(float mRoundCornerEndX) {
-    this.mRoundCornerEndX = mRoundCornerEndX;
-  }
-
-  public final float getRoundCornerEndY() {
-    return mRoundCornerEndY;
-  }
-
-  final void setRoundCornerEndY(float mRoundCornerEndY) {
-    this.mRoundCornerEndY = mRoundCornerEndY;
-  }
-
-  final void setOvalLeft(float mOvalLeft) {
-    this.mOvalLeft = mOvalLeft;
-  }
-
-  final void setOvalTop(float mOvalTop) {
-    this.mOvalTop = mOvalTop;
-  }
-
-  final void setOvalRight(float mOvalRight) {
-    this.mOvalRight = mOvalRight;
-  }
-
-  final void setOvalBottom(float mOvalBottom) {
-    this.mOvalBottom = mOvalBottom;
-  }
-
-  /**
-   * Tell whether this corner has a rounded inner corner.
-   * If a corner has a rounded inner corner, it has an outer corner as well.
-   * @return true for a rounded inner corner, otherwise false.
-   */
-  boolean hasInnerCorner() {
-    return hasInnerCorner;
-  }
-
-  /**
-   * Tell whether this corner has a rounded outer corner.
-   * @return true for a rounded outer corner, otherwise false.
-   */
-  boolean hasOuterCorner() {
-    return hasOuterCorner;
-  }
-
-  protected final float getPreBorderWidth() {
-    return mPreBorderWidth;
-  }
-
-  protected final float getPostBorderWidth() {
-    return mPostBorderWidth;
-  }
-
-  protected final float getOuterCornerRadius() {
-    return mCornerRadius;
-  }
-
-  protected final float getAngleBisectorDegree(){
-    return mAngleBisector;
-  }
-
-  protected final RectF getBorderBox() {
-    return mBorderBox;
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderDrawable.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderDrawable.java
deleted file mode 100644
index e4c0dfb..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderDrawable.java
+++ /dev/null
@@ -1,496 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.border;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.List;
-import java.util.Locale;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.ColorFilter;
-import android.graphics.Outline;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.PixelFormat;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.graphics.Shader;
-import android.graphics.drawable.Drawable;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.support.annotation.VisibleForTesting;
-import android.util.SparseIntArray;
-import com.taobao.weex.dom.CSSShorthand;
-import com.taobao.weex.dom.CSSShorthand.CORNER;
-import com.taobao.weex.dom.CSSShorthand.EDGE;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXViewUtils;
-
-import static com.taobao.weex.dom.CSSShorthand.CORNER.ALL;
-import static com.taobao.weex.dom.CSSShorthand.CORNER.BORDER_BOTTOM_LEFT;
-import static com.taobao.weex.dom.CSSShorthand.CORNER.BORDER_BOTTOM_RIGHT;
-import static com.taobao.weex.dom.CSSShorthand.CORNER.BORDER_TOP_LEFT;
-import static com.taobao.weex.dom.CSSShorthand.CORNER.BORDER_TOP_RIGHT;
-
-/**
- * A subclass of
- * {@link Drawable} used for background of {@link com.taobao.weex.ui.component.WXComponent}.
- * It supports drawing background color and borders (including rounded borders) by providing a react
- * friendly API (setter for each of those properties). The implementation tries to allocate as few
- * objects as possible depending on which properties are set. E.g. for views with rounded
- * background/borders we allocate {@code mPathForBorderDrawn} and {@code mTempRectForBorderRadius}.
- * In case when view have a rectangular borders we allocate {@code mBorderWidthResult} and similar.
- * When only background color is set we won't allocate any extra/unnecessary objects.
- */
-public class BorderDrawable extends Drawable {
-
-  public static final int BORDER_TOP_LEFT_RADIUS = 0;
-  public static final int BORDER_TOP_RIGHT_RADIUS = 1;
-  public static final int BORDER_BOTTOM_RIGHT_RADIUS = 2;
-  public static final int BORDER_BOTTOM_LEFT_RADIUS = 3;
-  public static final int BORDER_RADIUS_ALL = 5;
-  static final int DEFAULT_BORDER_COLOR = Color.BLACK;
-  static final float DEFAULT_BORDER_WIDTH = 0;
-  private static final BorderStyle DEFAULT_BORDER_STYLE = BorderStyle.SOLID;
-  private static final String TAG = "Border";
-  private final Paint mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
-  private static BorderStyle[] sBorderStyle = BorderStyle.values();
-
-  private
-  @Nullable
-  CSSShorthand<EDGE> mBorderWidth;
-  private
-  @Nullable
-  CSSShorthand<CORNER> mBorderRadius;
-  private
-  @Nullable
-  CSSShorthand<CORNER> mOverlappingBorderRadius;
-  private
-  @Nullable
-  SparseIntArray mBorderColor;
-  private
-  @Nullable
-  SparseIntArray mBorderStyle;
-
-  private
-  @Nullable
-  Path mPathForBorderOutline;
-  private boolean mNeedUpdatePath = false;
-  private int mColor = Color.TRANSPARENT;
-  /**
-   * set background-image linear-gradient
-   */
-  private Shader mShader = null;
-  private int mAlpha = 255;
-
-  private TopLeftCorner mTopLeftCorner;
-  private TopRightCorner mTopRightCorner;
-  private BottomRightCorner mBottomRightCorner;
-  private BottomLeftCorner mBottomLeftCorner;
-
-  private final BorderEdge mBorderEdge = new BorderEdge();
-
-  private RectF mRectBounds;
-
-  public BorderDrawable() {
-  }
-
-  @Override
-  public void draw(@NonNull Canvas canvas) {
-    canvas.save();
-    updateBorderOutline();
-    //Shader uses alpha as well.
-    mPaint.setAlpha(255);
-    if (mPathForBorderOutline != null) {
-      int useColor = WXViewUtils.multiplyColorAlpha(mColor, mAlpha);
-      if (mShader != null) {
-        mPaint.setShader(mShader);
-        mPaint.setStyle(Paint.Style.FILL);
-        canvas.drawPath(mPathForBorderOutline, mPaint);
-        mPaint.setShader(null);
-      } else if ((useColor >>> 24) != 0) {
-        mPaint.setColor(useColor);
-        mPaint.setStyle(Paint.Style.FILL);
-        canvas.drawPath(mPathForBorderOutline, mPaint);
-        mPaint.setShader(null);
-      }
-    }
-    mPaint.setStyle(Paint.Style.STROKE);
-    mPaint.setStrokeJoin(Paint.Join.ROUND);
-    drawBorders(canvas);
-    mPaint.setShader(null);
-    canvas.restore();
-  }
-
-  @Override
-  protected void onBoundsChange(Rect bounds) {
-    super.onBoundsChange(bounds);
-    mNeedUpdatePath = true;
-  }
-
-  @Override
-  public void setAlpha(int alpha) {
-    if (alpha != mAlpha) {
-      mAlpha = alpha;
-      invalidateSelf();
-    }
-  }
-
-  @Override
-  public int getAlpha() {
-    return mAlpha;
-  }
-
-  /**
-   * Do not support Color Filter
-   */
-  @Override
-  public void setColorFilter(ColorFilter cf) {
-
-  }
-
-  @Override
-  public int getOpacity() {
-    return mShader != null ? PixelFormat.OPAQUE :
-            WXViewUtils.getOpacityFromColor(WXViewUtils.multiplyColorAlpha(mColor, mAlpha));
-  }
-
-  /* Android's elevation implementation requires this to be implemented to know where to draw the
- shadow. */
-  @Override
-  public void getOutline(@NonNull Outline outline) {
-    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-      if (mPathForBorderOutline == null) {
-        mNeedUpdatePath = true;
-      }
-      updateBorderOutline();
-      outline.setConvexPath(mPathForBorderOutline);
-    }
-  }
-
-  public void setBorderWidth(CSSShorthand.EDGE edge, float width) {
-    if (mBorderWidth == null) {
-      mBorderWidth = new CSSShorthand<>();
-    }
-    if (mBorderWidth.get(edge) != width) {
-      mBorderWidth.set(edge, width);
-      mNeedUpdatePath = true;
-      invalidateSelf();
-    }
-  }
-
-  float getBorderWidth(CSSShorthand.EDGE edge) {
-    return mBorderWidth.get(edge);
-  }
-
-  public void setBorderRadius(CORNER position, float radius) {
-    if (mBorderRadius == null) {
-      mBorderRadius = new CSSShorthand<>();
-    }
-    if (mBorderRadius.get(position) != radius ||
-        (position == ALL &&
-            (radius != mBorderRadius.get(BORDER_TOP_LEFT) ||
-            radius != mBorderRadius.get(BORDER_TOP_RIGHT) ||
-            radius != mBorderRadius.get(BORDER_BOTTOM_RIGHT) ||
-            radius != mBorderRadius.get(BORDER_BOTTOM_LEFT)))) {
-      mBorderRadius.set(position, radius);
-      mNeedUpdatePath = true;
-      invalidateSelf();
-    }
-  }
-
-  public
-  @NonNull
-  float[] getBorderRadius(RectF borderBox) {
-    prepareBorderRadius(borderBox);
-    if (mOverlappingBorderRadius == null) {
-      mOverlappingBorderRadius = new CSSShorthand<>();
-    }
-    float topLeftRadius = mOverlappingBorderRadius.get(BORDER_TOP_LEFT);
-    float topRightRadius = mOverlappingBorderRadius.get(BORDER_TOP_RIGHT);
-    float bottomRightRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_RIGHT);
-    float bottomLeftRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_LEFT);
-    return new float[]{topLeftRadius, topLeftRadius,
-            topRightRadius, topRightRadius,
-            bottomRightRadius, bottomRightRadius,
-            bottomLeftRadius, bottomLeftRadius};
-  }
-
-  public
-  @NonNull
-  float[] getBorderInnerRadius(RectF borderBox) {
-    prepareBorderRadius(borderBox);
-    if (mOverlappingBorderRadius == null) {
-      mOverlappingBorderRadius = new CSSShorthand<>();
-    }
-    float topLeftRadius = mOverlappingBorderRadius.get(BORDER_TOP_LEFT);
-    float topRightRadius = mOverlappingBorderRadius.get(BORDER_TOP_RIGHT);
-    float bottomRightRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_RIGHT);
-    float bottomLeftRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_LEFT);
-    if (null != mBorderWidth) {
-      topLeftRadius = Math.max(topLeftRadius - mBorderWidth.get(EDGE.TOP), 0);
-      topRightRadius = Math.max(topRightRadius - mBorderWidth.get(EDGE.TOP), 0);
-      bottomRightRadius = Math.max(bottomRightRadius - mBorderWidth.get(EDGE.BOTTOM), 0);
-      bottomLeftRadius = Math.max(bottomLeftRadius - mBorderWidth.get(EDGE.BOTTOM), 0);
-    }
-    return new float[] {topLeftRadius, topLeftRadius,
-        topRightRadius, topRightRadius,
-        bottomRightRadius, bottomRightRadius,
-        bottomLeftRadius, bottomLeftRadius};
-  }
-
-  public void setBorderColor(CSSShorthand.EDGE edge, int color) {
-    if (mBorderColor == null) {
-      mBorderColor = new SparseIntArray(5);
-      mBorderColor.put(CSSShorthand.EDGE.ALL.ordinal(), DEFAULT_BORDER_COLOR);
-    }
-    if (getBorderColor(edge) != color) {
-      BorderUtil.updateSparseArray(mBorderColor, edge.ordinal(), color);
-      invalidateSelf();
-    }
-  }
-
-  int getBorderColor(CSSShorthand.EDGE edge) {
-    return BorderUtil.fetchFromSparseArray(mBorderColor, edge.ordinal(), DEFAULT_BORDER_COLOR);
-  }
-
-  public void setBorderStyle(CSSShorthand.EDGE edge, @NonNull String style) {
-    if (mBorderStyle == null) {
-      mBorderStyle = new SparseIntArray(5);
-      mBorderStyle.put(CSSShorthand.EDGE.ALL.ordinal(), DEFAULT_BORDER_STYLE.ordinal());
-    }
-    try {
-      int borderStyle = BorderStyle.valueOf(style.toUpperCase(Locale.US)).ordinal();
-      if (getBorderStyle(edge) != borderStyle) {
-        BorderUtil.updateSparseArray(mBorderStyle, edge.ordinal(), borderStyle);
-        invalidateSelf();
-      }
-    } catch (IllegalArgumentException e) {
-      WXLogUtils.e(TAG, WXLogUtils.getStackTrace(e));
-    }
-  }
-
-  int getBorderStyle(CSSShorthand.EDGE edge) {
-    return BorderUtil.fetchFromSparseArray(mBorderStyle, edge.ordinal(), BorderStyle.SOLID.ordinal());
-  }
-
-  public int getColor() {
-    return mColor;
-  }
-
-  public void setColor(int color) {
-    mColor = color;
-    invalidateSelf();
-  }
-
-  public void setImage(Shader shader) {
-    mShader = shader;
-    invalidateSelf();
-  }
-
-  public boolean hasImage() {
-    return mShader != null;
-  }
-
-  public boolean isRounded() {
-    return mBorderRadius != null &&
-            (mBorderRadius.get(BORDER_TOP_LEFT) != 0 ||
-                mBorderRadius.get(BORDER_TOP_RIGHT) != 0 ||
-                mBorderRadius.get(BORDER_BOTTOM_RIGHT) != 0 ||
-                mBorderRadius.get(BORDER_BOTTOM_LEFT) != 0);
-  }
-
-  public
-  @NonNull
-  Path getContentPath(@NonNull RectF borderBox) {
-    Path contentClip = new Path();
-    prepareBorderPath(0, 0, 0, 0, borderBox, contentClip);
-    return contentClip;
-  }
-
-  private void updateBorderOutline() {
-    if (mNeedUpdatePath) {
-      mNeedUpdatePath = false;
-      if (mPathForBorderOutline == null) {
-        mPathForBorderOutline = new Path();
-      }
-      mPathForBorderOutline.reset();
-      prepareBorderPath(0, 0, 0, 0, new RectF(getBounds()), mPathForBorderOutline);
-    }
-  }
-
-  private void prepareBorderPath(int topPadding,
-                                 int rightPadding,
-                                 int bottomPadding,
-                                 int leftPadding,
-                                 @NonNull RectF rectF,
-                                 @NonNull Path path) {
-    if (mBorderRadius != null) {
-      prepareBorderRadius(rectF);
-      if (mOverlappingBorderRadius == null) {
-        mOverlappingBorderRadius = new CSSShorthand<>();
-      }
-      float topLeftRadius = mOverlappingBorderRadius.get(BORDER_TOP_LEFT);
-      float topRightRadius = mOverlappingBorderRadius.get(BORDER_TOP_RIGHT);
-      float bottomRightRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_RIGHT);
-      float bottomLeftRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_LEFT);
-      path.addRoundRect(
-              rectF,
-              new float[]{
-                      topLeftRadius - leftPadding,
-                      topLeftRadius - topPadding,
-                      topRightRadius - rightPadding,
-                      topRightRadius - topPadding,
-                      bottomRightRadius - rightPadding,
-                      bottomRightRadius - bottomPadding,
-                      bottomLeftRadius - leftPadding,
-                      bottomLeftRadius - bottomPadding
-              },
-              Path.Direction.CW);
-    } else {
-      path.addRect(rectF, Path.Direction.CW);
-    }
-  }
-
-  /**
-   * Process overlapping curve according to https://www.w3.org/TR/css3-background/#corner-overlap .
-   */
-  private void prepareBorderRadius(@NonNull RectF borderBox) {
-    if (mBorderRadius != null) {
-      float factor = getScaleFactor(borderBox);
-      if (mOverlappingBorderRadius == null) {
-        mOverlappingBorderRadius = new CSSShorthand<>();
-      }
-      if (!Float.isNaN(factor) && factor < 1) {
-        mOverlappingBorderRadius.set(BORDER_TOP_LEFT,
-            mBorderRadius.get(BORDER_TOP_LEFT) * factor);
-        mOverlappingBorderRadius.set(BORDER_TOP_RIGHT,
-            mBorderRadius.get(BORDER_TOP_RIGHT) * factor);
-        mOverlappingBorderRadius.set(BORDER_BOTTOM_RIGHT,
-            mBorderRadius.get(BORDER_BOTTOM_RIGHT) * factor);
-        mOverlappingBorderRadius.set(BORDER_BOTTOM_LEFT,
-            mBorderRadius.get(BORDER_BOTTOM_LEFT) * factor);
-      } else {
-        mOverlappingBorderRadius.set(BORDER_TOP_LEFT,
-            mBorderRadius.get(BORDER_TOP_LEFT));
-        mOverlappingBorderRadius.set(BORDER_TOP_RIGHT,
-            mBorderRadius.get(BORDER_TOP_RIGHT));
-        mOverlappingBorderRadius.set(BORDER_BOTTOM_RIGHT,
-            mBorderRadius.get(BORDER_BOTTOM_RIGHT));
-        mOverlappingBorderRadius.set(BORDER_BOTTOM_LEFT,
-            mBorderRadius.get(BORDER_BOTTOM_LEFT));
-      }
-    }
-  }
-
-  private float getScaleFactor(@NonNull RectF borderBox) {
-    final float topRadius = mBorderRadius.get(BORDER_TOP_LEFT)
-            + mBorderRadius.get(BORDER_TOP_RIGHT);
-    final float rightRadius = mBorderRadius.get(BORDER_TOP_RIGHT)
-            + mBorderRadius.get(BORDER_BOTTOM_RIGHT);
-    final float bottomRadius = mBorderRadius.get(BORDER_BOTTOM_RIGHT)
-            + mBorderRadius.get(BORDER_BOTTOM_LEFT);
-    final float leftRadius = mBorderRadius.get(BORDER_BOTTOM_LEFT)
-            + mBorderRadius.get(BORDER_TOP_LEFT);
-    List<Float> factors = new ArrayList<>(4);
-    updateFactor(factors, borderBox.width(), topRadius);
-    updateFactor(factors, borderBox.height(), rightRadius);
-    updateFactor(factors, borderBox.width(), bottomRadius);
-    updateFactor(factors, borderBox.height(), leftRadius);
-    float factor;
-    if (factors.isEmpty()) {
-      factor = Float.NaN;
-    } else {
-      factor = Collections.min(factors);
-    }
-    return factor;
-  }
-
-  private void updateFactor(@NonNull List<Float> list, float numerator, float denominator) {
-    if (denominator != 0) {
-      list.add(numerator / denominator);
-    }
-  }
-
-  private void drawBorders(Canvas canvas) {
-    if (mRectBounds == null) {
-      mRectBounds = new RectF(getBounds());
-    } else {
-      mRectBounds.set(getBounds());
-    }
-
-    if (mBorderWidth == null)
-      return;
-
-    final float leftBorderWidth = mBorderWidth.get(EDGE.LEFT);
-    final float topBorderWidth = mBorderWidth.get(EDGE.TOP);
-    final float bottomBorderWidth = mBorderWidth.get(EDGE.BOTTOM);
-    final float rightBorderWidth = mBorderWidth.get(EDGE.RIGHT);
-
-    if (mTopLeftCorner == null) {
-      mTopLeftCorner = new TopLeftCorner();
-    }
-    mTopLeftCorner.set(getBorderRadius(BORDER_TOP_LEFT), leftBorderWidth, topBorderWidth, mRectBounds);
-    if (mTopRightCorner == null) {
-      mTopRightCorner = new TopRightCorner();
-    }
-    mTopRightCorner.set(getBorderRadius(BORDER_TOP_RIGHT), topBorderWidth, rightBorderWidth, mRectBounds);
-    if (mBottomRightCorner == null) {
-      mBottomRightCorner = new BottomRightCorner();
-    }
-    mBottomRightCorner.set(getBorderRadius(BORDER_BOTTOM_RIGHT), rightBorderWidth, bottomBorderWidth, mRectBounds);
-    if (mBottomLeftCorner == null) {
-      mBottomLeftCorner = new BottomLeftCorner();
-    }
-    mBottomLeftCorner.set(getBorderRadius(BORDER_BOTTOM_LEFT), bottomBorderWidth, leftBorderWidth, mRectBounds);
-
-    drawOneSide(canvas, mBorderEdge.set(mTopLeftCorner, mTopRightCorner, topBorderWidth, EDGE.TOP));
-    drawOneSide(canvas, mBorderEdge.set(mTopRightCorner, mBottomRightCorner, rightBorderWidth, EDGE.RIGHT));
-    drawOneSide(canvas, mBorderEdge.set(mBottomRightCorner, mBottomLeftCorner, bottomBorderWidth, EDGE.BOTTOM));
-    drawOneSide(canvas, mBorderEdge.set(mBottomLeftCorner, mTopLeftCorner, leftBorderWidth, EDGE.LEFT));
-  }
-
-  private float getBorderRadius(CORNER position) {
-    if (null != mOverlappingBorderRadius) {
-      return mOverlappingBorderRadius.get(position);
-    } else {
-      return 0.0f;
-    }
-  }
-
-  private void drawOneSide(Canvas canvas, @NonNull BorderEdge borderEdge) {
-    if (0 != borderEdge.getBorderWidth()) {
-      preparePaint(borderEdge.getEdge());
-      borderEdge.drawEdge(canvas, mPaint);
-    }
-  }
-
-  private void preparePaint(CSSShorthand.EDGE edge) {
-    final float borderWidth = mBorderWidth.get(edge);
-    final int color = WXViewUtils.multiplyColorAlpha(getBorderColor(edge), mAlpha);
-    final BorderStyle borderStyle = sBorderStyle[getBorderStyle(edge)];
-    final Shader shader = borderStyle.getLineShader(borderWidth, color, edge);
-    mPaint.setShader(shader);
-    mPaint.setColor(color);
-    mPaint.setStrokeCap(Paint.Cap.ROUND);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderEdge.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderEdge.java
deleted file mode 100644
index 76c4e95..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderEdge.java
+++ /dev/null
@@ -1,89 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.PointF;
-import android.support.annotation.NonNull;
-import com.taobao.weex.dom.CSSShorthand;
-
-/**
- * Edge for border. Every border has four edges, and each edge has a previous corner and a post
- * corner.
- */
-class BorderEdge {
-
-  private
-  @NonNull
-  BorderCorner mPreCorner;
-  private
-  @NonNull
-  BorderCorner mPostCorner;
-
-  private CSSShorthand.EDGE mEdge;
-  private float mBorderWidth;
-
-  BorderEdge() {
-  }
-
-  BorderEdge set(@NonNull BorderCorner preCorner, @NonNull BorderCorner postCorner,
-                 float borderWidth, CSSShorthand.EDGE edge) {
-    mPreCorner = preCorner;
-    mPostCorner = postCorner;
-    mBorderWidth = borderWidth;
-    mEdge = edge;
-    return this;
-  }
-
-  /**
-   * Draw the edge on the canvas with the specified paint.
-   * @param canvas the canvas where the edge will be drawn.
-   * @param paint the paint which is used to draw.
-   */
-  void drawEdge(@NonNull Canvas canvas, @NonNull Paint paint) {
-    paint.setStrokeWidth(mBorderWidth);
-
-    mPreCorner.drawRoundedCorner(canvas, paint, mPreCorner.getAngleBisectorDegree());
-
-    paint.setStrokeWidth(mBorderWidth);
-
-    final float lineStartX = mPreCorner.getRoundCornerEndX();
-    final float lineStartY = mPreCorner.getRoundCornerEndY();
-
-    final float lineEndX = mPostCorner.getRoundCornerStartX();
-    final float lineEndY = mPostCorner.getRoundCornerStartY();
-
-    canvas.drawLine(lineStartX, lineStartY, lineEndX, lineEndY, paint);
-
-    mPostCorner.drawRoundedCorner(canvas, paint, mPostCorner.getAngleBisectorDegree() - BorderCorner.SWEEP_ANGLE);
-  }
-
-  /**
-   * The index of the edge
-   * @return index of edge. May be one of
-   */
-  public CSSShorthand.EDGE getEdge() {
-    return mEdge;
-  }
-
-  public float getBorderWidth() {
-    return mBorderWidth;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderRadiusType.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderRadiusType.java
deleted file mode 100644
index 930ef14..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderRadiusType.java
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.ui.view.border;
-
-import android.support.annotation.IntDef;
-
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-
-@Retention(RetentionPolicy.SOURCE)
-@IntDef({
-    BorderDrawable.BORDER_TOP_LEFT_RADIUS,
-    BorderDrawable.BORDER_TOP_RIGHT_RADIUS,
-    BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS,
-    BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS,
-    BorderDrawable.BORDER_RADIUS_ALL})
-public @interface BorderRadiusType {
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderStyle.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderStyle.java
deleted file mode 100644
index 91f4ad7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderStyle.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.Color;
-import android.graphics.LinearGradient;
-import android.graphics.PathEffect;
-import android.graphics.Shader;
-import android.support.annotation.Nullable;
-import com.taobao.weex.dom.CSSShorthand;
-
-enum BorderStyle {
-  SOLID,
-  DASHED,
-  DOTTED;
-
-  /**
-   * Use {@link LinearGradient} to replace {@link PathEffect}
-   * for implementing {@link #DASHED} or {@link #DASHED}
-   * @param borderWidth width of the edge
-   * @param borderColor color of the edge
-   * @param edge the index of the ede. See {@link CSSShorthand}
-   * @return An object of {@link LinearGradient} without color transitions for {@link #DOTTED}
-   * or {@link #DASHED}, null otherwise
-   */
-  @Nullable
-  Shader getLineShader(float borderWidth, int borderColor, CSSShorthand.EDGE edge) {
-    switch (this) {
-      case DOTTED:
-        if (edge == CSSShorthand.EDGE.LEFT || edge == CSSShorthand.EDGE.RIGHT) {
-          return new LinearGradient(0, 0, 0, borderWidth * 2, new int[]{borderColor, Color
-                  .TRANSPARENT}, new float[]{0.5f, 0.5f}, Shader.TileMode.REPEAT);
-        } else if (edge == CSSShorthand.EDGE.TOP || edge == CSSShorthand.EDGE.BOTTOM) {
-          return new LinearGradient(0, 0, borderWidth * 2, 0, new int[]{borderColor, Color
-                  .TRANSPARENT}, new float[]{0.5f, 0.5f}, Shader.TileMode.REPEAT);
-        }
-      case DASHED:
-        if (edge == CSSShorthand.EDGE.LEFT || edge == CSSShorthand.EDGE.RIGHT) {
-          return new LinearGradient(0, 0, 0, borderWidth * 6, new int[]{borderColor, Color
-                  .TRANSPARENT}, new float[]{0.5f, 0.5f}, Shader.TileMode.REPEAT);
-        } else if (edge == CSSShorthand.EDGE.TOP || edge == CSSShorthand.EDGE.BOTTOM) {
-          return new LinearGradient(0, 0, borderWidth * 6, 0, new int[]{borderColor, Color
-                  .TRANSPARENT}, new float[]{0.5f, 0.5f}, Shader.TileMode.REPEAT);
-        }
-      default:
-        return null;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderUtil.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderUtil.java
deleted file mode 100644
index 9779dbe..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BorderUtil.java
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.ui.view.border;
-
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.util.SparseArray;
-import android.util.SparseIntArray;
-import com.taobao.weex.dom.CSSShorthand;
-
-class BorderUtil {
-
-  static int fetchFromSparseArray(@Nullable SparseIntArray array, int position, int fallback) {
-    return array == null ? fallback :
-            array.get(position, array.get(CSSShorthand.EDGE.ALL.ordinal()));
-  }
-
-  static void updateSparseArray(@NonNull SparseIntArray array, int position, int value) {
-    if (position == CSSShorthand.EDGE.ALL.ordinal()) {
-      array.put(CSSShorthand.EDGE.ALL.ordinal(), value);
-      array.put(CSSShorthand.EDGE.TOP.ordinal(), value);
-      array.put(CSSShorthand.EDGE.LEFT.ordinal(), value);
-      array.put(CSSShorthand.EDGE.RIGHT.ordinal(), value);
-      array.put(CSSShorthand.EDGE.BOTTOM.ordinal(), value);
-    } else {
-      array.put(position, value);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BottomLeftCorner.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BottomLeftCorner.java
deleted file mode 100644
index 40c3d14..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BottomLeftCorner.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.RectF;
-import android.support.annotation.NonNull;
-
-class BottomLeftCorner extends BorderCorner {
-
-  void set(float cornerRadius, float preBorderWidth, float postBorderWidth, @NonNull RectF borderBox) {
-    set(cornerRadius, preBorderWidth, postBorderWidth, borderBox, 135);
-  }
-
-  @Override
-  protected void prepareOval() {
-    if (hasInnerCorner()) {
-      setOvalLeft(getPostBorderWidth() / 2);
-      setOvalTop(getBorderBox().height() - (2 * getOuterCornerRadius() - getPreBorderWidth() / 2));
-      setOvalRight(2 * getOuterCornerRadius() - getPostBorderWidth() / 2);
-      setOvalBottom(getBorderBox().height() - getPreBorderWidth() / 2);
-    } else {
-      setOvalLeft(getOuterCornerRadius() / 2);
-      setOvalTop(getBorderBox().height() - 1.5f * getOuterCornerRadius());
-      setOvalRight(1.5f * getOuterCornerRadius());
-      setOvalBottom(getBorderBox().height() - getOuterCornerRadius() / 2);
-    }
-  }
-
-  @Override
-  protected void prepareRoundCorner() {
-    if (hasOuterCorner()) {
-      setRoundCornerStartX(getOuterCornerRadius());
-      setRoundCornerStartY(getBorderBox().height() - getPreBorderWidth() / 2);
-
-      setRoundCornerEndX(getPostBorderWidth() / 2);
-      setRoundCornerEndY(getBorderBox().height() - getOuterCornerRadius());
-    } else {
-      final float x = getPostBorderWidth() / 2;
-      final float y = getBorderBox().height() - getPreBorderWidth() / 2;
-
-      setRoundCornerStartX(x);
-      setRoundCornerStartY(y);
-
-      setRoundCornerEndX(x);
-      setRoundCornerEndY(y);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BottomRightCorner.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BottomRightCorner.java
deleted file mode 100644
index 82ef548..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/BottomRightCorner.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.RectF;
-import android.support.annotation.NonNull;
-
-class BottomRightCorner extends BorderCorner {
-
-  void set(float cornerRadius, float preBorderWidth, float postBorderWidth, @NonNull RectF borderBox) {
-    set(cornerRadius, preBorderWidth, postBorderWidth, borderBox, 45);
-  }
-
-  @Override
-  protected void prepareOval() {
-    if (hasInnerCorner()) {
-      setOvalLeft(getBorderBox().width() - (2 * getOuterCornerRadius() - getPreBorderWidth() / 2));
-      setOvalTop(getBorderBox().height() - (2 * getOuterCornerRadius() - getPostBorderWidth() / 2));
-      setOvalRight(getBorderBox().width() - (getPreBorderWidth() / 2));
-      setOvalBottom(getBorderBox().height() - (getPostBorderWidth() / 2));
-    } else {
-      setOvalLeft(getBorderBox().width() - 1.5f * getOuterCornerRadius());
-      setOvalTop(getBorderBox().height() - 1.5f * getOuterCornerRadius());
-      setOvalRight(getBorderBox().width() - getOuterCornerRadius() / 2);
-      setOvalBottom(getBorderBox().height() - getOuterCornerRadius() / 2);
-    }
-  }
-
-  @Override
-  protected void prepareRoundCorner() {
-    if (hasOuterCorner()) {
-      setRoundCornerStartX(getBorderBox().width() - getPreBorderWidth() / 2);
-      setRoundCornerStartY(getBorderBox().height() - getOuterCornerRadius());
-
-      setRoundCornerEndX(getBorderBox().width() - getOuterCornerRadius());
-      setRoundCornerEndY(getBorderBox().height() - getPostBorderWidth() / 2);
-    } else {
-      final float x = getBorderBox().width() - getPreBorderWidth() / 2;
-      final float y = getBorderBox().height() - getPostBorderWidth() / 2;
-
-      setRoundCornerStartX(x);
-      setRoundCornerStartY(y);
-
-      setRoundCornerEndX(x);
-      setRoundCornerEndY(y);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/TopLeftCorner.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/TopLeftCorner.java
deleted file mode 100644
index 42c9cb2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/TopLeftCorner.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.RectF;
-import android.support.annotation.NonNull;
-
-class TopLeftCorner extends BorderCorner {
-
-  void set(float cornerRadius, float preBorderWidth, float postBorderWidth, @NonNull RectF borderBox) {
-    set(cornerRadius, preBorderWidth, postBorderWidth, borderBox, 225);
-  }
-
-  @Override
-  protected void prepareOval() {
-    if (hasInnerCorner()) {
-      setOvalLeft(getPreBorderWidth() / 2);
-      setOvalTop(getPostBorderWidth() / 2);
-      setOvalRight(2 * getOuterCornerRadius() - getPreBorderWidth() / 2);
-      setOvalBottom(2 * getOuterCornerRadius() - getPostBorderWidth() / 2);
-    } else {
-      setOvalLeft(getOuterCornerRadius() / 2);
-      setOvalTop(getOuterCornerRadius() / 2);
-      setOvalRight(getOuterCornerRadius() * 1.5f);
-      setOvalBottom(getOuterCornerRadius() * 1.5f);
-    }
-  }
-
-  @Override
-  protected void prepareRoundCorner() {
-    if (hasOuterCorner()) {
-      setRoundCornerStartX(getPreBorderWidth() / 2);
-      setRoundCornerStartY(getOuterCornerRadius());
-
-      setRoundCornerEndX(getOuterCornerRadius());
-      setRoundCornerEndY(getPostBorderWidth() / 2);
-    } else {
-      final float x = getPreBorderWidth() / 2;
-      final float y = getPostBorderWidth() / 2;
-
-      setRoundCornerStartX(x);
-      setRoundCornerStartY(y);
-
-      setRoundCornerEndX(x);
-      setRoundCornerEndY(y);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/TopRightCorner.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/border/TopRightCorner.java
deleted file mode 100644
index 73a0adc..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/border/TopRightCorner.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.RectF;
-import android.support.annotation.NonNull;
-
-class TopRightCorner extends BorderCorner {
-
-  void set(float cornerRadius, float preBorderWidth, float postBorderWidth, @NonNull RectF borderBox) {
-    set(cornerRadius, preBorderWidth, postBorderWidth, borderBox, 315);
-  }
-
-  @Override
-  protected void prepareOval() {
-    if (hasInnerCorner()) {
-      setOvalLeft(getBorderBox().width() - (2 * getOuterCornerRadius() - getPostBorderWidth() / 2));
-      setOvalTop(getPreBorderWidth() / 2);
-      setOvalRight(getBorderBox().width() - getPostBorderWidth() / 2);
-      setOvalBottom(2 * getOuterCornerRadius() - getPreBorderWidth() / 2);
-    } else {
-      setOvalLeft(getBorderBox().width() - 1.5f * getOuterCornerRadius());
-      setOvalTop(getOuterCornerRadius() / 2);
-      setOvalRight(getBorderBox().width() - getOuterCornerRadius() / 2);
-      setOvalBottom(getOuterCornerRadius() * 1.5f);
-    }
-  }
-
-  @Override
-  protected void prepareRoundCorner() {
-    if (hasOuterCorner()) {
-      setRoundCornerStartX(getBorderBox().width() - getOuterCornerRadius());
-      setRoundCornerStartY(getPreBorderWidth() / 2);
-
-      setRoundCornerEndX(getBorderBox().width() - getPostBorderWidth() / 2);
-      setRoundCornerEndY(getOuterCornerRadius());
-    } else {
-      final float x = getBorderBox().width() - getPostBorderWidth() / 2;
-      final float y = getPreBorderWidth() / 2;
-
-      setRoundCornerStartX(x);
-      setRoundCornerStartY(y);
-
-      setRoundCornerEndX(x);
-      setRoundCornerEndY(y);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGesture.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGesture.java
deleted file mode 100644
index 6e88d67..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGesture.java
+++ /dev/null
@@ -1,663 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.gesture;
-
-import static com.taobao.weex.common.Constants.Event.STOP_PROPAGATION;
-import static com.taobao.weex.common.Constants.Event.STOP_PROPAGATION_RAX;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.graphics.Rect;
-import android.os.Looper;
-import android.support.annotation.NonNull;
-import android.view.GestureDetector;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.View.OnTouchListener;
-import android.view.ViewGroup;
-import android.view.ViewParent;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weex.bridge.EventResult;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.dom.WXEvent;
-import com.taobao.weex.ui.component.Scrollable;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.view.gesture.WXGestureType.GestureInfo;
-import com.taobao.weex.ui.view.gesture.WXGestureType.HighLevelGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureType.LowLevelGesture;
-import com.taobao.weex.utils.WXLogUtils;
-import com.taobao.weex.utils.WXUtils;
-import com.taobao.weex.utils.WXViewUtils;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-
-public class WXGesture extends GestureDetector.SimpleOnGestureListener implements OnTouchListener {
-
-  private final static String TAG = "Gesture";
-  private static final int CUR_EVENT = -1;
-  public static final String START = "start";
-  public static final String MOVE = "move";
-  public static final String END = "end";
-  public static final String UNKNOWN = "unknown";
-  public static final String LEFT = "left";
-  public static final String RIGHT = "right";
-  public static final String UP = "up";
-  public static final String DOWN = "down";
-  private WXComponent component;
-  private GestureDetector mGestureDetector;
-  private Rect globalRect;
-  private Point globalOffset;
-  private Point globalEventOffset;
-  private PointF locEventOffset;
-  private PointF locLeftTop;
-  private long swipeDownTime = -1;
-  private long panDownTime = -1;
-  private WXGestureType mPendingPan = null;//event type to notify when action_up or action_cancel
-  private int mParentOrientation =-1;
-  private boolean mIsPreventMoveEvent = false;
-  private boolean mIsTouchEventConsumed = false; //Reset to false when first touch event, set to true when gesture event fired.
-
-  private boolean requestDisallowInterceptTouchEvent = false;
-
-  private boolean shouldBubbleResult = true;
-  private int     shouldBubbleInterval = 0; //every times try
-  private int     shouldBubbleCallRemainTimes = 0;
-
-  private final List<OnTouchListener> mTouchListeners = new LinkedList<>();
-
-  public WXGesture(WXComponent wxComponent, Context context) {
-    this.component = wxComponent;
-    globalRect = new Rect();
-    globalOffset = new Point();
-    globalEventOffset = new Point();
-    locEventOffset = new PointF();
-    locLeftTop = new PointF();
-    mGestureDetector = new GestureDetector(context, this, new GestureHandler());
-    Scrollable parentScrollable = wxComponent.getParentScroller();
-    if(parentScrollable != null) {
-      mParentOrientation = parentScrollable.getOrientation();
-    }
-    shouldBubbleResult =  WXUtils.getBoolean(wxComponent.getAttrs().get(Constants.Name.SHOULD_STOP_PROPAGATION_INIT_RESULT), true);
-    shouldBubbleInterval = WXUtils.getNumberInt(wxComponent.getAttrs().get(Constants.Name.SHOULD_STOP_PROPAGATION_INTERVAL), 0);
-  }
-
-  private boolean isParentScrollable() {
-    if(component == null) {
-      return true;
-    }
-    Scrollable parentScrollable = component.getParentScroller();
-    return parentScrollable == null || parentScrollable.isScrollable();
-  }
-
-  private boolean hasSameOrientationWithParent(){
-    return (mParentOrientation == Constants.Orientation.HORIZONTAL && component.containsGesture(HighLevelGesture.HORIZONTALPAN))
-            || (mParentOrientation == Constants.Orientation.VERTICAL && component.containsGesture(HighLevelGesture.VERTICALPAN));
-  }
-
-  public void setPreventMoveEvent(boolean preventMoveEvent) {
-    mIsPreventMoveEvent = preventMoveEvent;
-  }
-
-  /**
-   *
-   * @return true if current touch event is already consumed by gesture.
-   * Reset to false when next first touch event, set to true when gesture event fired.
-   */
-  public boolean isTouchEventConsumedByAdvancedGesture(){
-    return mIsTouchEventConsumed;
-  }
-
-
-  /**
-   * stoppropagation
-   * */
-  public static boolean isStopPropagation(String type){
-    return  Constants.Event.STOP_PROPAGATION.equals(type) || Constants.Event.STOP_PROPAGATION_RAX.equals(type);
-  }
-
-  public static boolean hasStopPropagation(WXComponent component){
-    WXEvent event = component.getEvents();
-    if(event == null){
-      return false;
-    }
-    int size = event.size();
-    for (int i=0; i<size; i++) {
-      if(i >= event.size()){
-        break;
-      }
-      String type = event.get(i);
-      if(isStopPropagation(type)){
-        return true;
-      }
-    }
-    return false;
-  }
-
-  /**
-   * shouldBubbleEvent default true
-   * */
-  private boolean shouldBubbleTouchEvent(MotionEvent event){
-    if(hasStopPropagation(component)){
-      if(shouldBubbleInterval > 0 && shouldBubbleCallRemainTimes > 0){
-        shouldBubbleCallRemainTimes--;
-        return  shouldBubbleResult;
-      }
-      Map<String, Object> eventMap = createFireEventParam(event, CUR_EVENT, null);
-      eventMap.put("type", "touch");
-      if(event.getAction() == MotionEvent.ACTION_DOWN){
-        eventMap.put("action", START);
-      }else if(event.getAction() == MotionEvent.ACTION_CANCEL
-              ||  event.getAction() == MotionEvent.ACTION_UP){
-        eventMap.put("action", END);
-      }else{
-        eventMap.put("action", MOVE);
-      }
-
-      String name = STOP_PROPAGATION;
-      if(!component.getEvents().contains(STOP_PROPAGATION)){
-         name = STOP_PROPAGATION_RAX;
-      }
-      EventResult result = component.fireEventWait(name, eventMap);
-      if(result.isSuccess() && result.getResult() != null){
-        boolean stopPropagation = WXUtils.getBoolean(result.getResult(), !shouldBubbleResult);
-        shouldBubbleResult = !stopPropagation;
-      }
-      shouldBubbleCallRemainTimes = shouldBubbleInterval;
-      return shouldBubbleResult;
-
-    }
-    return  true;
-  }
-
-  @SuppressWarnings("unused")
-  public void addOnTouchListener(OnTouchListener listener) {
-    if(listener != null) {
-      mTouchListeners.add(listener);
-    }
-  }
-
-  @SuppressWarnings("unused")
-  public boolean removeTouchListener(OnTouchListener listener) {
-    if(listener != null) {
-      return mTouchListeners.remove(listener);
-    }
-    return false;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouch(View v, MotionEvent event) {
-    if(requestDisallowInterceptTouchEvent){
-      requestDisallowInterceptTouchEvent = false;
-      return false;
-    }
-    try {
-      boolean result = mGestureDetector.onTouchEvent(event);
-
-      if(mTouchListeners != null && !mTouchListeners.isEmpty()) {
-        for(OnTouchListener listener : mTouchListeners) {
-          result |= listener.onTouch(v, event);
-        }
-      }
-
-      switch (event.getActionMasked()) {
-        case MotionEvent.ACTION_POINTER_DOWN:
-        case MotionEvent.ACTION_DOWN:
-          mIsTouchEventConsumed = false;
-          /**
-           * If component has same scroll orientation with it's parent and it's parent not scrollable
-           * , we should disallow parent in DOWN.
-           */
-          if(hasSameOrientationWithParent() && !isParentScrollable()){
-            ViewParent p;
-            if ((p = component.getRealView().getParent()) != null) {
-              p.requestDisallowInterceptTouchEvent(true);
-            }
-          }
-          result |= handleMotionEvent(LowLevelGesture.ACTION_DOWN, event);
-          break;
-        case MotionEvent.ACTION_MOVE:
-          result |= handleMotionEvent(LowLevelGesture.ACTION_MOVE, event);
-          break;
-        case MotionEvent.ACTION_UP:
-        case MotionEvent.ACTION_POINTER_UP:
-          finishDisallowInterceptTouchEvent(v);
-          result |= handleMotionEvent(LowLevelGesture.ACTION_UP, event);
-          result |= handlePanMotionEvent(event);
-          break;
-        case MotionEvent.ACTION_CANCEL:
-          finishDisallowInterceptTouchEvent(v);
-          result |= handleMotionEvent(LowLevelGesture.ACTION_CANCEL, event);
-          result |= handlePanMotionEvent(event);
-          break;
-      }
-      if(hasStopPropagation(component)){
-        ViewGroup parent = (ViewGroup) v.getParent();
-        boolean requestDisallowInterceptTouchEvent = false;
-        if(parent != null){
-          if(!shouldBubbleTouchEvent(event)){
-            requestDisallowInterceptTouchEvent = true;
-          }
-          parent.requestDisallowInterceptTouchEvent(requestDisallowInterceptTouchEvent);
-        }
-        if(component.getParent() != null){
-          component.getParent().requestDisallowInterceptTouchEvent(requestDisallowInterceptTouchEvent);
-        }
-        if(mIsTouchEventConsumed && WXUtils.getBoolean(component.getAttrs().get("cancelTouchOnConsume"), false)){//when touch event consumed by one gesture, other component should not consumed
-          event.setAction(MotionEvent.ACTION_CANCEL);
-        }
-      }
-      return result;
-    } catch (Exception e) {
-      WXLogUtils.e("Gesture RunTime Error ", e);
-      return false;
-    }
-  }
-
-  private String getPanEventAction(MotionEvent event) {
-    switch (event.getAction()) {
-      case MotionEvent.ACTION_DOWN:
-        return START;
-      case MotionEvent.ACTION_MOVE:
-        return MOVE;
-      case MotionEvent.ACTION_UP:
-        return END;
-      case MotionEvent.ACTION_CANCEL:
-        return END;
-      default:
-        return UNKNOWN;
-    }
-  }
-
-  private void finishDisallowInterceptTouchEvent(View v){
-    if(v.getParent() != null){
-      v.getParent().requestDisallowInterceptTouchEvent(false);
-    }
-  }
-
-  private boolean handlePanMotionEvent(MotionEvent motionEvent) {
-    if (mPendingPan == null) {
-      return false;
-    }
-    String state = null;
-    if (mPendingPan == HighLevelGesture.HORIZONTALPAN || mPendingPan == HighLevelGesture.VERTICALPAN) {
-      state = getPanEventAction(motionEvent);
-
-    }
-
-    if (component.containsGesture(mPendingPan)) {
-      if(mIsPreventMoveEvent && MOVE.equals(state)){
-        return true;
-      }
-      List<Map<String, Object>> list = createMultipleFireEventParam(motionEvent, state);
-      for (Map<String, Object> map : list) {
-        component.fireEvent(mPendingPan.toString(), map);
-      }
-      //action is finish, clean pending pan
-      if (motionEvent.getAction() == MotionEvent.ACTION_UP || motionEvent.getAction() == MotionEvent.ACTION_CANCEL) {
-        mPendingPan = null;
-      }
-      return true;
-    } else {
-      return false;
-    }
-  }
-
-  /**
-   *
-   * @param WXGestureType possible low-level gesture, defined in {@link com.taobao.weex.common.Constants.Event}
-   * @param motionEvent motionEvent, which contains all pointers event in a period of time
-   * @return true if this event is handled, otherwise false.
-   */
-  private boolean handleMotionEvent(WXGestureType WXGestureType, MotionEvent motionEvent) {
-    if (component.containsGesture(WXGestureType)) {
-      List<Map<String, Object>> list = createMultipleFireEventParam(motionEvent, null);
-      for (Map<String, Object> map : list) {
-        component.fireEvent(WXGestureType.toString(), map);
-      }
-      return true;
-    } else {
-      return false;
-    }
-  }
-
-  /**
-   * Create a list of event for {@link com.taobao.weex.WXSDKInstance#fireEvent(String, String, Map, Map)}.
-   * As there is a batch mechanism in MotionEvent, so this method returns a list.
-   * @param motionEvent motionEvent, which contains all pointers event in a period of time
-   * @return List of Map, which contains touch object.
-   */
-  private List<Map<String, Object>> createMultipleFireEventParam(MotionEvent motionEvent,String state) {
-    List<Map<String, Object>> list = new ArrayList<>(motionEvent.getHistorySize() + 1);
-    //list.addAll(getHistoricalEvents(motionEvent));
-    list.add(createFireEventParam(motionEvent, CUR_EVENT, state));
-    return list;
-  }
-
-  /**
-   * Get historical event. This is only applied to {@link MotionEvent#ACTION_MOVE}.
-   * For other types of motionEvent, historical event is meaningless.
-   * @param motionEvent motionEvent, which contains all pointers event in a period of time
-   * @return If motionEvent.getActionMasked()!=MotionEvent.ACTION_MOVE,
-   * this method will return an empty list.
-   * Otherwise this method will return the historical motionEvent, which may also be empty.
-   */
-  private List<Map<String, Object>> getHistoricalEvents(MotionEvent motionEvent) {
-    List<Map<String, Object>> list = new ArrayList<>(motionEvent.getHistorySize());
-    if (motionEvent.getActionMasked() == MotionEvent.ACTION_MOVE) {
-      Map<String, Object> param;
-      for (int i = 0; i < motionEvent.getHistorySize(); i++) {
-        param = createFireEventParam(motionEvent, i,null);
-        list.add(param);
-      }
-    }
-    return list;
-  }
-
-  /**
-   * Create a map represented touch event at a certain moment.
-   * @param motionEvent motionEvent, which contains all pointers event in a period of time
-   * @param pos index used to retrieve a certain moment in a period of time.
-   * @return touchEvent
-   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/TouchEvent">touchEvent</a>
-   */
-  private Map<String, Object> createFireEventParam(MotionEvent motionEvent, int pos, String state) {
-    JSONArray jsonArray = new JSONArray(motionEvent.getPointerCount());
-    if (motionEvent.getActionMasked() == MotionEvent.ACTION_MOVE) {
-      for (int i = 0; i < motionEvent.getPointerCount(); i++) {
-        jsonArray.add(createJSONObject(motionEvent, pos, i));
-      }
-    } else if (isPointerNumChanged(motionEvent)) {
-      int pointerIndex = motionEvent.getActionIndex();
-      jsonArray.add(createJSONObject(motionEvent, CUR_EVENT, pointerIndex));
-    }
-    Map<String, Object> map = new HashMap<>();
-    map.put(GestureInfo.HISTORICAL_XY, jsonArray);
-    if (state != null) {
-      map.put(GestureInfo.STATE, state);
-    }
-    return map;
-  }
-
-  /**
-   * Tell whether the number of motion event's pointer changed.
-   * @param event the current motion event
-   * @return true for number of motion event's pointer changed, otherwise false.
-   */
-  private boolean isPointerNumChanged(MotionEvent event) {
-    return event.getActionMasked() == MotionEvent.ACTION_DOWN ||
-            event.getActionMasked() == MotionEvent.ACTION_POINTER_DOWN ||
-            event.getActionMasked() == MotionEvent.ACTION_UP ||
-            event.getActionMasked() == MotionEvent.ACTION_POINTER_UP ||
-            event.getActionMasked() == MotionEvent.ACTION_CANCEL;
-  }
-
-  /**
-   * Tell whether component contains pan gesture
-   * @return true for contains pan gesture, otherwise false.
-   */
-  private boolean containsSimplePan() {
-    return component.containsGesture(HighLevelGesture.PAN_START) ||
-            component.containsGesture(HighLevelGesture.PAN_MOVE) ||
-            component.containsGesture(HighLevelGesture.PAN_END);
-  }
-
-  /**
-   * Create a touchObject for a pointer at a certain moment.
-   * @param motionEvent motionEvent, which contains all pointers event in a period of time
-   * @param pos index used to retrieve a certain moment in a period of time.
-   * @param pointerIndex pointerIndex
-   * @return JSONObject represent a touch event
-   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch">touch</a>
-   */
-  private JSONObject createJSONObject(MotionEvent motionEvent, int pos, int pointerIndex) {
-    PointF screenXY, pageXY;
-    if (pos == CUR_EVENT) {
-      pageXY = getEventLocInPageCoordinate(motionEvent, pointerIndex);
-      screenXY = getEventLocInScreenCoordinate(motionEvent, pointerIndex);
-    } else {
-      pageXY = getEventLocInPageCoordinate(motionEvent, pointerIndex, pos);
-      screenXY = getEventLocInScreenCoordinate(motionEvent, pointerIndex, pos);
-    }
-    JSONObject map = createJSONObject(screenXY, pageXY, (float) motionEvent.getPointerId(pointerIndex));
-    float force = motionEvent.getPressure();
-    if(force > 0 && force < 1) {
-      map.put("force", motionEvent.getPressure());
-    }
-    return map;
-  }
-
-  /**
-   * Create a touchObject for a pointer at a certain moment.
-   * @param screenXY the point of event happened in screen coordinate
-   * @param pageXY the point of event happened in page coorindate
-   * @param pointerId pointerIndex pointerIndex
-   * @return JSONObject represent a touch event
-   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch">touch</a>
-   */
-  @NonNull
-  private JSONObject createJSONObject(PointF screenXY, PointF pageXY, float pointerId) {
-    JSONObject jsonObject = new JSONObject();
-    jsonObject.put(GestureInfo.PAGE_X, pageXY.x);
-    jsonObject.put(GestureInfo.PAGE_Y, pageXY.y);
-    jsonObject.put(GestureInfo.SCREEN_X, screenXY.x);
-    jsonObject.put(GestureInfo.SCREEN_Y, screenXY.y);
-    jsonObject.put(GestureInfo.POINTER_ID, pointerId);
-    return jsonObject;
-  }
-
-  /**
-   * @see {@link #getEventLocInScreenCoordinate(MotionEvent, int, int)}
-   */
-  private PointF getEventLocInScreenCoordinate(MotionEvent motionEvent, int pointerIndex) {
-    return getEventLocInScreenCoordinate(motionEvent, pointerIndex, CUR_EVENT);
-  }
-
-  /**
-   * Get event location in Screen's coordinate, e.g. root(global) coordinate.
-   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/screenX">screenX</a>
-   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/screenY">screenY</a>
-   * @param motionEvent the original motionEvent
-   * @param pointerIndex pointerIndex
-   * @param position if motionEvent.getHistoricalSize()!=0, the is the index of historical event,
-   *                 otherwise this is {@link #CUR_EVENT} which indicates historicalSize is zero
-   * @return the eventLocation in screen's coordinate
-   */
-  private PointF getEventLocInScreenCoordinate(MotionEvent motionEvent, int pointerIndex, int position) {
-    float eventX, eventY;
-    if (position == CUR_EVENT) {
-      eventX = motionEvent.getX(pointerIndex);
-      eventY = motionEvent.getY(pointerIndex);
-    } else {
-      eventX = motionEvent.getHistoricalX(pointerIndex, position);
-      eventY = motionEvent.getHistoricalY(pointerIndex, position);
-    }
-    return getEventLocInScreenCoordinate(eventX, eventY);
-  }
-
-  /**
-   * Get event location in Screen's coordinate, e.g. root(global) coordinate.
-   * @param eventX {@link MotionEvent#getX()} or {@link MotionEvent#getHistoricalX(int, int)}
-   * @param eventY {@link MotionEvent#getX()} or {@link MotionEvent#getHistoricalX(int, int)}
-   * @return the eventLocation in screen's coordinate
-   * @see {@link #getEventLocInScreenCoordinate(MotionEvent, int, int)}
-   */
-  @NonNull
-  private PointF getEventLocInScreenCoordinate(float eventX, float eventY) {
-    globalRect.set(0, 0, 0, 0);
-    globalOffset.set(0, 0);
-    globalEventOffset.set((int) eventX, (int) eventY);
-    component.getRealView().getGlobalVisibleRect(globalRect, globalOffset);
-    globalEventOffset.offset(globalOffset.x, globalOffset.y);
-    return new PointF(WXViewUtils.getWebPxByWidth(globalEventOffset.x,component.getInstance().getInstanceViewPortWidth()),
-            WXViewUtils.getWebPxByWidth(globalEventOffset.y,component.getInstance().getInstanceViewPortWidth()));
-  }
-
-  /**
-   * @see {@link #getEventLocInPageCoordinate(MotionEvent, int, int)}
-   */
-  private PointF getEventLocInPageCoordinate(MotionEvent motionEvent, int pointerIndex) {
-    return getEventLocInPageCoordinate(motionEvent, pointerIndex, CUR_EVENT);
-  }
-
-  /**
-   * Get event's location in Document's (Page) coordinate.
-   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/pageX">pageX</a>
-   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/pageY">pageY</a>
-   * @param motionEvent the original motionEvent
-   * @param pointerIndex pointerIndex
-   * @param position if motionEvent.getHistoricalSize()!=0, the is the index of historical event,
-   *                 otherwise this is {@link #CUR_EVENT} which indicates historicalSize is zero
-   * @return the event location in page's coordinate.
-   */
-  private PointF getEventLocInPageCoordinate(MotionEvent motionEvent, int pointerIndex, int position) {
-    float eventX, eventY;
-    if (position == CUR_EVENT) {
-      eventX = motionEvent.getX(pointerIndex);
-      eventY = motionEvent.getY(pointerIndex);
-    } else {
-      eventX = motionEvent.getHistoricalX(pointerIndex, position);
-      eventY = motionEvent.getHistoricalY(pointerIndex, position);
-    }
-    return getEventLocInPageCoordinate(eventX, eventY);
-  }
-
-  /**
-   * Get event's location in Document's (Page) coordinate.
-   * @param eventX {@link MotionEvent#getX()} or {@link MotionEvent#getHistoricalX(int, int)}
-   * @param eventY {@link MotionEvent#getX()} or {@link MotionEvent#getHistoricalX(int, int)}
-   * @return the event location in page's coordinate.
-   * @see {@link #getEventLocInPageCoordinate(MotionEvent, int, int)}
-   */
-  @NonNull
-  private PointF getEventLocInPageCoordinate(float eventX, float eventY) {
-    locEventOffset.set(eventX, eventY);
-    locLeftTop.set(0, 0);
-    component.computeVisiblePointInViewCoordinate(locLeftTop);
-    locEventOffset.offset(locLeftTop.x, locLeftTop.y);
-    return new PointF(WXViewUtils.getWebPxByWidth(locEventOffset.x,component.getInstance().getInstanceViewPortWidth()),
-            WXViewUtils.getWebPxByWidth(locEventOffset.y,component.getInstance().getInstanceViewPortWidth()));
-  }
-
-  private static class GestureHandler extends android.os.Handler {
-
-    public GestureHandler() {
-      super(Looper.getMainLooper());
-    }
-  }
-
-
-  /***************** OnGestureListener ****************/
-
-  @Override
-  public void onLongPress(MotionEvent e) {
-    if (component.containsGesture(HighLevelGesture.LONG_PRESS)) {
-      List<Map<String, Object>> list = createMultipleFireEventParam(e,null);
-      component.getInstance().fireEvent(
-              component.getRef(),
-              HighLevelGesture.LONG_PRESS.toString(),
-              list.get(list.size() - 1));
-      mIsTouchEventConsumed = true;
-    }
-  }
-
-  /**
-   * Gesture priority：horizontalPan & verticalPan > pan > swipe
-   */
-  @Override
-  public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
-    boolean result = false;
-    if (e1 == null || e2 == null) {
-      return false;
-    }
-    float dx = Math.abs(e2.getX() - e1.getX());
-    float dy = Math.abs(e2.getY() - e1.getY());
-    WXGestureType possiblePan;
-    if (dx > dy) {
-      possiblePan = HighLevelGesture.HORIZONTALPAN;
-    } else {
-      possiblePan = HighLevelGesture.VERTICALPAN;
-    }
-    if (mPendingPan == HighLevelGesture.HORIZONTALPAN || mPendingPan == HighLevelGesture.VERTICALPAN) {
-      //already during directional-pan
-      result = handlePanMotionEvent(e2);
-    } else if (component.containsGesture(possiblePan)) {
-      ViewParent p;
-      if ((p = component.getRealView().getParent()) != null) {
-        p.requestDisallowInterceptTouchEvent(true);
-      }
-      if (mPendingPan != null) {
-        handleMotionEvent(mPendingPan, e2);//finish pan if exist
-      }
-      mPendingPan = possiblePan;
-      component.fireEvent(possiblePan.toString(), createFireEventParam(e2, CUR_EVENT, START));
-
-      result = true;
-    } else if (containsSimplePan()) {
-      if (panDownTime != e1.getEventTime()) {
-        panDownTime = e1.getEventTime();
-        mPendingPan = HighLevelGesture.PAN_END;
-        component.fireEvent(HighLevelGesture.PAN_START.toString(),
-                createFireEventParam(e1, CUR_EVENT, null));
-      } else {
-        component.fireEvent(HighLevelGesture.PAN_MOVE.toString(),
-                createFireEventParam(e2, CUR_EVENT, null));
-      }
-      result = true;
-    } else if (component.containsGesture(HighLevelGesture.SWIPE)) {
-      if (swipeDownTime != e1.getEventTime()) {
-        swipeDownTime = e1.getEventTime();
-        List<Map<String, Object>> list = createMultipleFireEventParam(e2, null);
-        Map<String, Object> param = list.get(list.size() - 1);
-        if (Math.abs(distanceX) > Math.abs(distanceY)) {
-          param.put(GestureInfo.DIRECTION, distanceX > 0 ? LEFT : RIGHT);
-        } else {
-          param.put(GestureInfo.DIRECTION, distanceY > 0 ? UP : DOWN);
-        }
-        component.getInstance().fireEvent(component.getRef(),
-                HighLevelGesture.SWIPE.toString(), param);
-        result = true;
-      }
-    }
-    mIsTouchEventConsumed = mIsTouchEventConsumed || result;
-    return result;
-  }
-
-  @Override
-  public boolean onDown(MotionEvent e) {
-    return true;
-  }
-
-  public boolean isRequestDisallowInterceptTouchEvent() {
-    return requestDisallowInterceptTouchEvent;
-  }
-
-  public void setRequestDisallowInterceptTouchEvent(boolean requestDisallowInterceptTouchEvent) {
-    this.requestDisallowInterceptTouchEvent = requestDisallowInterceptTouchEvent;
-  }
-
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGestureObservable.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGestureObservable.java
deleted file mode 100644
index e568793..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGestureObservable.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.gesture;
-
-import android.support.annotation.Nullable;
-import android.view.MotionEvent;
-import android.view.View;
-
-import com.taobao.weex.ui.view.WXFrameLayout;
-
-/**
- * Views that want to receive Gesture Event must implement this interface. Besides,
- * those view must override their {@link android.view.View#onTouchEvent(MotionEvent)}
- * and add method invocation to {@link WXGesture#onTouch(View, MotionEvent)}.
- * Refer to {@link WXFrameLayout#onTouchEvent(MotionEvent)} for more info.
- *
- */
-public interface WXGestureObservable {
-
-  /**
-   * Register a {@link WXGesture} for corresponding view.
-   * @param wxGesture The Gesture to register, null for unregister.
-   */
-  void registerGestureListener(@Nullable WXGesture wxGesture);
-
-  /**
-   * Get gesture listener for corresponding view.
-   *
-   * @return the gesture listener has register before
-   *
-   * */
-  WXGesture getGestureListener();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGestureType.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGestureType.java
deleted file mode 100644
index 807daac..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/gesture/WXGestureType.java
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.gesture;
-
-public interface WXGestureType {
-
-  enum LowLevelGesture implements WXGestureType {
-    ACTION_DOWN("touchstart"),
-    ACTION_MOVE("touchmove"),
-    ACTION_UP("touchend"),
-    ACTION_CANCEL("touchcancel");
-    private String description;
-
-    LowLevelGesture(String description) {
-      this.description = description;
-    }
-
-    @Override
-    public String toString() {
-      return description;
-    }
-  }
-
-  enum HighLevelGesture implements WXGestureType {
-    SWIPE("swipe"),
-    LONG_PRESS("longpress"),
-    PAN_START("panstart"),
-    PAN_MOVE("panmove"),
-    PAN_END("panend"),
-    HORIZONTALPAN("horizontalpan"),
-    VERTICALPAN("verticalpan");
-    private String description;
-
-    HighLevelGesture(String description) {
-      this.description = description;
-    }
-
-    @Override
-    public String toString() {
-      return description;
-    }
-  }
-
-  class GestureInfo {
-
-    public static final String HISTORICAL_XY = "changedTouches";
-    public static final String PAGE_X = "pageX";
-    public static final String PAGE_Y = "pageY";
-    public static final String SCREEN_X = "screenX";
-    public static final String SCREEN_Y = "screenY";
-    public static final String POINTER_ID = "identifier";
-    public static final String DIRECTION = "direction";
-    public static final String STATE = "state";
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/ExtendedLinearLayoutManager.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/ExtendedLinearLayoutManager.java
deleted file mode 100644
index bdb5f91..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/ExtendedLinearLayoutManager.java
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview;
-
-import android.content.Context;
-import android.graphics.PointF;
-import android.support.v7.widget.LinearLayoutManager;
-import android.support.v7.widget.LinearSmoothScroller;
-import android.support.v7.widget.RecyclerView;
-
-/**
- * Created by moxun on 17/2/16.
- */
-
-public class ExtendedLinearLayoutManager extends LinearLayoutManager{
-
-    private RecyclerView.SmoothScroller smoothScroller;
-
-
-    private OnSmoothScrollEndListener onScrollEndListener;
-
-    public ExtendedLinearLayoutManager(Context context) {
-        super(context, VERTICAL, false);
-    }
-
-    public ExtendedLinearLayoutManager(Context context, int orientation, boolean reverseLayout) {
-        super(context, orientation, reverseLayout);
-    }
-
-    @Override
-    public boolean supportsPredictiveItemAnimations() {
-        return false;
-    }
-
-    public void onLayoutChildren(RecyclerView.Recycler recycler, RecyclerView.State state) {
-        try {
-            super.onLayoutChildren(recycler, state);
-        } catch (IndexOutOfBoundsException e) {
-            e.printStackTrace();
-
-        }
-    }
-
-    @Override
-    public int scrollVerticallyBy(int dy, RecyclerView.Recycler recycler, RecyclerView.State state) {
-        try {
-            return super.scrollVerticallyBy(dy, recycler, state);
-        } catch (Exception e) {
-            e.printStackTrace();
-        }
-        return 0;
-    }
-
-
-    @Override
-    public void smoothScrollToPosition(RecyclerView recyclerView, RecyclerView.State state,
-                                       int position) {
-        if (smoothScroller == null) {
-            smoothScroller = new ExtendedLinearLayoutManager.TopSnappedSmoothScroller(recyclerView.getContext());
-        }
-        smoothScroller.setTargetPosition(position);
-        startSmoothScroll(smoothScroller);
-    }
-
-    private class TopSnappedSmoothScroller extends LinearSmoothScroller {
-        public TopSnappedSmoothScroller(Context context) {
-            super(context);
-
-        }
-
-        @Override
-        public PointF computeScrollVectorForPosition(int targetPosition) {
-            return ExtendedLinearLayoutManager.this
-                    .computeScrollVectorForPosition(targetPosition);
-        }
-
-        @Override
-        protected int getVerticalSnapPreference() {
-            return SNAP_TO_START;
-        }
-
-        @Override
-        protected void onStop() {
-            super.onStop();
-            if(onScrollEndListener != null){
-                onScrollEndListener.onStop();
-                onScrollEndListener = null;
-            }
-        }
-    }
-
-    public void setOnScrollEndListener(OnSmoothScrollEndListener onScrollEndListener) {
-        this.onScrollEndListener = onScrollEndListener;
-    }
-
-    public interface OnSmoothScrollEndListener {
-        void  onStop();
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/ExtendedStaggeredGridLayoutManager.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/ExtendedStaggeredGridLayoutManager.java
deleted file mode 100644
index ee27ab2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/ExtendedStaggeredGridLayoutManager.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview;
-
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.utils.WXLogUtils;
-
-/**
- * Created by zhengshihan on 2017/5/5.
- */
-
-public class ExtendedStaggeredGridLayoutManager extends StaggeredGridLayoutManager{
-
-  public ExtendedStaggeredGridLayoutManager(int spanCount, int orientation) {
-    super(spanCount, orientation);
-  }
-
-  @Override
-  public void onItemsRemoved(RecyclerView recyclerView, int positionStart, int itemCount) {
-    if(positionStart ==-1){
-      WXLogUtils.e("ExtendedStaggeredGridLayoutManager: onItemsRemoved  Error Invalid Index : positionStart :"+positionStart +"  itemCount:"+ itemCount);
-      return ;
-    }else {
-      if(WXEnvironment.isApkDebugable()){
-        WXLogUtils.e("ExtendedStaggeredGridLayoutManager: onItemsRemoved  positionStart :"+positionStart+"  itemCount:"+ itemCount);
-      }
-    }
-    super.onItemsRemoved(recyclerView, positionStart, itemCount);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/WXRecyclerView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/WXRecyclerView.java
deleted file mode 100644
index 3f0d990..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/WXRecyclerView.java
+++ /dev/null
@@ -1,157 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview;
-
-import android.annotation.SuppressLint;
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.os.Build;
-import android.support.annotation.Nullable;
-import android.support.v7.widget.GridLayoutManager;
-import android.support.v7.widget.LinearLayoutManager;
-import android.support.v7.widget.OrientationHelper;
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-import android.view.MotionEvent;
-
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-
-public class WXRecyclerView extends RecyclerView implements WXGestureObservable {
-
-  public static final int TYPE_LINEAR_LAYOUT = 1;
-  public static final int TYPE_GRID_LAYOUT = 2;
-  public static final int TYPE_STAGGERED_GRID_LAYOUT = 3;
-  private WXGesture mGesture;
-  private boolean scrollable = true;
-  private boolean hasTouch = false;
-
-
-  public WXRecyclerView(Context context) {
-    super(context);
-  }
-
-  public boolean isScrollable() {
-    return scrollable;
-  }
-
-  public void setScrollable(boolean scrollable) {
-    this.scrollable = scrollable;
-  }
-
-  public void initView(Context context, int type,int orientation) {
-    initView(context,type, Constants.Value.COLUMN_COUNT_NORMAL,Constants.Value.COLUMN_GAP_NORMAL,orientation);
-  }
-
-
-  /**
-   *
-   * @param context
-   * @param type
-   * @param orientation should be {@link OrientationHelper#HORIZONTAL} or {@link OrientationHelper#VERTICAL}
-   */
-  @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
-  public void initView(Context context, int type, int columnCount, float columnGap, int orientation) {
-    if (type == TYPE_GRID_LAYOUT) {
-      setLayoutManager(new GridLayoutManager(context, columnCount,orientation,false));
-    } else if (type == TYPE_STAGGERED_GRID_LAYOUT) {
-      setLayoutManager(new ExtendedStaggeredGridLayoutManager(columnCount, orientation));
-    } else if (type == TYPE_LINEAR_LAYOUT) {
-      setLayoutManager(new ExtendedLinearLayoutManager(context,orientation,false));
-    }
-  }
-
-  @Override
-  public void registerGestureListener(@Nullable WXGesture wxGesture) {
-    mGesture = wxGesture;
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return mGesture;
-  }
-
-  @SuppressLint("ClickableViewAccessibility")
-  @Override
-  public boolean onTouchEvent(MotionEvent event) {
-    if(!scrollable) {
-      return true;
-    }
-    return super.onTouchEvent(event);
-  }
-
-  @Override
-  public boolean dispatchTouchEvent(MotionEvent event) {
-    hasTouch = true;
-    boolean result = super.dispatchTouchEvent(event);
-    if (mGesture != null) {
-      result |= mGesture.onTouch(this, event);
-    }
-    return result;
-  }
-
-  public void scrollTo(boolean smooth, int position, final  int offset, final int orientation){
-    if (!smooth) {
-      RecyclerView.LayoutManager layoutManager = getLayoutManager();
-      if (layoutManager instanceof LinearLayoutManager) {
-        //GridLayoutManager is also instance of LinearLayoutManager
-        ((LinearLayoutManager) layoutManager).scrollToPositionWithOffset(position, -offset);
-      } else if (layoutManager instanceof StaggeredGridLayoutManager) {
-        ((StaggeredGridLayoutManager) layoutManager).scrollToPositionWithOffset(position, -offset);
-      }
-      //Any else?
-    } else {
-      smoothScrollToPosition(position);
-      if (offset != 0) {
-        setOnSmoothScrollEndListener(new ExtendedLinearLayoutManager.OnSmoothScrollEndListener() {
-          @Override
-          public void onStop() {
-            post(WXThread.secure(new Runnable() {
-              @Override
-              public void run() {
-                if (orientation == Constants.Orientation.VERTICAL) {
-                  smoothScrollBy(0, offset);
-                } else {
-                  smoothScrollBy(offset, 0);
-                }
-              }
-            }));
-          }
-        });
-      }
-    }
-  }
-
-  public void setOnSmoothScrollEndListener(final ExtendedLinearLayoutManager.OnSmoothScrollEndListener onSmoothScrollEndListener){
-    addOnScrollListener(new RecyclerView.OnScrollListener() {
-      @Override
-      public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
-        if (newState == RecyclerView.SCROLL_STATE_IDLE) {
-          recyclerView.removeOnScrollListener(this);
-          if(onSmoothScrollEndListener != null){
-            onSmoothScrollEndListener.onStop();
-          }
-        }
-      }
-    });
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/IOnLoadMoreListener.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/IOnLoadMoreListener.java
deleted file mode 100644
index e703149..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/IOnLoadMoreListener.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview.adapter;
-
-
-public interface IOnLoadMoreListener {
-
-  void onLoadMore(int offScreenY);
-  void notifyAppearStateChange(int firstVisible, int lastVisible, int directionX, int directionY);
-  void onBeforeScroll(int dx, int dy);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/IRecyclerAdapterListener.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/IRecyclerAdapterListener.java
deleted file mode 100644
index 36094f2..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/IRecyclerAdapterListener.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview.adapter;
-
-import android.support.v7.widget.RecyclerView;
-import android.view.ViewGroup;
-
-/**
- * Listener for recyclerView event
- */
-public interface IRecyclerAdapterListener<T extends RecyclerView.ViewHolder> {
-
-  void onViewRecycled(T holder);
-
-  void onBindViewHolder(T holder, int position);
-
-  T onCreateViewHolder(ViewGroup parent, int viewType);
-
-  int getItemViewType(int position);
-
-  int getItemCount();
-
-  boolean onFailedToRecycleView(T holder);
-
-  long getItemId(int position);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/ListBaseViewHolder.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/ListBaseViewHolder.java
deleted file mode 100644
index 3c332da..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/ListBaseViewHolder.java
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview.adapter;
-
-import android.support.v7.widget.RecyclerView;
-import android.view.View;
-
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXHeader;
-
-import java.lang.ref.WeakReference;
-
-
-/**
- * There are bi-directional association between ViewHolder and View.
- * This is accomplished by weak-reference and final field from ViewHolder to View.
- * From View to ViewHolder, this is done by set {@link android.view.ViewGroup.LayoutParams} to View.
- */
-public class ListBaseViewHolder extends RecyclerView.ViewHolder {
-  private int mViewType;
-  private boolean isRecycled;
-  private WeakReference<WXComponent> mComponent;
-
-  public ListBaseViewHolder(WXComponent component, int viewType) {
-    super(component.getHostView());
-    mViewType = viewType;
-    mComponent = new WeakReference(component);
-    // This tag is used to determine whether bind / rebind data is needed.
-    // It should be false When component can not be recycled Which means
-    // no need to bind / rebind data.
-    isRecycled = component.canRecycled();
-  }
-
-  public ListBaseViewHolder(WXComponent component, int viewType, boolean forceBindData) {
-    this(component, viewType);
-    isRecycled = isRecycled || forceBindData;
-  }
-
-  public ListBaseViewHolder(View view, int viewType) {
-    super(view);
-    mViewType = viewType;
-  }
-
-  public boolean isRecycled() {
-    return isRecycled;
-  }
-
-  public void recycled() {
-    if (mComponent != null && mComponent.get() != null) {
-      mComponent.get().recycled();
-      isRecycled = true;
-
-    }
-  }
-
-  public void bindData(WXComponent component) {
-    if (mComponent != null && mComponent.get() != null) {
-      mComponent.get().bindData(component);
-      isRecycled = false;
-    }
-  }
-    
-  public boolean isFullSpan() {
-    return mComponent != null && mComponent.get() instanceof WXHeader;
-  }
-
-  public boolean canRecycled() {
-    if (mComponent != null && mComponent.get() != null) {
-      return mComponent.get().canRecycled();
-    }
-    return true;
-  }
-
-  public View getView() {
-    return itemView;
-  }
-
-  public int getViewType() {
-    return mViewType;
-  }
-
-  public void setComponentUsing(boolean using) {
-    if (mComponent != null && mComponent.get() != null)
-      mComponent.get().setUsing(using);
-  }
-
-  public WXComponent getComponent() {
-    return mComponent != null ? mComponent.get() : null;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/RecyclerViewBaseAdapter.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/RecyclerViewBaseAdapter.java
deleted file mode 100644
index b7ba22d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/RecyclerViewBaseAdapter.java
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview.adapter;
-
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-import android.view.ViewGroup;
-
-
-/**
- * Adapter for recyclerView
- */
-public class RecyclerViewBaseAdapter<T extends ListBaseViewHolder> extends RecyclerView.Adapter<T> {
-
-  private IRecyclerAdapterListener iRecyclerAdapterListener;
-
-  public RecyclerViewBaseAdapter(IRecyclerAdapterListener Listener) {
-    this.iRecyclerAdapterListener = Listener;
-  }
-
-  @Override
-  public T onCreateViewHolder(ViewGroup parent, int viewType) {
-    if (iRecyclerAdapterListener != null) {
-      return (T) iRecyclerAdapterListener.onCreateViewHolder(parent, viewType);
-    }
-
-    return null;
-  }
-
-  @Override
-  public void onViewAttachedToWindow(T holder) {
-    super.onViewAttachedToWindow(holder);
-    if( holder !=null && holder.isFullSpan()){
-      ViewGroup.LayoutParams lp = holder.itemView.getLayoutParams();
-      if(lp != null
-              && lp instanceof StaggeredGridLayoutManager.LayoutParams
-              ) {
-        StaggeredGridLayoutManager.LayoutParams p = (StaggeredGridLayoutManager.LayoutParams) lp;
-        p.setFullSpan(true);
-      }
-    }
-  }
-
-  @Override
-  public void onViewDetachedFromWindow(T holder) {
-    super.onViewDetachedFromWindow(holder);
-    if (holder != null)
-      holder.setComponentUsing(false);
-  }
-
-  @Override
-  public void onBindViewHolder(T viewHolder, int i) {
-    if (iRecyclerAdapterListener != null) {
-      iRecyclerAdapterListener.onBindViewHolder(viewHolder, i);
-    }
-  }
-
-  @Override
-  public int getItemViewType(int position) {
-    if (iRecyclerAdapterListener != null) {
-      return iRecyclerAdapterListener.getItemViewType(position);
-    }
-    return position;
-  }
-
-  @Override
-  public long getItemId(int position) {
-    return iRecyclerAdapterListener.getItemId(position);
-  }
-
-  @Override
-  public int getItemCount() {
-    if (iRecyclerAdapterListener != null) {
-      return iRecyclerAdapterListener.getItemCount();
-    }
-    return 0;
-  }
-
-  @Override
-  public void onViewRecycled(T holder) {
-    if (iRecyclerAdapterListener != null) {
-      iRecyclerAdapterListener.onViewRecycled(holder);
-    }
-    super.onViewRecycled(holder);
-  }
-
-  @Override
-  public boolean onFailedToRecycleView(T holder) {
-    if (iRecyclerAdapterListener != null) {
-      return iRecyclerAdapterListener.onFailedToRecycleView(holder);
-    }
-    return super.onFailedToRecycleView(holder);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/TransformItemDecoration.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/TransformItemDecoration.java
deleted file mode 100644
index 415c7d5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/TransformItemDecoration.java
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview.adapter;
-
-import android.graphics.Canvas;
-import android.support.v7.widget.RecyclerView;
-import android.view.View;
-
-public class TransformItemDecoration extends RecyclerView.ItemDecoration{
-  boolean mIsVertical = true;
-  float mAlpha = -1f;
-  int mXTranslate = 0;
-  int mYTranslate = 0;
-  int mRotation = 0;
-  float mScaleX = 0;
-  float mScaleY  = 0;
-
-  public TransformItemDecoration(boolean isVertical,float alpha,int translateX,int translateY,int rotation,float scaleX,float scaleY){
-    this.mIsVertical = isVertical;
-    this.mAlpha = alpha;
-    this.mXTranslate = translateX;
-    this.mYTranslate = translateY;
-    this.mRotation = rotation;
-    this.mScaleX = scaleX;
-    this.mScaleY = scaleY;
-  }
-
-
-  @Override
-  public void onDrawOver(Canvas c, RecyclerView parent, RecyclerView.State state) {
-    super.onDrawOver(c, parent, state);
-    int width = parent.getWidth();
-    int height = parent.getHeight();
-    for (int i = 0,count=parent.getChildCount(); i < count; i++) {
-      updateItem(parent.getChildAt(i),width,height);
-    }
-  }
-
-  private void updateItem(View child, int width, int height) {
-    int size,childCenter,containerSize;
-    if (mIsVertical) {
-      containerSize = height;
-      size = child.getHeight();
-      childCenter = child.getTop() + size / 2;
-    } else {
-      containerSize = width;
-      size = child.getWidth();
-      childCenter = child.getLeft() + size / 2;
-    }
-
-    final int actionDistance = (containerSize + size) / 2;
-    final float effectsAmount = Math.min(1.0f, Math.max(-1.0f, (1.0f / actionDistance) * (childCenter - containerSize/2)));
-
-
-    if(mAlpha>0){
-      child.setAlpha(1-mAlpha*Math.abs(effectsAmount));
-    }
-
-    if(mScaleX>0||mScaleY>0){
-      child.setScaleX(1-mScaleX*Math.abs(effectsAmount));
-      child.setScaleY(1-mScaleY*Math.abs(effectsAmount));
-    }
-
-    if(mRotation!=0){
-      child.setRotation(mRotation * effectsAmount);
-    }
-
-    if(mXTranslate!=0){
-      child.setTranslationX(mXTranslate * Math.abs( effectsAmount));
-    }
-
-    if(mYTranslate!=0){
-      child.setTranslationY(mYTranslate * Math.abs( effectsAmount));
-    }
-
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/WXRecyclerViewOnScrollListener.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/WXRecyclerViewOnScrollListener.java
deleted file mode 100644
index 694c8b5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/listview/adapter/WXRecyclerViewOnScrollListener.java
+++ /dev/null
@@ -1,180 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.listview.adapter;
-
-import android.support.v7.widget.GridLayoutManager;
-import android.support.v7.widget.LinearLayoutManager;
-import android.support.v7.widget.RecyclerView;
-import android.support.v7.widget.StaggeredGridLayoutManager;
-
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.lang.ref.WeakReference;
-
-
-/**
- * Listener for scroll event of recyclerView
- */
-public class WXRecyclerViewOnScrollListener extends RecyclerView.OnScrollListener {
-
-  /**
-   * type of layoutManager
-   */
-  protected LAYOUT_MANAGER_TYPE layoutManagerType;
-
-  /**
-   * The last position
-   */
-  private int[] mLastPositions;
-  /**
-   * The first position
-   */
-  private int[] mFirstPositions;
-
-
-  /**
-   * The location of last visible item
-   */
-  private int mLastVisibleItemPosition;
-
-  /**
-   * The location of last visible item
-   */
-  private int mFirstVisibleItemPosition;
-
-  /**
-   * The state of scroll status
-   */
-  private int mCurrentScrollState = 0;
-
-  private WeakReference<IOnLoadMoreListener> listener;
-
-  public WXRecyclerViewOnScrollListener(IOnLoadMoreListener listener) {
-    this.listener = new WeakReference<>(listener);
-  }
-
-  @Override
-  public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
-    super.onScrollStateChanged(recyclerView, newState);
-    mCurrentScrollState = newState;
-    RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
-    int visibleItemCount = layoutManager.getChildCount();
-    int totalItemCount = layoutManager.getItemCount();
-
-    if (visibleItemCount != 0) {
-      int bottomOffset = (totalItemCount - mLastVisibleItemPosition - 1) * (recyclerView.getHeight()) / visibleItemCount;
-      if (visibleItemCount > 0 && mCurrentScrollState == RecyclerView.SCROLL_STATE_IDLE) {
-        if (listener != null && listener.get() != null) {
-          listener.get().onLoadMore(bottomOffset);
-        }
-      }
-    }
-  }
-
-  @Override
-  public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
-    super.onScrolled(recyclerView, dx, dy);
-    RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
-    if(listener == null){
-      return;
-    }
-    IOnLoadMoreListener iOnLoadMoreListener = listener.get();
-
-    if(iOnLoadMoreListener!=null) {
-
-      iOnLoadMoreListener.onBeforeScroll(dx, dy);
-
-      if (layoutManager instanceof LinearLayoutManager) {
-        layoutManagerType = LAYOUT_MANAGER_TYPE.LINEAR;
-        LinearLayoutManager linearLayoutManager = (LinearLayoutManager) layoutManager;
-        mLastVisibleItemPosition = linearLayoutManager.findLastVisibleItemPosition();
-        int firstVisible = linearLayoutManager.findFirstVisibleItemPosition();
-        iOnLoadMoreListener.notifyAppearStateChange(firstVisible
-            , mLastVisibleItemPosition
-            , dx
-            , dy);
-      } else if (layoutManager instanceof GridLayoutManager) {
-        layoutManagerType = LAYOUT_MANAGER_TYPE.GRID;
-        GridLayoutManager gridLayoutManager = (GridLayoutManager) layoutManager;
-        mLastVisibleItemPosition = gridLayoutManager.findLastVisibleItemPosition();
-        iOnLoadMoreListener.notifyAppearStateChange(gridLayoutManager.findFirstVisibleItemPosition()
-            , mLastVisibleItemPosition
-            , dx
-            , dy);
-
-      } else if (layoutManager instanceof StaggeredGridLayoutManager) {
-        layoutManagerType = LAYOUT_MANAGER_TYPE.STAGGERED_GRID;
-        StaggeredGridLayoutManager staggeredGridLayoutManager = (StaggeredGridLayoutManager) layoutManager;
-        int newSpanCount = staggeredGridLayoutManager.getSpanCount();
-        if (mLastPositions == null || newSpanCount != mLastPositions.length) {
-          mLastPositions = new int[newSpanCount];
-        }
-        if (mFirstPositions == null || newSpanCount != mFirstPositions.length) {
-          mFirstPositions = new int[newSpanCount];
-        }
-        //avoid crash of support-v7 original bug
-        try{
-          staggeredGridLayoutManager.findFirstVisibleItemPositions(mFirstPositions);
-          mFirstVisibleItemPosition = findMin(mFirstPositions);
-          staggeredGridLayoutManager.findLastVisibleItemPositions(mLastPositions);
-          mLastVisibleItemPosition = findMax(mLastPositions);
-          iOnLoadMoreListener.notifyAppearStateChange(
-              mFirstVisibleItemPosition
-              , mLastVisibleItemPosition
-              , dx
-              , dy);
-
-        }catch(Exception e){
-          e.printStackTrace();
-          WXLogUtils.e(e.toString());
-        }
-
-      } else {
-        throw new RuntimeException(
-            "Unsupported LayoutManager used. Valid ones are LinearLayoutManager, GridLayoutManager and StaggeredGridLayoutManager");
-      }
-    }
-  }
-
-  private int findMax(int[] lastPositions) {
-    int max = lastPositions[0];
-    for (int value : lastPositions) {
-      if (value > max) {
-        max = value;
-      }
-    }
-    return max;
-  }
-
-  private int findMin(int[] firstPositions) {
-    int min = firstPositions[0];
-    for (int value : firstPositions) {
-      if (value < min) {
-        min = value;
-      }
-    }
-    return min;
-  }
-
-  public enum LAYOUT_MANAGER_TYPE {
-    LINEAR,
-    GRID,
-    STAGGERED_GRID
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/circlebar/CircleProgressBar.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/circlebar/CircleProgressBar.java
deleted file mode 100644
index 7780624..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/circlebar/CircleProgressBar.java
+++ /dev/null
@@ -1,329 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.refresh.circlebar;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.RadialGradient;
-import android.graphics.Shader;
-import android.graphics.drawable.ShapeDrawable;
-import android.graphics.drawable.shapes.OvalShape;
-import android.support.v4.view.ViewCompat;
-import android.util.AttributeSet;
-import android.view.animation.Animation;
-import android.widget.ImageView;
-
-/**
- * Modify of android.support.v4
- */
-@SuppressLint("AppCompatCustomView")
-public class CircleProgressBar extends ImageView {
-
-  private static final int KEY_SHADOW_COLOR = 0x1E000000;
-  private static final int FILL_SHADOW_COLOR = 0x3D000000;
-  private static final float X_OFFSET = 0f;
-  private static final float Y_OFFSET = 1.75f;
-  private static final float SHADOW_RADIUS = 3.5f;
-  private static final int SHADOW_ELEVATION = 4;
-
-  public static final int DEFAULT_CIRCLE_BG_LIGHT = 0xFFFAFAFA;
-  public static final int DEFAULT_CIRCLE_COLOR = 0xFFF00000;
-  private static final int DEFAULT_CIRCLE_DIAMETER = 40;
-  private static final int STROKE_WIDTH_LARGE = 3;
-
-  private Animation.AnimationListener mListener;
-  private int mShadowRadius;
-  private int mBackGroundColor;
-  private int mProgressColor;
-  private int mProgressStokeWidth;
-  private int mArrowWidth;
-  private int mArrowHeight;
-  private int mProgress;
-  private int mMax;
-  private int mDiameter;
-  private int mInnerRadius;
-  private boolean mShowArrow;
-  public MaterialProgressDrawable mProgressDrawable;
-  private ShapeDrawable mBgCircle;
-  private boolean mCircleBackgroundEnabled;
-  private int[] mColors = new int[]{Color.BLACK};
-
-  public CircleProgressBar(Context context) {
-    super(context);
-    init(context, null, 0);
-
-  }
-
-  public CircleProgressBar(Context context, AttributeSet attrs) {
-    super(context, attrs);
-    init(context, attrs, 0);
-
-  }
-
-  public CircleProgressBar(Context context, AttributeSet attrs, int defStyleAttr) {
-    super(context, attrs, defStyleAttr);
-    init(context, attrs, defStyleAttr);
-  }
-
-  private void init(Context context, AttributeSet attrs, int defStyleAttr) {
-
-    final float density = getContext().getResources().getDisplayMetrics().density;
-    mBackGroundColor = DEFAULT_CIRCLE_BG_LIGHT;
-    mProgressColor = DEFAULT_CIRCLE_COLOR;
-    mColors = new int[]{mProgressColor};
-    mInnerRadius = -1;
-    mProgressStokeWidth = (int) (STROKE_WIDTH_LARGE * density);
-    mArrowWidth =  -1;
-    mArrowHeight = -1;
-    mShowArrow = true;
-    mCircleBackgroundEnabled = true;
-    mProgress = 0;
-    mMax = 100;
-    mProgressDrawable = new MaterialProgressDrawable(getContext(), this);
-    super.setImageDrawable(mProgressDrawable);
-  }
-
-  public void setProgressBackGroundColor(int color) {
-    this.mBackGroundColor = color;
-  }
-
-  private boolean elevationSupported() {
-    return android.os.Build.VERSION.SDK_INT >= 21;
-  }
-
-  @Override
-  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
-    super.onMeasure(widthMeasureSpec, heightMeasureSpec);
-    if (!elevationSupported()) {
-      setMeasuredDimension(getMeasuredWidth() + mShadowRadius * 2, getMeasuredHeight()
-                                                                   + mShadowRadius * 2);
-    }
-  }
-
-  public int getProgressStokeWidth() {
-    return mProgressStokeWidth;
-  }
-
-  public void setProgressStokeWidth(int mProgressStokeWidth) {
-    final float density = getContext().getResources().getDisplayMetrics().density;
-    this.mProgressStokeWidth = (int) (mProgressStokeWidth * density);
-  }
-
-  @Override
-  protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
-    super.onLayout(changed, left, top, right, bottom);
-    final float density = getContext().getResources().getDisplayMetrics().density;
-    mDiameter = Math.min(getMeasuredWidth(), getMeasuredHeight());
-    if (mDiameter <= 0) {
-      mDiameter = (int) density * DEFAULT_CIRCLE_DIAMETER;
-    }
-    if (getBackground() == null && mCircleBackgroundEnabled) {
-      final int shadowYOffset = (int) (density * Y_OFFSET);
-      final int shadowXOffset = (int) (density * X_OFFSET);
-      mShadowRadius = (int) (density * SHADOW_RADIUS);
-
-      if (elevationSupported()) {
-        if(mBgCircle == null) {
-          mBgCircle = new ShapeDrawable(new OvalShape());
-        }
-        ViewCompat.setElevation(this, SHADOW_ELEVATION * density);
-      } else {
-        if(!(mBgCircle != null &&
-            mBgCircle.getShape() instanceof  OvalShadow &&
-            ((OvalShadow) mBgCircle.getShape()).mCircleDiameter == (mDiameter - mShadowRadius * 2) &&
-            ((OvalShadow) mBgCircle.getShape()).mShadowRadius == mShadowRadius)) {
-          OvalShape oval = new OvalShadow(mShadowRadius, mDiameter - mShadowRadius * 2);
-          mBgCircle = new ShapeDrawable(oval);
-        }
-        ViewCompat.setLayerType(this, ViewCompat.LAYER_TYPE_SOFTWARE, mBgCircle.getPaint());
-        mBgCircle.getPaint().setShadowLayer(mShadowRadius, shadowXOffset, shadowYOffset,
-                                            KEY_SHADOW_COLOR);
-        final int padding = (int) mShadowRadius;
-        // set padding so the inner image sits correctly within the shadow.
-        setPadding(padding, padding, padding, padding);
-      }
-      mBgCircle.getPaint().setColor(mBackGroundColor);
-      setBackgroundDrawable(mBgCircle);
-    }
-    mProgressDrawable.setBackgroundColor(mBackGroundColor);
-    mProgressDrawable.setColorSchemeColors(mColors);
-    if (isShowArrow()) {
-      mProgressDrawable.setArrowScale(1f);
-      mProgressDrawable.showArrow(true);
-    }
-    super.setImageDrawable(null);
-    super.setImageDrawable(mProgressDrawable);
-    mProgressDrawable.setAlpha(255);
-    if (getVisibility() == VISIBLE) {
-      mProgressDrawable.setStartEndTrim(0, (float) 0.8);
-    }
-  }
-
-  public boolean isShowArrow() {
-    return mShowArrow;
-  }
-
-  public void setShowArrow(boolean showArrow) {
-    this.mShowArrow = showArrow;
-  }
-
-  public void setAnimationListener(Animation.AnimationListener listener) {
-    mListener = listener;
-  }
-
-  @Override
-  public void onAnimationStart() {
-    super.onAnimationStart();
-    if (mListener != null) {
-      mListener.onAnimationStart(getAnimation());
-    }
-  }
-
-  @Override
-  public void onAnimationEnd() {
-    super.onAnimationEnd();
-    if (mListener != null) {
-      mListener.onAnimationEnd(getAnimation());
-    }
-  }
-
-  /**
-   * Set the colors used in the progress animation. The first
-   * color will also be the color of the bar that grows in response to a user
-   * swipe gesture.
-   *
-   * @param colors
-   */
-  public void setColorSchemeColors(int... colors) {
-    mColors = colors;
-    if (mProgressDrawable != null) {
-      mProgressDrawable.setColorSchemeColors(colors);
-    }
-  }
-
-  /**
-   * Update the background color of the mBgCircle image view.
-   */
-  public void setBackgroundColorResource(int colorRes) {
-    if (getBackground() instanceof ShapeDrawable) {
-      final Resources res = getResources();
-      ((ShapeDrawable) getBackground()).getPaint().setColor(res.getColor(colorRes));
-    }
-  }
-
-  public void setBackgroundColor(int color) {
-    if (getBackground() instanceof ShapeDrawable) {
-      ((ShapeDrawable) getBackground()).getPaint().setColor(color);
-    }
-  }
-
-  public int getMax() {
-    return mMax;
-  }
-
-  public void setMax(int max) {
-    mMax = max;
-  }
-
-  public int getProgress() {
-    return mProgress;
-  }
-
-  public void setProgress(int progress) {
-    if (getMax() > 0) {
-      mProgress = progress;
-    }
-    invalidate();
-  }
-
-  public boolean circleBackgroundEnabled() {
-    return mCircleBackgroundEnabled;
-  }
-
-  public void setCircleBackgroundEnabled(boolean enableCircleBackground) {
-    this.mCircleBackgroundEnabled = enableCircleBackground;
-  }
-
-  @Override
-  protected void onAttachedToWindow() {
-    super.onAttachedToWindow();
-    if (mProgressDrawable != null) {
-      mProgressDrawable.stop();
-      mProgressDrawable.setVisible(getVisibility() == VISIBLE, false);
-    }
-  }
-
-  @Override
-  protected void onDetachedFromWindow() {
-    super.onDetachedFromWindow();
-    if (mProgressDrawable != null) {
-      mProgressDrawable.stop();
-      mProgressDrawable.setVisible(false, false);
-    }
-  }
-
-  private class OvalShadow extends OvalShape {
-
-    private RadialGradient mRadialGradient;
-    private int mShadowRadius;
-    private Paint mShadowPaint;
-    private int mCircleDiameter;
-
-    public OvalShadow(int shadowRadius, int circleDiameter) {
-      super();
-      mShadowPaint = new Paint();
-      mShadowRadius = shadowRadius;
-      mCircleDiameter = circleDiameter;
-      mRadialGradient = new RadialGradient(mCircleDiameter / 2, mCircleDiameter / 2,
-                                           mShadowRadius, new int[]{
-          FILL_SHADOW_COLOR, Color.TRANSPARENT
-      }, null, Shader.TileMode.CLAMP);
-      mShadowPaint.setShader(mRadialGradient);
-    }
-
-    @Override
-    public void draw(Canvas canvas, Paint paint) {
-      final int viewWidth = CircleProgressBar.this.getWidth();
-      final int viewHeight = CircleProgressBar.this.getHeight();
-      canvas.drawCircle(viewWidth / 2, viewHeight / 2, (mCircleDiameter / 2 + mShadowRadius),
-                        mShadowPaint);
-      canvas.drawCircle(viewWidth / 2, viewHeight / 2, (mCircleDiameter / 2), paint);
-    }
-  }
-
-  public void start() {
-    mProgressDrawable.start();
-  }
-
-  public void setStartEndTrim(float startAngle, float endAngle) {
-    mProgressDrawable.setStartEndTrim(startAngle, endAngle);
-  }
-
-  public void stop() {
-    mProgressDrawable.stop();
-  }
-
-  public void setProgressRotation(float rotation) {
-    mProgressDrawable.setProgressRotation(rotation);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/circlebar/MaterialProgressDrawable.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/circlebar/MaterialProgressDrawable.java
deleted file mode 100644
index 476e6c1..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/circlebar/MaterialProgressDrawable.java
+++ /dev/null
@@ -1,797 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.refresh.circlebar;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.ColorFilter;
-import android.graphics.Paint;
-import android.graphics.Paint.Style;
-import android.graphics.Path;
-import android.graphics.PixelFormat;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.graphics.drawable.Animatable;
-import android.graphics.drawable.Drawable;
-import android.support.annotation.IntDef;
-import android.support.annotation.NonNull;
-import android.support.v4.view.animation.FastOutSlowInInterpolator;
-import android.util.DisplayMetrics;
-import android.view.View;
-import android.view.animation.Animation;
-import android.view.animation.Interpolator;
-import android.view.animation.LinearInterpolator;
-import android.view.animation.Transformation;
-
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.util.ArrayList;
-
-/**
- * Copy of android.support.v4
- */
-class MaterialProgressDrawable extends Drawable implements Animatable {
-
-  private static final Interpolator LINEAR_INTERPOLATOR = new LinearInterpolator();
-  private static final Interpolator MATERIAL_INTERPOLATOR = new FastOutSlowInInterpolator();
-
-  private static final float FULL_ROTATION = 1080.0f;
-
-  @Retention(RetentionPolicy.CLASS)
-  @IntDef({LARGE, DEFAULT})
-  public @interface ProgressDrawableSize {
-
-  }
-
-  // Maps to ProgressBar.Large style
-  static final int LARGE = 0;
-  // Maps to ProgressBar default style
-  static final int DEFAULT = 1;
-
-  // Maps to ProgressBar default style
-  private static final int CIRCLE_DIAMETER = 40;
-  private static final float CENTER_RADIUS = 8.75f; //should add up to 10 when + stroke_width
-  private static final float STROKE_WIDTH = 2.5f;
-
-  // Maps to ProgressBar.Large style
-  private static final int CIRCLE_DIAMETER_LARGE = 56;
-  private static final float CENTER_RADIUS_LARGE = 12.5f;
-  private static final float STROKE_WIDTH_LARGE = 3f;
-
-  private final int[] COLORS = new int[]{
-      Color.BLACK
-  };
-
-  /**
-   * The value in the linear interpolator for animating the drawable at which
-   * the color transition should start
-   */
-  private static final float COLOR_START_DELAY_OFFSET = 0.75f;
-  private static final float END_TRIM_START_DELAY_OFFSET = 0.5f;
-  private static final float START_TRIM_DURATION_OFFSET = 0.5f;
-
-  /** The duration of a single progress spin in milliseconds. */
-  private static final int ANIMATION_DURATION = 1332;
-
-  /** The number of points in the progress "star". */
-  private static final float NUM_POINTS = 5f;
-  /** The list of animators operating on this drawable. */
-  private final ArrayList<Animation> mAnimators = new ArrayList<Animation>();
-
-  /** The indicator ring, used to manage animation state. */
-  private final Ring mRing;
-
-  /** Canvas rotation in degrees. */
-  private float mRotation;
-
-  /** Layout info for the arrowhead in dp */
-  private static final int ARROW_WIDTH = 10;
-  private static final int ARROW_HEIGHT = 5;
-  private static final float ARROW_OFFSET_ANGLE = 5;
-
-  /** Layout info for the arrowhead for the large spinner in dp */
-  private static final int ARROW_WIDTH_LARGE = 12;
-  private static final int ARROW_HEIGHT_LARGE = 6;
-  private static final float MAX_PROGRESS_ARC = .8f;
-
-  private Resources mResources;
-  private View mParent;
-  private Animation mAnimation;
-  private float mRotationCount;
-  private double mWidth;
-  private double mHeight;
-  boolean mFinishing;
-
-  public MaterialProgressDrawable(Context context, View parent) {
-    mParent = parent;
-    mResources = context.getResources();
-
-    mRing = new Ring(mCallback);
-    mRing.setColors(COLORS);
-
-    updateSizes(DEFAULT);
-    setupAnimators();
-  }
-
-  private void setSizeParameters(double progressCircleWidth, double progressCircleHeight,
-                                 double centerRadius, double strokeWidth, float arrowWidth, float arrowHeight) {
-    final Ring ring = mRing;
-    final DisplayMetrics metrics = mResources.getDisplayMetrics();
-    final float screenDensity = metrics.density;
-
-    mWidth = progressCircleWidth * screenDensity;
-    mHeight = progressCircleHeight * screenDensity;
-    ring.setStrokeWidth((float) strokeWidth * screenDensity);
-    ring.setCenterRadius(centerRadius * screenDensity);
-    ring.setColorIndex(0);
-    ring.setArrowDimensions(arrowWidth * screenDensity, arrowHeight * screenDensity);
-    ring.setInsets((int) mWidth, (int) mHeight);
-  }
-
-  /**
-   * Set the overall size for the progress spinner. This updates the radius
-   * and stroke width of the ring.
-   *
-   * @param size One of {@link MaterialProgressDrawable.LARGE} or
-   *            {@link MaterialProgressDrawable.DEFAULT}
-   */
-  public void updateSizes(@ProgressDrawableSize int size) {
-    if (size == LARGE) {
-      setSizeParameters(CIRCLE_DIAMETER_LARGE, CIRCLE_DIAMETER_LARGE, CENTER_RADIUS_LARGE,
-                        STROKE_WIDTH_LARGE, ARROW_WIDTH_LARGE, ARROW_HEIGHT_LARGE);
-    } else {
-      setSizeParameters(CIRCLE_DIAMETER, CIRCLE_DIAMETER, CENTER_RADIUS, STROKE_WIDTH,
-                        ARROW_WIDTH, ARROW_HEIGHT);
-    }
-  }
-
-  /**
-   * @param show Set to true to display the arrowhead on the progress spinner.
-   */
-  public void showArrow(boolean show) {
-    mRing.setShowArrow(show);
-  }
-
-  /**
-   * @param scale Set the scale of the arrowhead for the spinner.
-   */
-  public void setArrowScale(float scale) {
-    mRing.setArrowScale(scale);
-  }
-
-  /**
-   * Set the start and end trim for the progress spinner arc.
-   *
-   * @param startAngle start angle
-   * @param endAngle end angle
-   */
-  public void setStartEndTrim(float startAngle, float endAngle) {
-    mRing.setStartTrim(startAngle);
-    mRing.setEndTrim(endAngle);
-  }
-
-  /**
-   * Set the amount of rotation to apply to the progress spinner.
-   *
-   * @param rotation Rotation is from [0..1]
-   */
-  public void setProgressRotation(float rotation) {
-    mRing.setRotation(rotation);
-  }
-
-  /**
-   * Update the background color of the circle image view.
-   */
-  public void setBackgroundColor(int color) {
-    mRing.setBackgroundColor(color);
-  }
-
-  /**
-   * Set the colors used in the progress animation from color resources.
-   * The first color will also be the color of the bar that grows in response
-   * to a user swipe gesture.
-   *
-   * @param colors
-   */
-  public void setColorSchemeColors(int... colors) {
-    mRing.setColors(colors);
-    mRing.setColorIndex(0);
-  }
-
-  @Override
-  public int getIntrinsicHeight() {
-    return (int) mHeight;
-  }
-
-  @Override
-  public int getIntrinsicWidth() {
-    return (int) mWidth;
-  }
-
-  @Override
-  public void draw(Canvas c) {
-    final Rect bounds = getBounds();
-    final int saveCount = c.save();
-    c.rotate(mRotation, bounds.exactCenterX(), bounds.exactCenterY());
-    mRing.draw(c, bounds);
-    c.restoreToCount(saveCount);
-  }
-
-  @Override
-  public void setAlpha(int alpha) {
-    mRing.setAlpha(alpha);
-  }
-
-  public int getAlpha() {
-    return mRing.getAlpha();
-  }
-
-  @Override
-  public void setColorFilter(ColorFilter colorFilter) {
-    mRing.setColorFilter(colorFilter);
-  }
-
-  @SuppressWarnings("unused")
-  void setRotation(float rotation) {
-    mRotation = rotation;
-    invalidateSelf();
-  }
-
-  @SuppressWarnings("unused")
-  private float getRotation() {
-    return mRotation;
-  }
-
-  @Override
-  public int getOpacity() {
-    return PixelFormat.TRANSLUCENT;
-  }
-
-  @Override
-  public boolean isRunning() {
-    final ArrayList<Animation> animators = mAnimators;
-    final int N = animators.size();
-    for (int i = 0; i < N; i++) {
-      final Animation animator = animators.get(i);
-      if (animator.hasStarted() && !animator.hasEnded()) {
-        return true;
-      }
-    }
-    return false;
-  }
-
-  @Override
-  public void start() {
-    mAnimation.reset();
-    mRing.storeOriginals();
-    // Already showing some part of the ring
-    if (mRing.getEndTrim() != mRing.getStartTrim()) {
-      mFinishing = true;
-      mAnimation.setDuration(ANIMATION_DURATION / 2);
-      mParent.startAnimation(mAnimation);
-    } else {
-      mRing.setColorIndex(0);
-      mRing.resetOriginals();
-      mAnimation.setDuration(ANIMATION_DURATION);
-      mParent.startAnimation(mAnimation);
-    }
-  }
-
-  @Override
-  public void stop() {
-    mParent.clearAnimation();
-    setRotation(0);
-    mRing.setShowArrow(false);
-    mRing.setColorIndex(0);
-    mRing.resetOriginals();
-  }
-
-  private float getMinProgressArc(Ring ring) {
-    return (float) Math.toRadians(
-        ring.getStrokeWidth() / (2 * Math.PI * ring.getCenterRadius()));
-  }
-
-  // Adapted from ArgbEvaluator.java
-  private int evaluateColorChange(float fraction, int startValue, int endValue) {
-    int startInt = (Integer) startValue;
-    int startA = (startInt >> 24) & 0xff;
-    int startR = (startInt >> 16) & 0xff;
-    int startG = (startInt >> 8) & 0xff;
-    int startB = startInt & 0xff;
-
-    int endInt = (Integer) endValue;
-    int endA = (endInt >> 24) & 0xff;
-    int endR = (endInt >> 16) & 0xff;
-    int endG = (endInt >> 8) & 0xff;
-    int endB = endInt & 0xff;
-
-    return (int) ((startA + (int) (fraction * (endA - startA))) << 24) |
-           (int) ((startR + (int) (fraction * (endR - startR))) << 16) |
-           (int) ((startG + (int) (fraction * (endG - startG))) << 8) |
-           (int) ((startB + (int) (fraction * (endB - startB))));
-  }
-
-  /**
-   * Update the ring color if this is within the last 25% of the animation.
-   * The new ring color will be a translation from the starting ring color to
-   * the next color.
-   */
-  private void updateRingColor(float interpolatedTime, Ring ring) {
-    if (interpolatedTime > COLOR_START_DELAY_OFFSET) {
-      // scale the interpolatedTime so that the full
-      // transformation from 0 - 1 takes place in the
-      // remaining time
-      ring.setColor(evaluateColorChange((interpolatedTime - COLOR_START_DELAY_OFFSET)
-                                        / (1.0f - COLOR_START_DELAY_OFFSET), ring.getStartingColor(),
-                                        ring.getNextColor()));
-    }
-  }
-
-  private void applyFinishTranslation(float interpolatedTime, Ring ring) {
-    // shrink back down and complete a full rotation before
-    // starting other circles
-    // Rotation goes between [0..1].
-    updateRingColor(interpolatedTime, ring);
-    float targetRotation = (float) (Math.floor(ring.getStartingRotation() / MAX_PROGRESS_ARC)
-                                    + 1f);
-    final float minProgressArc = getMinProgressArc(ring);
-    final float startTrim = ring.getStartingStartTrim()
-                            + (ring.getStartingEndTrim() - minProgressArc - ring.getStartingStartTrim())
-                              * interpolatedTime;
-    ring.setStartTrim(startTrim);
-    ring.setEndTrim(ring.getStartingEndTrim());
-    final float rotation = ring.getStartingRotation()
-                           + ((targetRotation - ring.getStartingRotation()) * interpolatedTime);
-    ring.setRotation(rotation);
-  }
-
-  private void setupAnimators() {
-    final Ring ring = mRing;
-    final Animation animation = new Animation() {
-      @Override
-      public void applyTransformation(float interpolatedTime, Transformation t) {
-        if (mFinishing) {
-          applyFinishTranslation(interpolatedTime, ring);
-        } else {
-          // The minProgressArc is calculated from 0 to create an
-          // angle that matches the stroke width.
-          final float minProgressArc = getMinProgressArc(ring);
-          final float startingEndTrim = ring.getStartingEndTrim();
-          final float startingTrim = ring.getStartingStartTrim();
-          final float startingRotation = ring.getStartingRotation();
-
-          updateRingColor(interpolatedTime, ring);
-
-          // Moving the start trim only occurs in the first 50% of a
-          // single ring animation
-          if (interpolatedTime <= START_TRIM_DURATION_OFFSET) {
-            // scale the interpolatedTime so that the full
-            // transformation from 0 - 1 takes place in the
-            // remaining time
-            final float scaledTime = (interpolatedTime)
-                                     / (1.0f - START_TRIM_DURATION_OFFSET);
-            final float startTrim = startingTrim
-                                    + ((MAX_PROGRESS_ARC - minProgressArc) * MATERIAL_INTERPOLATOR
-                .getInterpolation(scaledTime));
-            ring.setStartTrim(startTrim);
-          }
-
-          // Moving the end trim starts after 50% of a single ring
-          // animation completes
-          if (interpolatedTime > END_TRIM_START_DELAY_OFFSET) {
-            // scale the interpolatedTime so that the full
-            // transformation from 0 - 1 takes place in the
-            // remaining time
-            final float minArc = MAX_PROGRESS_ARC - minProgressArc;
-            float scaledTime = (interpolatedTime - START_TRIM_DURATION_OFFSET)
-                               / (1.0f - START_TRIM_DURATION_OFFSET);
-            final float endTrim = startingEndTrim
-                                  + (minArc * MATERIAL_INTERPOLATOR.getInterpolation(scaledTime));
-            ring.setEndTrim(endTrim);
-          }
-
-          final float rotation = startingRotation + (0.25f * interpolatedTime);
-          ring.setRotation(rotation);
-
-          float groupRotation = ((FULL_ROTATION / NUM_POINTS) * interpolatedTime)
-                                + (FULL_ROTATION * (mRotationCount / NUM_POINTS));
-          setRotation(groupRotation);
-        }
-      }
-    };
-    animation.setRepeatCount(Animation.INFINITE);
-    animation.setRepeatMode(Animation.RESTART);
-    animation.setInterpolator(LINEAR_INTERPOLATOR);
-    animation.setAnimationListener(new Animation.AnimationListener() {
-
-      @Override
-      public void onAnimationStart(Animation animation) {
-        mRotationCount = 0;
-      }
-
-      @Override
-      public void onAnimationEnd(Animation animation) {
-        // do nothing
-      }
-
-      @Override
-      public void onAnimationRepeat(Animation animation) {
-        ring.storeOriginals();
-        ring.goToNextColor();
-        ring.setStartTrim(ring.getEndTrim());
-        if (mFinishing) {
-          // finished closing the last ring from the swipe gesture; go
-          // into progress mode
-          mFinishing = false;
-          animation.setDuration(ANIMATION_DURATION);
-          ring.setShowArrow(false);
-        } else {
-          mRotationCount = (mRotationCount + 1) % (NUM_POINTS);
-        }
-      }
-    });
-    mAnimation = animation;
-  }
-
-  private final Callback mCallback = new Callback() {
-    @Override
-    public void invalidateDrawable(Drawable d) {
-      invalidateSelf();
-    }
-
-    @Override
-    public void scheduleDrawable(Drawable d, Runnable what, long when) {
-      scheduleSelf(what, when);
-    }
-
-    @Override
-    public void unscheduleDrawable(Drawable d, Runnable what) {
-      unscheduleSelf(what);
-    }
-  };
-
-  private static class Ring {
-
-    private final RectF mTempBounds = new RectF();
-    private final Paint mPaint = new Paint();
-    private final Paint mArrowPaint = new Paint();
-
-    private final Callback mCallback;
-
-    private float mStartTrim = 0.0f;
-    private float mEndTrim = 0.0f;
-    private float mRotation = 0.0f;
-    private float mStrokeWidth = 5.0f;
-    private float mStrokeInset = 2.5f;
-
-    private int[] mColors;
-    // mColorIndex represents the offset into the available mColors that the
-    // progress circle should currently display. As the progress circle is
-    // animating, the mColorIndex moves by one to the next available color.
-    private int mColorIndex;
-    private float mStartingStartTrim;
-    private float mStartingEndTrim;
-    private float mStartingRotation;
-    private boolean mShowArrow;
-    private Path mArrow;
-    private float mArrowScale;
-    private double mRingCenterRadius;
-    private int mArrowWidth;
-    private int mArrowHeight;
-    private int mAlpha;
-    private final Paint mCirclePaint = new Paint(Paint.ANTI_ALIAS_FLAG);
-    private int mBackgroundColor;
-    private int mCurrentColor;
-
-    public Ring(Callback callback) {
-      mCallback = callback;
-
-      mPaint.setStrokeCap(Paint.Cap.SQUARE);
-      mPaint.setAntiAlias(true);
-      mPaint.setStyle(Style.STROKE);
-
-      mArrowPaint.setStyle(Style.FILL);
-      mArrowPaint.setAntiAlias(true);
-    }
-
-    public void setBackgroundColor(int color) {
-      mBackgroundColor = color;
-    }
-
-    /**
-     * Set the dimensions of the arrowhead.
-     *
-     * @param width Width of the hypotenuse of the arrow head
-     * @param height Height of the arrow point
-     */
-    public void setArrowDimensions(float width, float height) {
-      mArrowWidth = (int) width;
-      mArrowHeight = (int) height;
-    }
-
-    /**
-     * Draw the progress spinner
-     */
-    public void draw(Canvas c, Rect bounds) {
-      final RectF arcBounds = mTempBounds;
-      arcBounds.set(bounds);
-      arcBounds.inset(mStrokeInset, mStrokeInset);
-
-      final float startAngle = (mStartTrim + mRotation) * 360;
-      final float endAngle = (mEndTrim + mRotation) * 360;
-      float sweepAngle = endAngle - startAngle;
-
-      mPaint.setColor(mCurrentColor);
-      c.drawArc(arcBounds, startAngle, sweepAngle, false, mPaint);
-
-      drawTriangle(c, startAngle, sweepAngle, bounds);
-
-      if (mAlpha < 255) {
-        mCirclePaint.setColor(mBackgroundColor);
-        mCirclePaint.setAlpha(255 - mAlpha);
-        c.drawCircle(bounds.exactCenterX(), bounds.exactCenterY(), bounds.width() / 2,
-                     mCirclePaint);
-      }
-    }
-
-    private void drawTriangle(Canvas c, float startAngle, float sweepAngle, Rect bounds) {
-      if (mShowArrow) {
-        if (mArrow == null) {
-          mArrow = new Path();
-          mArrow.setFillType(Path.FillType.EVEN_ODD);
-        } else {
-          mArrow.reset();
-        }
-
-        // Adjust the position of the triangle so that it is inset as
-        // much as the arc, but also centered on the arc.
-        float inset = (int) mStrokeInset / 2 * mArrowScale;
-        float x = (float) (mRingCenterRadius * Math.cos(0) + bounds.exactCenterX());
-        float y = (float) (mRingCenterRadius * Math.sin(0) + bounds.exactCenterY());
-
-        // Update the path each time. This works around an issue in SKIA
-        // where concatenating a rotation matrix to a scale matrix
-        // ignored a starting negative rotation. This appears to have
-        // been fixed as of API 21.
-        mArrow.moveTo(0, 0);
-        mArrow.lineTo(mArrowWidth * mArrowScale, 0);
-        mArrow.lineTo((mArrowWidth * mArrowScale / 2), (mArrowHeight
-                                                        * mArrowScale));
-        mArrow.offset(x - inset, y);
-        mArrow.close();
-        // draw a triangle
-        mArrowPaint.setColor(mCurrentColor);
-        c.rotate(startAngle + sweepAngle - ARROW_OFFSET_ANGLE, bounds.exactCenterX(),
-                 bounds.exactCenterY());
-        c.drawPath(mArrow, mArrowPaint);
-      }
-    }
-
-    /**
-     * Set the colors the progress spinner alternates between.
-     *
-     * @param colors Array of integers describing the colors. Must be non-<code>null</code>.
-     */
-    public void setColors(@NonNull int[] colors) {
-      mColors = colors;
-      // if colors are reset, make sure to reset the color index as well
-      setColorIndex(0);
-    }
-
-    /**
-     * Set the absolute color of the progress spinner. This is should only
-     * be used when animating between current and next color when the
-     * spinner is rotating.
-     *
-     * @param color int describing the color.
-     */
-    public void setColor(int color) {
-      mCurrentColor = color;
-    }
-
-    /**
-     * @param index Index into the color array of the color to display in
-     *            the progress spinner.
-     */
-    public void setColorIndex(int index) {
-      mColorIndex = index;
-      mCurrentColor = mColors[mColorIndex];
-    }
-
-    /**
-     * @return int describing the next color the progress spinner should use when drawing.
-     */
-    public int getNextColor() {
-      return mColors[getNextColorIndex()];
-    }
-
-    private int getNextColorIndex() {
-      return (mColorIndex + 1) % (mColors.length);
-    }
-
-    /**
-     * Proceed to the next available ring color. This will automatically
-     * wrap back to the beginning of colors.
-     */
-    public void goToNextColor() {
-      setColorIndex(getNextColorIndex());
-    }
-
-    public void setColorFilter(ColorFilter filter) {
-      mPaint.setColorFilter(filter);
-      invalidateSelf();
-    }
-
-    /**
-     * @param alpha Set the alpha of the progress spinner and associated arrowhead.
-     */
-    public void setAlpha(int alpha) {
-      mAlpha = alpha;
-    }
-
-    /**
-     * @return Current alpha of the progress spinner and arrowhead.
-     */
-    public int getAlpha() {
-      return mAlpha;
-    }
-
-    /**
-     * @param strokeWidth Set the stroke width of the progress spinner in pixels.
-     */
-    public void setStrokeWidth(float strokeWidth) {
-      mStrokeWidth = strokeWidth;
-      mPaint.setStrokeWidth(strokeWidth);
-      invalidateSelf();
-    }
-
-    @SuppressWarnings("unused")
-    public float getStrokeWidth() {
-      return mStrokeWidth;
-    }
-
-    @SuppressWarnings("unused")
-    public void setStartTrim(float startTrim) {
-      mStartTrim = startTrim;
-      invalidateSelf();
-    }
-
-    @SuppressWarnings("unused")
-    public float getStartTrim() {
-      return mStartTrim;
-    }
-
-    public float getStartingStartTrim() {
-      return mStartingStartTrim;
-    }
-
-    public float getStartingEndTrim() {
-      return mStartingEndTrim;
-    }
-
-    public int getStartingColor() {
-      return mColors[mColorIndex];
-    }
-
-    @SuppressWarnings("unused")
-    public void setEndTrim(float endTrim) {
-      mEndTrim = endTrim;
-      invalidateSelf();
-    }
-
-    @SuppressWarnings("unused")
-    public float getEndTrim() {
-      return mEndTrim;
-    }
-
-    @SuppressWarnings("unused")
-    public void setRotation(float rotation) {
-      mRotation = rotation;
-      invalidateSelf();
-    }
-
-    @SuppressWarnings("unused")
-    public float getRotation() {
-      return mRotation;
-    }
-
-    public void setInsets(int width, int height) {
-      final float minEdge = (float) Math.min(width, height);
-      float insets;
-      if (mRingCenterRadius <= 0 || minEdge < 0) {
-        insets = (float) Math.ceil(mStrokeWidth / 2.0f);
-      } else {
-        insets = (float) (minEdge / 2.0f - mRingCenterRadius);
-      }
-      mStrokeInset = insets;
-    }
-
-    @SuppressWarnings("unused")
-    public float getInsets() {
-      return mStrokeInset;
-    }
-
-    /**
-     * @param centerRadius Inner radius in px of the circle the progress
-     *            spinner arc traces.
-     */
-    public void setCenterRadius(double centerRadius) {
-      mRingCenterRadius = centerRadius;
-    }
-
-    public double getCenterRadius() {
-      return mRingCenterRadius;
-    }
-
-    /**
-     * @param show Set to true to show the arrow head on the progress spinner.
-     */
-    public void setShowArrow(boolean show) {
-      if (mShowArrow != show) {
-        mShowArrow = show;
-        invalidateSelf();
-      }
-    }
-
-    /**
-     * @param scale Set the scale of the arrowhead for the spinner.
-     */
-    public void setArrowScale(float scale) {
-      if (scale != mArrowScale) {
-        mArrowScale = scale;
-        invalidateSelf();
-      }
-    }
-
-    /**
-     * @return The amount the progress spinner is currently rotated, between [0..1].
-     */
-    public float getStartingRotation() {
-      return mStartingRotation;
-    }
-
-    /**
-     * If the start / end trim are offset to begin with, store them so that
-     * animation starts from that offset.
-     */
-    public void storeOriginals() {
-      mStartingStartTrim = mStartTrim;
-      mStartingEndTrim = mEndTrim;
-      mStartingRotation = mRotation;
-    }
-
-    /**
-     * Reset the progress spinner to default rotation, start and end angles.
-     */
-    public void resetOriginals() {
-      mStartingStartTrim = 0;
-      mStartingEndTrim = 0;
-      mStartingRotation = 0;
-      setStartTrim(0);
-      setEndTrim(0);
-      setRotation(0);
-    }
-
-    private void invalidateSelf() {
-      mCallback.invalidateDrawable(null);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/core/WXRefreshView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/core/WXRefreshView.java
deleted file mode 100644
index 7c69be8..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/core/WXRefreshView.java
+++ /dev/null
@@ -1,149 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.refresh.core;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import android.view.Gravity;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-
-import com.taobao.weex.common.WXThread;
-import com.taobao.weex.ui.view.refresh.circlebar.CircleProgressBar;
-
-public class WXRefreshView extends FrameLayout {
-
-  private CircleProgressBar circleProgressBar;
-  private LinearLayout linearLayout;
-
-  public WXRefreshView(Context context) {
-    super(context);
-    setupViews();
-  }
-
-  public WXRefreshView(Context context, AttributeSet attrs) {
-    super(context, attrs);
-    setupViews();
-  }
-
-  public WXRefreshView(Context context, AttributeSet attrs, int defStyleAttr) {
-    super(context, attrs, defStyleAttr);
-    setupViews();
-  }
-
-  private void setupViews() {
-    linearLayout = new LinearLayout(getContext());
-    FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(FrameLayout.LayoutParams
-            .MATCH_PARENT,FrameLayout
-            .LayoutParams.MATCH_PARENT);
-    linearLayout.setOrientation(LinearLayout.VERTICAL);
-    linearLayout.setGravity(Gravity.CENTER);
-    addView(linearLayout,lp);
-  }
-
-  public void setContentGravity(int gravity) {
-    if (linearLayout != null) {
-      linearLayout.setGravity(gravity);
-    }
-  }
-
-  /**
-   * Setting refresh view or loading view
-   *
-   * @param view refresh or loading
-   */
-  public void setRefreshView(final View view) {
-    if (view == null)
-      return;
-    post(WXThread.secure(new Runnable() {
-      @Override
-      public void run() {
-        View child = null;
-        View temp = view;
-        if (view.getParent() != null) {
-          ((ViewGroup) view.getParent()).removeView(view);
-        }
-        for (int i = 0;i<((ViewGroup)temp).getChildCount(); i++) {
-          child = ((ViewGroup) temp).getChildAt(i);
-          if (child instanceof CircleProgressBar)
-            circleProgressBar = (CircleProgressBar) child;
-        }
-        linearLayout.addView(temp);
-      }
-    }));
-  }
-
-  /**
-   * Set loading_indicator bgColor
-   *
-   * @param color
-   */
-  public void setProgressBgColor(int color) {
-    if (circleProgressBar != null) {
-      circleProgressBar.setBackgroundColor(color);
-    }
-  }
-
-  /**
-   * Set loading_indicator color
-   *
-   * @param color
-   */
-  public void setProgressColor(int color) {
-    if (circleProgressBar != null) {
-      circleProgressBar.setColorSchemeColors(color);
-    }
-  }
-
-  protected void startAnimation() {
-    if (circleProgressBar != null) {
-      circleProgressBar.start();
-    }
-  }
-
-  /**
-   * Set the start and end trim for the progress spinner arc.
-   *
-   * @param startAngle start angle
-   * @param endAngle end angle
-   */
-  public void setStartEndTrim(float startAngle, float endAngle) {
-    if (circleProgressBar != null) {
-      circleProgressBar.setStartEndTrim(startAngle, endAngle);
-    }
-  }
-
-  protected void stopAnimation() {
-    if (circleProgressBar != null) {
-      circleProgressBar.stop();
-    }
-  }
-
-  /**
-   * Set the amount of rotation to apply to the progress spinner.
-   *
-   * @param rotation Rotation is from [0..1]
-   */
-  public void setProgressRotation(float rotation) {
-    if (circleProgressBar != null)
-      circleProgressBar.setProgressRotation(rotation);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/core/WXSwipeLayout.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/core/WXSwipeLayout.java
deleted file mode 100644
index 91f2711..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/core/WXSwipeLayout.java
+++ /dev/null
@@ -1,854 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.refresh.core;
-
-import android.animation.Animator;
-import android.animation.ValueAnimator;
-import android.annotation.SuppressLint;
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.graphics.Color;
-import android.os.Build;
-import android.support.annotation.Nullable;
-import android.support.v4.view.NestedScrollingChild;
-import android.support.v4.view.NestedScrollingChildHelper;
-import android.support.v4.view.NestedScrollingParent;
-import android.support.v4.view.NestedScrollingParentHelper;
-import android.support.v4.view.ViewCompat;
-import android.support.v4.view.ViewParentCompat;
-import android.util.AttributeSet;
-import android.util.DisplayMetrics;
-import android.util.TypedValue;
-import android.view.Gravity;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewParent;
-import android.widget.AbsListView;
-import android.widget.FrameLayout;
-
-import java.util.LinkedList;
-import java.util.List;
-
-public class WXSwipeLayout extends FrameLayout implements NestedScrollingParent, NestedScrollingChild {
-
-  private NestedScrollingParentHelper mNestedScrollingParentHelper;
-  private NestedScrollingChildHelper mNestedScrollingChildHelper;
-  private final int[] mParentScrollConsumed = new int[2];
-  private final int[] mParentOffsetInWindow = new int[2];
-  private boolean mNestedScrollInProgress;
-  private WXOnRefreshListener onRefreshListener;
-  private WXOnLoadingListener onLoadingListener;
-
-  private ViewParent mNestedScrollAcceptedParent;
-
-  private final List<OnRefreshOffsetChangedListener> mRefreshOffsetChangedListeners = new LinkedList<>();
-
-  public interface OnRefreshOffsetChangedListener {
-    void onOffsetChanged(int verticalOffset);
-  }
-
-  /**
-   * On refresh Callback, call on start refresh
-   */
-  public interface WXOnRefreshListener {
-
-    void onRefresh();
-
-    void onPullingDown(float dy, int pullOutDistance, float viewHeight);
-  }
-
-  /**
-   * On loadmore Callback, call on start loadmore
-   */
-  public interface WXOnLoadingListener {
-
-    void onLoading();
-    void onPullingUp(float dy, int pullOutDistance, float viewHeight);
-  }
-
-  static class WXRefreshAnimatorListener implements Animator.AnimatorListener {
-
-    @Override
-    public void onAnimationStart(Animator animation) {
-    }
-
-    @Override
-    public void onAnimationEnd(Animator animation) {
-    }
-
-    @Override
-    public void onAnimationCancel(Animator animation) {
-    }
-
-    @Override
-    public void onAnimationRepeat(Animator animation) {
-    }
-  }
-
-  private WXRefreshView headerView;
-  private WXRefreshView footerView;
-  private View mTargetView;
-
-  private static final int INVALID = -1;
-  private static final int PULL_REFRESH = 0;
-  private static final int LOAD_MORE = 1;
-
-  // Enable PullRefresh and Loadmore
-  private boolean mPullRefreshEnable = false;
-  private boolean mPullLoadEnable = false;
-
-  // Is Refreshing
-  volatile private boolean mRefreshing = false;
-
-  // RefreshView Height
-  private volatile float refreshViewHeight = 0;
-  private volatile float loadingViewHeight = 0;
-
-  // RefreshView Over Flow Height
-  private volatile float refreshViewFlowHeight = 0;
-  private volatile float loadingViewFlowHeight = 0;
-
-  private static final float overFlow = 1.0f;
-
-  private static final float DAMPING = 0.4f;
-
-  // Drag Action
-  private int mCurrentAction = -1;
-  private boolean isConfirm = false;
-
-  // RefreshView Attrs
-  private int mRefreshViewBgColor;
-  private int mProgressBgColor;
-  private int mProgressColor;
-
-  public WXSwipeLayout(Context context) {
-    super(context);
-    initAttrs(context, null);
-  }
-
-  public WXSwipeLayout(Context context, AttributeSet attrs) {
-    super(context, attrs);
-    initAttrs(context, attrs);
-  }
-
-  public WXSwipeLayout(Context context, AttributeSet attrs, int defStyleAttr) {
-    super(context, attrs, defStyleAttr);
-    initAttrs(context, attrs);
-  }
-
-  @TargetApi(Build.VERSION_CODES.LOLLIPOP)
-  public WXSwipeLayout(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
-    super(context, attrs, defStyleAttr, defStyleRes);
-    initAttrs(context, attrs);
-  }
-
-  private void initAttrs(Context context, AttributeSet attrs) {
-
-    if (getChildCount() > 1) {
-      throw new RuntimeException("WXSwipeLayout should not have more than one child");
-    }
-
-    mNestedScrollingParentHelper = new NestedScrollingParentHelper(this);
-    mNestedScrollingChildHelper = new NestedScrollingChildHelper(this);
-    setNestedScrollingEnabled(false);
-
-    if (isInEditMode() && attrs == null) {
-      return;
-    }
-
-    mRefreshViewBgColor = Color.TRANSPARENT;
-    mProgressBgColor = Color.TRANSPARENT;
-    mProgressColor = Color.RED;
-  }
-
-  @Override
-  protected void onAttachedToWindow() {
-    super.onAttachedToWindow();
-    if(mTargetView == null && getChildCount() > 0){
-      mTargetView = getChildAt(0);
-    }
-    if(mTargetView != null){
-      if(headerView == null || footerView == null){
-        setRefreshView();
-      }
-    }
-  }
-
-
-  public void addTargetView(View mInnerView){
-    this.addView(mInnerView, new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, FrameLayout.LayoutParams.MATCH_PARENT));
-    setRefreshView();
-  }
-  /**
-   * Init refresh view or loading view
-   */
-  private void setRefreshView() {
-    // SetUp HeaderView
-    FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, 0);
-    headerView = new WXRefreshView(getContext());
-    headerView.setStartEndTrim(0, 0.75f);
-    headerView.setBackgroundColor(mRefreshViewBgColor);
-    headerView.setProgressBgColor(mProgressBgColor);
-    headerView.setProgressColor(mProgressColor);
-    headerView.setContentGravity(Gravity.BOTTOM);
-    addView(headerView, lp);
-
-    // SetUp FooterView
-    lp = new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, 0);
-    lp.gravity = Gravity.BOTTOM;
-    footerView = new WXRefreshView(getContext());
-    footerView.setStartEndTrim(0.5f, 1.25f);
-    footerView.setBackgroundColor(mRefreshViewBgColor);
-    footerView.setProgressBgColor(mProgressBgColor);
-    footerView.setProgressColor(mProgressColor);
-    footerView.setContentGravity(Gravity.TOP);
-    addView(footerView, lp);
-  }
-
-  @Override
-  public boolean onInterceptTouchEvent(MotionEvent ev) {
-    if ((!mPullRefreshEnable && !mPullLoadEnable)) {
-      return false;
-    }
-    if (!isEnabled() || canChildScrollUp()
-            || mRefreshing || mNestedScrollInProgress) {
-      // Fail fast if we're not in a state where a swipe is possible
-      return false;
-    }
-
-    return super.onInterceptTouchEvent(ev);
-  }
-
-  // NestedScrollingChild
-
-  @Override
-  public void setNestedScrollingEnabled(boolean enabled) {
-    mNestedScrollingChildHelper.setNestedScrollingEnabled(enabled);
-  }
-
-  @Override
-  public boolean isNestedScrollingEnabled() {
-    return mNestedScrollingChildHelper.isNestedScrollingEnabled();
-  }
-
-  @Override
-  public boolean startNestedScroll(int axes) {
-    boolean result = mNestedScrollingChildHelper.startNestedScroll(axes);
-    if(result){
-      if(mNestedScrollAcceptedParent == null){
-        ViewParent parent  = this.getParent();
-        View child = this;
-        while (parent != null) {
-          if (ViewParentCompat.onStartNestedScroll(parent, child, this, axes)){
-            mNestedScrollAcceptedParent = parent;
-            break;
-          }
-          if(parent instanceof  View){
-            child = (View) parent;
-          }
-          parent = parent.getParent();
-        }
-      }
-    }
-    return result;
-  }
-
-  @Override
-  public void stopNestedScroll() {
-    mNestedScrollingChildHelper.stopNestedScroll();
-    if(mNestedScrollAcceptedParent != null){
-      mNestedScrollAcceptedParent = null;
-    }
-  }
-
-  @Override
-  public boolean hasNestedScrollingParent() {
-    return mNestedScrollingChildHelper.hasNestedScrollingParent();
-  }
-
-  @Override
-  public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed,
-                                      int dyUnconsumed, int[] offsetInWindow) {
-    return mNestedScrollingChildHelper.dispatchNestedScroll(dxConsumed, dyConsumed,
-            dxUnconsumed, dyUnconsumed, offsetInWindow);
-  }
-
-  @Override
-  public boolean dispatchNestedPreScroll(int dx, int dy, int[] consumed, int[] offsetInWindow) {
-    return mNestedScrollingChildHelper.dispatchNestedPreScroll(
-            dx, dy, consumed, offsetInWindow);
-  }
-
-
-
-  @Override
-  public boolean dispatchNestedFling(float velocityX, float velocityY, boolean consumed) {
-    return mNestedScrollingChildHelper.dispatchNestedFling(velocityX, velocityY, consumed);
-  }
-
-  @Override
-  public boolean dispatchNestedPreFling(float velocityX, float velocityY) {
-    return mNestedScrollingChildHelper.dispatchNestedPreFling(velocityX, velocityY);
-  }
-
-  /*********************************** NestedScrollParent *************************************/
-
-
-  @Override
-  public boolean onNestedPreFling(View target, float velocityX,
-                                  float velocityY) {
-    if(isNestedScrollingEnabled()) {
-      return dispatchNestedPreFling(velocityX, velocityY);
-    }
-    return  false;
-  }
-
-  @Override
-  public boolean onNestedFling(View target, float velocityX, float velocityY,
-                               boolean consumed) {
-    if(isNestedScrollingEnabled()) {
-      return dispatchNestedFling(velocityX, velocityY, consumed);
-    }
-    return  false;
-  }
-
-  @Override
-  public boolean onStartNestedScroll(View child, View target, int nestedScrollAxes) {
-    boolean result =  isEnabled()  && !mRefreshing
-            && (nestedScrollAxes & ViewCompat.SCROLL_AXIS_VERTICAL) != 0;
-
-    return  result;
-  }
-
-  @Override
-  public void onNestedScrollAccepted(View child, View target, int axes) {
-    mNestedScrollingParentHelper.onNestedScrollAccepted(child, target, axes);
-    if(isNestedScrollingEnabled()){
-      startNestedScroll(axes & ViewCompat.SCROLL_AXIS_VERTICAL);
-      mNestedScrollInProgress = true;
-    }
-  }
-
-
-  /**
-   * With child view to processing move events
-   * @param target the child view
-   * @param dx move x
-   * @param dy move y
-   * @param consumed parent consumed move distance
-   */
-  @Override
-  public void onNestedPreScroll(View target, int dx, int dy, int[] consumed) {
-    // Now let our nested parent consume the leftovers
-    final int[] parentConsumed = mParentScrollConsumed;
-    if(isNestedScrollingEnabled()){
-      if (dispatchNestedPreScroll(dx - consumed[0], dy - consumed[1], parentConsumed, null)) {
-        consumed[0] += parentConsumed[0];
-        consumed[1] += parentConsumed[1];
-        return;
-      }
-    }
-    if ((!mPullRefreshEnable && !mPullLoadEnable)) {
-      return;
-    }
-
-    /**
-     * when in nest-scroll, list canChildScrollUp() false,
-     * maybe parent scroll can scroll up
-     * */
-    if(!canChildScrollUp() && isNestedScrollingEnabled()){
-      if(mNestedScrollAcceptedParent != null && mNestedScrollAcceptedParent != mTargetView){
-        ViewGroup group = (ViewGroup) mNestedScrollAcceptedParent;
-        if(group.getChildCount() > 0){
-          int count = group.getChildCount();
-          for(int i=0; i<count; i++){
-            View view  = group.getChildAt(i);
-            if(view.getVisibility() != View.GONE && view.getMeasuredHeight() > 0){
-              if(view.getTop() < 0){
-                return;
-              }else{
-                break;
-              }
-            }
-          }
-        }
-      }
-    }
-
-
-
-    int spinnerDy = (int) calculateDistanceY(target, dy);
-
-    mRefreshing = false;
-
-    if (!isConfirm) {
-      if (spinnerDy < 0 && !canChildScrollUp()) {
-        mCurrentAction = PULL_REFRESH;
-        isConfirm = true;
-      } else if (spinnerDy > 0 && !canChildScrollDown() && (!mRefreshing)) {
-        mCurrentAction = LOAD_MORE;
-        isConfirm = true;
-      }
-    }
-
-    if (moveSpinner(-spinnerDy)) {
-      if (!canChildScrollUp() && mPullRefreshEnable
-              && mTargetView.getTranslationY() > 0
-              && dy > 0) {
-        consumed[1] += dy;
-      }else if (!canChildScrollDown() && mPullLoadEnable
-              && mTargetView.getTranslationY() < 0
-              && dy < 0){
-        consumed[1] += dy;
-      }else{
-        consumed[1] += spinnerDy;
-      }
-    }
-  }
-
-  @Override
-  public int getNestedScrollAxes() {
-    return mNestedScrollingParentHelper.getNestedScrollAxes();
-  }
-
-
-  /**
-   * Callback on TouchEvent.ACTION_CANCLE or TouchEvent.ACTION_UP
-   * handler : refresh or loading
-   * @param child : child view of SwipeLayout,RecyclerView or Scroller
-   */
-  @Override
-  public void onStopNestedScroll(View child) {
-    mNestedScrollingParentHelper.onStopNestedScroll(child);
-    handlerAction();
-    if(isNestedScrollingEnabled()) {
-      mNestedScrollInProgress = true;
-      stopNestedScroll();
-    }
-  }
-
-
-  @Override
-  public void onNestedScroll(View target, int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed) {
-    if(isNestedScrollingEnabled()) {
-      dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, mParentOffsetInWindow);
-    }
-  }
-
-
-
-
-
-  private double calculateDistanceY(View target, int dy) {
-    int viewHeight = target.getMeasuredHeight();
-    double ratio = (viewHeight - Math.abs(target.getY())) / 1.0d / viewHeight * DAMPING;
-    if (ratio <= 0.01d) {
-      //Filter tiny scrolling action
-      ratio = 0.01d;
-    }
-    return ratio * dy;
-  }
-
-  /**
-   * Adjust the refresh or loading view according to the size of the gesture
-   *
-   * @param distanceY move distance of Y
-   */
-  private boolean moveSpinner(float distanceY) {
-    if (mRefreshing) {
-      return false;
-    }
-
-    if (!canChildScrollUp() && mPullRefreshEnable && mCurrentAction == PULL_REFRESH) {
-      // Pull Refresh
-      LayoutParams lp = (LayoutParams) headerView.getLayoutParams();
-      lp.height += distanceY;
-      if (lp.height < 0) {
-        lp.height = 0;
-      }
-
-      if (lp.height == 0) {
-        isConfirm = false;
-        mCurrentAction = INVALID;
-      }
-      headerView.setLayoutParams(lp);
-      onRefreshListener.onPullingDown(distanceY, lp.height, refreshViewFlowHeight);
-      notifyOnRefreshOffsetChangedListener(lp.height);
-      headerView.setProgressRotation(lp.height / refreshViewFlowHeight);
-      moveTargetView(lp.height);
-      return true;
-    } else if (!canChildScrollDown() && mPullLoadEnable && mCurrentAction == LOAD_MORE) {
-      // Load more
-      LayoutParams lp = (LayoutParams) footerView.getLayoutParams();
-      lp.height -= distanceY;
-      if (lp.height < 0) {
-        lp.height = 0;
-      }
-
-      if (lp.height == 0) {
-        isConfirm = false;
-        mCurrentAction = INVALID;
-      }
-      footerView.setLayoutParams(lp);
-      onLoadingListener.onPullingUp(distanceY, lp.height, loadingViewFlowHeight);
-      footerView.setProgressRotation(lp.height / loadingViewFlowHeight);
-      moveTargetView(-lp.height);
-      return true;
-    }
-    return false;
-  }
-
-  /**
-   * Adjust contentView(Scroller or List) at refresh or loading time
-   * @param h Height of refresh view or loading view
-   */
-  private void moveTargetView(float h) {
-    mTargetView.setTranslationY(h);
-  }
-
-  /**
-   * Decide on the action refresh or loadmore
-   */
-  private void handlerAction() {
-
-    if (isRefreshing()) {
-      return;
-    }
-    isConfirm = false;
-
-    LayoutParams lp;
-    if (mPullRefreshEnable && mCurrentAction == PULL_REFRESH) {
-      lp = (LayoutParams) headerView.getLayoutParams();
-      if (lp.height >= refreshViewHeight) {
-        startRefresh(lp.height);
-      } else if (lp.height > 0) {
-        resetHeaderView(lp.height);
-      } else {
-        resetRefreshState();
-      }
-    }
-
-    if (mPullLoadEnable && mCurrentAction == LOAD_MORE) {
-      lp = (LayoutParams) footerView.getLayoutParams();
-      if (lp.height >= loadingViewHeight) {
-        startLoadmore(lp.height);
-      } else if (lp.height > 0) {
-        resetFootView(lp.height);
-      } else {
-        resetLoadmoreState();
-      }
-    }
-  }
-
-  /**
-   * Start Refresh
-   * @param headerViewHeight
-   */
-  private void startRefresh(int headerViewHeight) {
-    mRefreshing = true;
-    ValueAnimator animator = ValueAnimator.ofFloat(headerViewHeight, refreshViewHeight);
-    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
-      @Override
-      public void onAnimationUpdate(ValueAnimator animation) {
-        LayoutParams lp = (LayoutParams) headerView.getLayoutParams();
-        lp.height = (int) ((Float) animation.getAnimatedValue()).floatValue();
-        notifyOnRefreshOffsetChangedListener(lp.height);
-        headerView.setLayoutParams(lp);
-        moveTargetView(lp.height);
-      }
-    });
-    animator.addListener(new WXRefreshAnimatorListener() {
-      @Override
-      public void onAnimationEnd(Animator animation) {
-        headerView.startAnimation();
-        //TODO updateLoadText
-        if (onRefreshListener != null) {
-          onRefreshListener.onRefresh();
-        }
-      }
-    });
-    animator.setDuration(300);
-    animator.start();
-  }
-
-  /**
-   * Reset refresh state
-   * @param headerViewHeight
-   */
-  private void resetHeaderView(int headerViewHeight) {
-    headerView.stopAnimation();
-    headerView.setStartEndTrim(0, 0.75f);
-    ValueAnimator animator = ValueAnimator.ofFloat(headerViewHeight, 0);
-    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
-      @Override
-      public void onAnimationUpdate(ValueAnimator animation) {
-        LayoutParams lp = (LayoutParams) headerView.getLayoutParams();
-        lp.height = (int) ((Float) animation.getAnimatedValue()).floatValue();
-        notifyOnRefreshOffsetChangedListener(lp.height);
-        headerView.setLayoutParams(lp);
-        moveTargetView(lp.height);
-      }
-    });
-    animator.addListener(new WXRefreshAnimatorListener() {
-      @Override
-      public void onAnimationEnd(Animator animation) {
-        resetRefreshState();
-
-      }
-    });
-    animator.setDuration(300);
-    animator.start();
-  }
-
-  private void resetRefreshState() {
-    mRefreshing = false;
-    isConfirm = false;
-    mCurrentAction = -1;
-    //TODO updateLoadText
-  }
-
-  /**
-   * Start loadmore
-   * @param headerViewHeight
-   */
-  private void startLoadmore(int headerViewHeight) {
-    mRefreshing = true;
-    ValueAnimator animator = ValueAnimator.ofFloat(headerViewHeight, loadingViewHeight);
-    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
-      @Override
-      public void onAnimationUpdate(ValueAnimator animation) {
-        LayoutParams lp = (LayoutParams) footerView.getLayoutParams();
-        lp.height = (int) ((Float) animation.getAnimatedValue()).floatValue();
-        footerView.setLayoutParams(lp);
-        moveTargetView(-lp.height);
-      }
-    });
-    animator.addListener(new WXRefreshAnimatorListener() {
-      @Override
-      public void onAnimationEnd(Animator animation) {
-        footerView.startAnimation();
-        //TODO updateLoadText
-        if (onLoadingListener != null) {
-          onLoadingListener.onLoading();
-        }
-      }
-    });
-    animator.setDuration(300);
-    animator.start();
-  }
-
-  /**
-   * Reset loadmore state
-   * @param headerViewHeight
-   */
-  private void resetFootView(int headerViewHeight) {
-    footerView.stopAnimation();
-    footerView.setStartEndTrim(0.5f, 1.25f);
-    ValueAnimator animator = ValueAnimator.ofFloat(headerViewHeight, 0);
-    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
-      @Override
-      public void onAnimationUpdate(ValueAnimator animation) {
-        LayoutParams lp = (LayoutParams) footerView.getLayoutParams();
-        lp.height = (int) ((Float) animation.getAnimatedValue()).floatValue();
-        footerView.setLayoutParams(lp);
-        moveTargetView(-lp.height);
-      }
-    });
-    animator.addListener(new WXRefreshAnimatorListener() {
-      @Override
-      public void onAnimationEnd(Animator animation) {
-        resetLoadmoreState();
-
-      }
-    });
-    animator.setDuration(300);
-    animator.start();
-  }
-
-  private void resetLoadmoreState() {
-    mRefreshing = false;
-    isConfirm = false;
-    mCurrentAction = -1;
-    //TODO updateLoadText
-  }
-
-  /**
-   * Whether child view can scroll up
-   * @return
-   */
-  @SuppressLint("ObsoleteSdkInt")
-  public boolean canChildScrollUp() {
-    if (mTargetView == null) {
-      return false;
-    }
-    if (Build.VERSION.SDK_INT < 14) {
-      //The minimum version of Android platform that Weex supports is API 14,
-      //so this block should never enter.
-      if (mTargetView instanceof AbsListView) {
-        final AbsListView absListView = (AbsListView) mTargetView;
-        return absListView.getChildCount() > 0
-                && (absListView.getFirstVisiblePosition() > 0 || absListView.getChildAt(0)
-                .getTop() < absListView.getPaddingTop());
-      } else {
-        return ViewCompat.canScrollVertically(mTargetView, -1) || mTargetView.getScrollY() > 0;
-      }
-    } else {
-      return ViewCompat.canScrollVertically(mTargetView, -1);
-    }
-  }
-
-  /**
-   * Whether child view can scroll down
-   * @return
-   */
-  @SuppressLint("ObsoleteSdkInt")
-  public boolean canChildScrollDown() {
-    if (mTargetView == null) {
-      return false;
-    }
-    if (Build.VERSION.SDK_INT < 14) {
-      //The minimum version of Android platform that Weex supports is API 14,
-      //so this block should never enter.
-      if (mTargetView instanceof AbsListView) {
-        final AbsListView absListView = (AbsListView) mTargetView;
-        if (absListView.getChildCount() > 0) {
-          int lastChildBottom = absListView.getChildAt(absListView.getChildCount() - 1)
-                  .getBottom();
-          return absListView.getLastVisiblePosition() == absListView.getAdapter().getCount() - 1
-                  && lastChildBottom <= absListView.getMeasuredHeight();
-        } else {
-          return false;
-        }
-
-      } else {
-        return ViewCompat.canScrollVertically(mTargetView, 1) || mTargetView.getScrollY() > 0;
-      }
-    } else {
-      return ViewCompat.canScrollVertically(mTargetView, 1);
-    }
-  }
-
-  public float dipToPx(Context context, float value) {
-    DisplayMetrics metrics = context.getResources().getDisplayMetrics();
-    return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, value, metrics);
-  }
-
-  public void setOnLoadingListener(WXOnLoadingListener onLoadingListener) {
-    this.onLoadingListener = onLoadingListener;
-  }
-
-  public void setOnRefreshListener(WXOnRefreshListener onRefreshListener) {
-    this.onRefreshListener = onRefreshListener;
-  }
-
-  @SuppressWarnings("unused")
-  public void addOnRefreshOffsetChangedListener(@Nullable OnRefreshOffsetChangedListener listener) {
-    if(listener != null && !mRefreshOffsetChangedListeners.contains(listener)) {
-      mRefreshOffsetChangedListeners.add(listener);
-    }
-  }
-
-  @SuppressWarnings("unused")
-  public boolean removeOnRefreshOffsetChangedListener(@Nullable OnRefreshOffsetChangedListener listener) {
-    if(listener != null) {
-      return mRefreshOffsetChangedListeners.remove(listener);
-    }
-    return false;
-  }
-
-  private void notifyOnRefreshOffsetChangedListener(int verticalOffset) {
-    int size = mRefreshOffsetChangedListeners.size();
-    OnRefreshOffsetChangedListener listener;
-    for (int i=0; i<size; i++) {
-      if(i >= mRefreshOffsetChangedListeners.size()){
-        break;
-      }
-      listener = mRefreshOffsetChangedListeners.get(i);
-
-      if (listener != null) {
-        listener.onOffsetChanged(verticalOffset);
-      }
-    }
-  }
-
-  /**
-   * Callback on refresh finish
-   */
-  public void finishPullRefresh() {
-    if (mCurrentAction == PULL_REFRESH) {
-      resetHeaderView(headerView == null ? 0 : headerView.getMeasuredHeight());
-    }
-  }
-
-  /**
-   * Callback on loadmore finish
-   */
-  public void finishPullLoad() {
-    if (mCurrentAction == LOAD_MORE) {
-      resetFootView(footerView == null ? 0 : footerView.getMeasuredHeight());
-    }
-  }
-
-  public WXRefreshView getHeaderView() {
-    return headerView;
-  }
-
-  public WXRefreshView getFooterView() {
-    return footerView;
-  }
-
-  public boolean isPullLoadEnable() {
-    return mPullLoadEnable;
-  }
-
-  public void setPullLoadEnable(boolean mPullLoadEnable) {
-    this.mPullLoadEnable = mPullLoadEnable;
-  }
-
-  public boolean isPullRefreshEnable() {
-    return mPullRefreshEnable;
-  }
-
-  public void setPullRefreshEnable(boolean mPullRefreshEnable) {
-    this.mPullRefreshEnable = mPullRefreshEnable;
-  }
-
-  public boolean isRefreshing() {
-    return mRefreshing;
-  }
-
-  public void setRefreshHeight(int height) {
-    refreshViewHeight = height;
-    refreshViewFlowHeight = refreshViewHeight * overFlow;
-  }
-
-  public void setLoadingHeight(int height) {
-    loadingViewHeight = height;
-    loadingViewFlowHeight = loadingViewHeight * overFlow;
-  }
-
-  public void setRefreshBgColor(int color) {
-    headerView.setBackgroundColor(color);
-  }
-
-  public void setLoadingBgColor(int color) {
-    footerView.setBackgroundColor(color);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BaseBounceView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BaseBounceView.java
deleted file mode 100644
index ca8f510..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BaseBounceView.java
+++ /dev/null
@@ -1,226 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.refresh.wrapper;
-
-import android.content.Context;
-import android.graphics.Color;
-import android.support.v7.widget.OrientationHelper;
-import android.text.TextUtils;
-import android.util.AttributeSet;
-import android.view.View;
-import android.widget.FrameLayout;
-
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.view.WXLoadingLayout;
-import com.taobao.weex.ui.view.WXRefreshLayout;
-import com.taobao.weex.ui.view.refresh.core.WXRefreshView;
-import com.taobao.weex.ui.view.refresh.core.WXSwipeLayout;
-import com.taobao.weex.utils.WXResourceUtils;
-import com.taobao.weex.utils.WXUtils;
-
-/**
- * BounceView(SwipeLayout) contains Scroller/List and refresh/loading view
- * @param <T> InnerView
- */
-public abstract class BaseBounceView<T extends View> extends FrameLayout {
-
-    private int mOrientation = OrientationHelper.VERTICAL;
-    protected WXSwipeLayout swipeLayout;
-    private T mInnerView;
-
-    public BaseBounceView(Context context,int orientation) {
-        this(context, null,orientation);
-    }
-
-    public BaseBounceView(Context context, AttributeSet attrs,int orientation) {
-        super(context, attrs);
-        mOrientation = orientation;
-    }
-
-    public int getOrientation(){
-        return mOrientation;
-    }
-
-    public void init(Context context) {
-        createBounceView(context);
-    }
-
-    boolean isVertical(){
-        return mOrientation==OrientationHelper.VERTICAL;
-    }
-
-    public void setOnRefreshListener(WXSwipeLayout.WXOnRefreshListener onRefreshListener) {
-        if (swipeLayout != null)
-            swipeLayout.setOnRefreshListener(onRefreshListener);
-    }
-
-    public void setOnLoadingListener(WXSwipeLayout.WXOnLoadingListener onLoadingListener) {
-        if (swipeLayout != null)
-            swipeLayout.setOnLoadingListener(onLoadingListener);
-    }
-
-    public void finishPullRefresh() {
-        if (swipeLayout != null)
-            swipeLayout.finishPullRefresh();
-    }
-
-    public void finishPullLoad() {
-        if (swipeLayout != null)
-            swipeLayout.finishPullLoad();
-    }
-
-    /**
-     * Init wipelayout
-     */
-    private WXSwipeLayout createBounceView(Context context) {
-        swipeLayout = new WXSwipeLayout(context);
-        swipeLayout.setLayoutParams(new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, FrameLayout.LayoutParams.MATCH_PARENT));
-        mInnerView = setInnerView(context);
-        if (mInnerView == null)
-            return null;
-        swipeLayout.addTargetView(mInnerView);
-        addView(swipeLayout, LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
-        return swipeLayout;
-    }
-
-    /**
-     * @return the child of swipelayout : recyclerview or scrollview
-     */
-    public T getInnerView() {
-        return mInnerView;
-    }
-
-    public abstract T setInnerView(Context context);
-
-    /**
-     *
-     * @param refresh should be {@link WXRefreshView}
-     */
-    public void setHeaderView(WXComponent refresh) {
-        setRefreshEnable(true);
-        if (swipeLayout != null) {
-            WXRefreshView refreshView = swipeLayout.getHeaderView();
-            if (refreshView != null) {
-                if (refresh != null) {
-                    int refreshHeight = (int) refresh.getLayoutHeight();
-                    swipeLayout.setRefreshHeight(refreshHeight);
-                    String colorStr = (String) refresh.getStyles().get(Constants.Name.BACKGROUND_COLOR);
-                    String bgColor = WXUtils.getString(colorStr, null);
-                    if (bgColor != null) {
-                        if (!TextUtils.isEmpty(bgColor)) {
-                            int colorInt = WXResourceUtils.getColor(bgColor);
-                            if (!(colorInt == Color.TRANSPARENT)) {
-                                swipeLayout.setRefreshBgColor(colorInt);
-                            }
-                        }
-                    }
-                    refreshView.setRefreshView(refresh.getHostView());
-                }
-            }
-        }
-    }
-
-    /**
-     *
-     * @param loading should be {@link WXRefreshView}
-     */
-    public void setFooterView(WXComponent loading) {
-        setLoadmoreEnable(true);
-        if (swipeLayout != null) {
-            WXRefreshView refreshView = swipeLayout.getFooterView();
-            if (refreshView != null) {
-                if (loading != null) {
-                    int loadingHeight = (int) loading.getLayoutHeight();
-                    swipeLayout.setLoadingHeight(loadingHeight);
-                    String colorStr = (String) loading.getStyles().get(Constants.Name.BACKGROUND_COLOR);
-                    String bgColor = WXUtils.getString(colorStr, null);
-                    if (bgColor != null) {
-                        if (!TextUtils.isEmpty(bgColor)) {
-                            int colorInt = WXResourceUtils.getColor(bgColor);
-                            if (!(colorInt == Color.TRANSPARENT)) {
-                                swipeLayout.setLoadingBgColor(colorInt);
-                            }
-                        }
-                    }
-                    refreshView.setRefreshView(loading.getHostView());
-                }
-            }
-        }
-    }
-
-    public void removeFooterView(WXComponent loading){
-        setLoadmoreEnable(false);
-        if(swipeLayout!=null){
-            if(swipeLayout.getFooterView()!=null){
-                swipeLayout.setLoadingHeight(0);
-                swipeLayout.getFooterView().removeView(loading.getHostView());
-                swipeLayout.finishPullLoad();
-            }
-        }
-    }
-    //TODO There are bugs, will be more than a rolling height
-    public void removeHeaderView(WXComponent refresh){
-        setRefreshEnable(false);
-        if(swipeLayout!=null){
-            if(swipeLayout.getHeaderView()!=null){
-                swipeLayout.setRefreshHeight(0);
-                swipeLayout.getHeaderView().removeView(refresh.getHostView());
-                swipeLayout.finishPullRefresh();
-            }
-        }
-    }
-
-    public void setRefreshEnable(boolean enable) {
-        if (swipeLayout != null)
-            swipeLayout.setPullRefreshEnable(enable);
-    }
-
-    public void setLoadmoreEnable(boolean enable) {
-        if (swipeLayout != null)
-            swipeLayout.setPullLoadEnable(enable);
-    }
-
-    @Override
-    public void removeView(View view) {
-        if (view instanceof WXLoadingLayout) {
-            finishPullLoad();
-            setLoadmoreEnable(false);
-            if (swipeLayout != null) {
-                swipeLayout.removeView(swipeLayout.getFooterView());
-            }
-        } else if (view instanceof WXRefreshLayout) {
-            finishPullRefresh();
-            setRefreshEnable(false);
-            if (swipeLayout != null) {
-                swipeLayout.removeView(swipeLayout.getHeaderView());
-            }
-        } else {
-            super.removeView(view);
-        }
-    }
-
-    public WXSwipeLayout getSwipeLayout() {
-        return swipeLayout;
-    }
-
-    public abstract void onRefreshingComplete();
-
-    public abstract void onLoadmoreComplete();
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BounceRecyclerView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BounceRecyclerView.java
deleted file mode 100644
index 84e7ac7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BounceRecyclerView.java
+++ /dev/null
@@ -1,135 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.refresh.wrapper;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.support.annotation.Nullable;
-import android.view.MotionEvent;
-
-import com.taobao.weex.ui.component.list.ListComponentView;
-import com.taobao.weex.ui.component.list.StickyHeaderHelper;
-import com.taobao.weex.ui.component.list.WXCell;
-import com.taobao.weex.ui.view.gesture.WXGesture;
-import com.taobao.weex.ui.view.gesture.WXGestureObservable;
-import com.taobao.weex.ui.view.listview.WXRecyclerView;
-import com.taobao.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
-
-@SuppressLint("ViewConstructor")
-public class BounceRecyclerView extends BaseBounceView<WXRecyclerView> implements ListComponentView,WXGestureObservable {
-
-  public static final int DEFAULT_COLUMN_COUNT = 1;
-  public static final int DEFAULT_COLUMN_GAP = 1;
-  private RecyclerViewBaseAdapter adapter = null;
-  private WXGesture mGesture;
-  private int mLayoutType = WXRecyclerView.TYPE_LINEAR_LAYOUT;
-  private int mColumnCount = DEFAULT_COLUMN_COUNT;
-  private float mColumnGap = DEFAULT_COLUMN_GAP;
-  private StickyHeaderHelper mStickyHeaderHelper;
-
-  public BounceRecyclerView(Context context,int type,int columnCount,float columnGap,int orientation) {
-    super(context, orientation);
-    mLayoutType = type;
-    mColumnCount = columnCount;
-    mColumnGap = columnGap;
-    init(context);
-    mStickyHeaderHelper = new StickyHeaderHelper(this);
-  }
-
-  public BounceRecyclerView(Context context,int type,int orientation) {
-    this(context,type, DEFAULT_COLUMN_COUNT, DEFAULT_COLUMN_GAP,orientation);
-  }
-
-  public void setRecyclerViewBaseAdapter(RecyclerViewBaseAdapter adapter) {
-    this.adapter = adapter;
-    if (getInnerView() != null) {
-      getInnerView().setAdapter(adapter);
-    }
-  }
-
-  public RecyclerViewBaseAdapter getRecyclerViewBaseAdapter() {
-    return adapter;
-  }
-
-  @Override
-  public boolean dispatchTouchEvent(MotionEvent event) {
-    boolean result = super.dispatchTouchEvent(event);
-    if (mGesture != null) {
-      result |= mGesture.onTouch(this, event);
-    }
-    return result;
-  }
-
-  @Override
-  public WXRecyclerView setInnerView(Context context) {
-    WXRecyclerView wxRecyclerView = new WXRecyclerView(context);
-    wxRecyclerView.initView(context, mLayoutType,mColumnCount,mColumnGap,getOrientation());
-    return wxRecyclerView;
-  }
-
-  @Override
-  public void onRefreshingComplete() {
-    if (adapter != null) {
-      adapter.notifyDataSetChanged();
-    }
-  }
-
-  @Override
-  public void onLoadmoreComplete() {
-    if (adapter != null) {
-      adapter.notifyDataSetChanged();
-    }
-  }
-
-  /**
-   * @param component
-   */
-  public void notifyStickyShow(WXCell component) {
-    mStickyHeaderHelper.notifyStickyShow(component);
-  }
-
-  @Override
-  public void updateStickyView(int currentStickyPos) {
-    mStickyHeaderHelper.updateStickyView(currentStickyPos);
-  }
-
-  /**
-   *
-   * @param compToRemove
-   */
-  @Override
-  public void notifyStickyRemove(WXCell compToRemove) {
-    mStickyHeaderHelper.notifyStickyRemove(compToRemove);
-  }
-
-  public StickyHeaderHelper getStickyHeaderHelper() {
-    return mStickyHeaderHelper;
-  }
-
-  @Override
-  public void registerGestureListener(@Nullable WXGesture wxGesture) {
-    mGesture = wxGesture;
-    getInnerView().registerGestureListener(wxGesture);
-  }
-
-  @Override
-  public WXGesture getGestureListener() {
-    return mGesture;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BounceScrollerView.java b/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BounceScrollerView.java
deleted file mode 100644
index 20e2249..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/ui/view/refresh/wrapper/BounceScrollerView.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.refresh.wrapper;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-
-import com.taobao.weex.ui.component.WXScroller;
-import com.taobao.weex.ui.view.WXScrollView;
-
-@SuppressLint("ViewConstructor")
-public class BounceScrollerView extends BaseBounceView<WXScrollView> {
-
-    public BounceScrollerView(Context context, int orientation, WXScroller waScroller) {
-        super(context,orientation);
-        init(context);
-        if (getInnerView() != null)
-            getInnerView().setWAScroller(waScroller);
-    }
-
-    @Override
-    public WXScrollView setInnerView(Context context) {
-        return new WXScrollView(context);
-    }
-
-    @Override
-    public void onRefreshingComplete() {
-        //TODO update scroller dataset
-    }
-
-    @Override
-    public void onLoadmoreComplete() {
-        //TODO update scroller dataset
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/ATagUtil.java b/android/sdk/src/main/java/com/taobao/weex/utils/ATagUtil.java
deleted file mode 100644
index cc179e3..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/ATagUtil.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.utils;
-
-import android.net.Uri;
-import android.view.View;
-
-import com.alibaba.fastjson.JSONArray;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.URIAdapter;
-
-public class ATagUtil {
-  public static void onClick(View widget, String instanceId, String url) {
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (instance == null) {
-      return;
-    }
-    String href = instance.rewriteUri(Uri.parse(url), URIAdapter.LINK).toString();
-    JSONArray array = new JSONArray();
-    array.add(href);
-    WXSDKManager.getInstance().getWXBridgeManager().
-        callModuleMethod(instanceId, "event", "openURL", array);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/BoxShadowUtil.java b/android/sdk/src/main/java/com/taobao/weex/utils/BoxShadowUtil.java
deleted file mode 100644
index 66df2c9..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/BoxShadowUtil.java
+++ /dev/null
@@ -1,669 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.BlurMaskFilter;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.ColorFilter;
-import android.graphics.LinearGradient;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.PixelFormat;
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.graphics.Region;
-import android.graphics.Shader;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.LayerDrawable;
-import android.os.Build;
-import android.os.Build.VERSION_CODES;
-import android.support.annotation.IntRange;
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-import android.util.Log;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewParent;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.common.WXThread;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-
-/**
- * Created by moxun on 2017/9/4.
- * Utils for create shadow layer on view
- * Requires Android 4.3 and higher
- *
- * @see <a href="https://www.w3schools.com/cssref/css3_pr_box-shadow.asp">CSS3 box-shadow Property</>
- */
-
-public class BoxShadowUtil {
-  private static final String TAG = "BoxShadowUtil";
-  private static boolean sBoxShadowEnabled = true /*disable box-shadow temporary*/;
-
-  private static Pattern sColorPattern;
-
-  public static void setBoxShadowEnabled(boolean enabled) {
-    sBoxShadowEnabled = enabled;
-    WXLogUtils.w(TAG, "Switch box-shadow status: " + enabled);
-  }
-
-  public static boolean isBoxShadowEnabled() {
-    return sBoxShadowEnabled;
-  }
-
-  public static void setBoxShadow(final View target, String style, final float[] radii, int viewPort, final float quality) {
-    if (!sBoxShadowEnabled) {
-      WXLogUtils.w(TAG, "box-shadow was disabled by config");
-      return;
-    }
-
-    if (target == null) {
-      WXLogUtils.w(TAG, "Target view is null!");
-      return;
-    }
-
-    if (TextUtils.isEmpty(style) && Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
-      target.getOverlay().clear();
-      WXLogUtils.d(TAG, "Remove all box-shadow");
-      return;
-    }
-
-    final BoxShadowOptions[] shadows = parseBoxShadows(style, viewPort);
-    if (shadows == null || shadows.length == 0) {
-      WXLogUtils.w(TAG, "Failed to parse box-shadow: " + style);
-      return;
-    }
-
-    final List<BoxShadowOptions> normalShadows = new ArrayList<>(), insetShadows = new ArrayList<>();
-    for (BoxShadowOptions shadow : shadows) {
-      if (shadow != null) {
-        if (shadow.isInset) {
-          insetShadows.add(0, shadow);
-        } else {
-          normalShadows.add(0, shadow);
-        }
-      }
-    }
-
-    if (radii != null) {
-      if (radii.length != 8) {
-        WXLogUtils.w(TAG, "Length of radii must be 8");
-      } else {
-        for (int i = 0; i < radii.length; i++) {
-          float realRadius = WXViewUtils.getRealSubPxByWidth(radii[i], viewPort);
-          radii[i] = realRadius;
-        }
-      }
-    }
-
-    target.post(WXThread.secure(new Runnable() {
-      @Override
-      public void run() {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
-          target.getOverlay().clear();
-          if (normalShadows.size() > 0) {
-            setNormalBoxShadow(target, normalShadows, quality, radii);
-          }
-
-          if (insetShadows.size() > 0) {
-            setInsetBoxShadow(target, insetShadows, quality, radii);
-          }
-        }
-      }
-    }));
-  }
-
-  private static void drawShadow(Canvas canvas, BoxShadowOptions options) {
-    RectF shadowRect = new RectF(
-        0f, 0f,
-        options.viewWidth + 2f * options.spread, options.viewHeight + 2f * options.spread
-    );
-
-    if (options.topLeft != null) {
-      shadowRect.offset(options.topLeft.x, options.topLeft.y);
-    }
-
-    float shadowDx = options.blur;
-    float shadowDy = options.blur;
-    if (options.hShadow > 0) {
-      shadowDx = shadowDx + 2f * options.hShadow;
-    }
-    if (options.vShadow > 0) {
-      shadowDy = shadowDy + 2f * options.vShadow;
-    }
-    shadowRect.offset(shadowDx, shadowDy);
-
-    Paint shadowPaint = new Paint();
-    shadowPaint.setAntiAlias(true);
-    shadowPaint.setColor(options.color);
-    shadowPaint.setStyle(Paint.Style.FILL);
-
-    if (options.blur > 0) {
-      shadowPaint.setMaskFilter(new BlurMaskFilter(options.blur, BlurMaskFilter.Blur.NORMAL));
-    }
-
-    Path shadowPath = new Path();
-    float[] shadowRadii = new float[8];
-    for (int i = 0; i < options.radii.length; i++) {
-      float contentRadius = options.radii[i];
-      if (contentRadius == 0f) {
-        shadowRadii[i] = 0f;
-      } else {
-        shadowRadii[i] = options.radii[i] + options.spread;
-      }
-    }
-    shadowPath.addRoundRect(shadowRect, shadowRadii, Path.Direction.CCW);
-    canvas.drawPath(shadowPath, shadowPaint);
-
-    if (false && WXEnvironment.isApkDebugable()) {
-      Paint paint = new Paint();
-      paint.setAntiAlias(true);
-      paint.setColor(Color.BLACK);
-      paint.setStyle(Paint.Style.STROKE);
-      canvas.drawRect(shadowRect, paint);
-    }
-  }
-
-  private static void setNormalBoxShadow(View target, List<BoxShadowOptions> options, float quality, float[] radii) {
-    int h = target.getHeight();
-    int w = target.getWidth();
-
-    ViewGroup.LayoutParams p = target.getLayoutParams();
-
-    if (h == 0 || w == 0) {
-      Log.w(TAG, "Target view is invisible, ignore set shadow.");
-      return;
-    }
-
-    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
-      int maxWidth = 0, maxHeight = 0;
-      for (BoxShadowOptions option : options) {
-        option.viewWidth = w;
-        option.viewHeight = h;
-        option.radii = radii;
-
-        Rect rect = option.getTargetCanvasRect();
-        if (maxWidth < rect.width()) {
-          maxWidth = rect.width();
-        }
-
-        if (maxHeight < rect.height()) {
-          maxHeight = rect.height();
-        }
-      }
-
-      int canvasWidth = (int) (maxWidth * quality);
-      int canvasHeight = (int) (maxHeight * quality);
-      Bitmap output = Bitmap.createBitmap(canvasWidth, canvasHeight, Bitmap.Config.ARGB_4444);
-      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
-        WXLogUtils.d(TAG, "Allocation memory for box-shadow: " + (output.getAllocationByteCount() / 1024) + " KB");
-      }
-      Canvas canvas = new Canvas(output);
-
-      if (false && WXEnvironment.isApkDebugable()) {
-        // Using for debug
-        Paint strokePaint = new Paint();
-        strokePaint.setColor(Color.BLACK);
-        strokePaint.setStrokeWidth(2);
-        strokePaint.setStyle(Paint.Style.STROKE);
-        canvas.drawRect(canvas.getClipBounds(), strokePaint);
-      }
-
-      for (BoxShadowOptions option : options) {
-        Rect rect = option.getTargetCanvasRect();
-        float left = (maxWidth - rect.width()) / 2f;
-        float top = (maxHeight - rect.height()) / 2f;
-        option.topLeft = new PointF(left, top);
-
-        BoxShadowOptions scaledOption = option.scale(quality);
-        drawShadow(canvas, scaledOption);
-      }
-
-      //Drawable's bounds must match the bitmap size, otherwise the shadows will be scaled
-      int paddingX = (maxWidth - w) / 2;
-      int paddingY = (maxHeight - h) / 2;
-      OverflowBitmapDrawable shadowDrawable = new OverflowBitmapDrawable(target.getResources(),
-          output, new Point(paddingX, paddingY), new Rect(0, 0, w, h), radii);
-
-      target.getOverlay().add(shadowDrawable);
-      //Relayout to ensure the shadows are fully drawn
-      ViewParent parent = target.getParent();
-      if (parent != null) {
-        parent.requestLayout();
-        if (parent instanceof ViewGroup) {
-          ((ViewGroup) parent).invalidate(shadowDrawable.getBounds());
-        }
-      }
-    } else {
-      // I have a dream that one day our minSdkVersion will equals or higher than 21
-      Log.w("BoxShadowUtil", "Call setNormalBoxShadow() requires API level 18 or higher.");
-    }
-  }
-
-  private static void setInsetBoxShadow(View target, List<BoxShadowOptions> options, float quality, float[] radii) {
-    if (target == null || options == null) {
-      WXLogUtils.w(TAG, "Illegal arguments");
-      return;
-    }
-
-    if (target.getWidth() == 0 || target.getHeight() == 0) {
-      WXLogUtils.w(TAG, "Target view is invisible, ignore set shadow.");
-      return;
-    }
-
-    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
-      Drawable[] drawables = new Drawable[options.size()];
-      for (int i = 0; i < options.size(); i++) {
-        BoxShadowOptions option = options.get(i);
-        Drawable shadow = new InsetShadowDrawable(target.getWidth(), target.getHeight(),
-            option.hShadow, option.vShadow,
-            option.blur, option.spread,
-            option.color, radii);
-        drawables[i] = shadow;
-      }
-
-      LayerDrawable layerDrawable = new LayerDrawable(drawables);
-      target.getOverlay().add(layerDrawable);
-      target.invalidate();
-    } else {
-      Log.w(TAG, "Call setInsetBoxShadow() requires API level 18 or higher.");
-    }
-  }
-
-  public static BoxShadowOptions[] parseBoxShadows(String boxShadowStyle, int viewport) {
-    // normalization color expression to #AARRGGBB
-    if (sColorPattern == null) {
-      sColorPattern = Pattern.compile("([rR][gG][bB][aA]?)\\((\\d+\\s*),\\s*(\\d+\\s*),\\s*(\\d+\\s*)(?:,\\s*(\\d+(?:\\.\\d+)?))?\\)");
-    }
-
-    Matcher matcher = sColorPattern.matcher(boxShadowStyle);
-
-    String processedStyle = boxShadowStyle;
-    while (matcher.find()) {
-      String color = matcher.group();
-      processedStyle = processedStyle.replace(color, "#" + String.format("%8s", Integer.toHexString(WXResourceUtils.getColor(color, Color.BLACK))).replaceAll("\\s", "0"));
-    }
-
-    String[] styles = processedStyle.split(",");
-    if (styles != null && styles.length > 0) {
-      BoxShadowOptions[] result = new BoxShadowOptions[styles.length];
-      for (int i = 0; i < styles.length; i++) {
-        result[i] = parseBoxShadow(styles[i], viewport);
-      }
-      return result;
-    }
-    return null;
-  }
-
-  private static BoxShadowOptions parseBoxShadow(String boxShadow, int viewport) {
-    BoxShadowOptions result = new BoxShadowOptions(viewport);
-    if (TextUtils.isEmpty(boxShadow)) {
-      return null;
-    }
-
-    String boxShadowCopy = boxShadow;
-
-    // trim rgb() & rgba()
-    boxShadowCopy = boxShadowCopy.replaceAll("\\s*,\\s+", ",");
-
-    // match inset first
-    if (boxShadowCopy.contains("inset")) {
-      result.isInset = true;
-      boxShadowCopy = boxShadowCopy.replace("inset", "");
-    }
-
-    boxShadowCopy = boxShadowCopy.trim();
-    List<String> params = new ArrayList<>(Arrays.asList(boxShadowCopy.split("\\s+")));
-
-    // match color
-    String maybeColor = params.get(params.size() - 1);
-    if (!TextUtils.isEmpty(maybeColor)) {
-      if (maybeColor.startsWith("#") || maybeColor.startsWith("rgb") || WXResourceUtils.isNamedColor(maybeColor)) {
-        result.color = WXResourceUtils.getColor(maybeColor, Color.BLACK);
-        params.remove(params.size() - 1);
-      }
-    }
-
-    try {
-      if (params.size() < 2) {
-        // Missing required param
-        return null;
-      } else {
-        if (!TextUtils.isEmpty(params.get(0))) {
-          float px = WXUtils.getFloat(params.get(0).trim(), 0f);
-          result.hShadow = WXViewUtils.getRealSubPxByWidth(px, viewport);
-        }
-
-        if (!TextUtils.isEmpty(params.get(1))) {
-          float px = WXUtils.getFloat(params.get(1).trim(), 0f);
-          result.vShadow = WXViewUtils.getRealPxByWidth(px, viewport);
-        }
-
-        for (int i = 2; i < params.size(); i++) {
-          int parserIndex = i - 2;
-          BoxShadowOptions.IParser parser = result.optionParamParsers.get(parserIndex);
-          parser.parse(params.get(i));
-        }
-      }
-    } catch (Throwable t) {
-      t.printStackTrace();
-    }
-    return result;
-  }
-
-  private static class OverflowBitmapDrawable extends BitmapDrawable {
-    private int paddingX;
-    private int paddingY;
-    private Rect viewRect;
-    private float[] radii;
-
-    private OverflowBitmapDrawable(Resources resources, Bitmap bitmap, Point topLeft, Rect viewRect, float[] radii) {
-      super(resources, bitmap);
-      this.paddingX = topLeft.x;
-      this.paddingY = topLeft.y;
-      this.viewRect = viewRect;
-      this.radii = radii;
-
-      setBounds(-paddingX, -paddingY, viewRect.width() + paddingX, viewRect.height() + paddingY);
-    }
-
-    public void draw(Canvas canvas) {
-      Rect bounds = canvas.getClipBounds();
-      Rect newRect = new Rect(bounds);
-      // Make the Canvas Rect bigger according to the padding.
-      newRect.inset(-paddingX * 2, -paddingY * 2);
-      try {
-        if(WXEnvironment.sApplication.getApplicationInfo().targetSdkVersion > VERSION_CODES.O){
-          canvas.clipRect(newRect);
-        }
-        else{
-          canvas.clipRect(newRect, Region.Op.REPLACE);
-        }
-      }catch (NullPointerException e) {
-        canvas.clipRect(newRect);
-      }
-
-      Path contentPath = new Path();
-      // the content area map must be aligned with bounds
-      RectF rectF = new RectF(bounds);
-      contentPath.addRoundRect(rectF, radii, Path.Direction.CCW);
-      // can not antialias
-      canvas.clipPath(contentPath, Region.Op.DIFFERENCE);
-
-      // translate the canvas to a suitable position and then draw the bitmap, otherwise draw from the origin(0, 0)
-      canvas.translate(bounds.left, bounds.top);
-
-      super.draw(canvas);
-    }
-  }
-
-  private static class InsetShadowDrawable extends Drawable {
-    private static final int LEFT_TO_RIGHT = 0;
-    private static final int TOP_TO_BOTTOM = 1;
-    private static final int RIGHT_TO_LEFT = 2;
-    private static final int BOTTOM_TO_TOP = 3;
-
-    private float blurRadius;
-    private int shadowColor;
-
-    private float[] radii;
-
-    private float width, height;
-
-    private float shadowXSize, shadowYSize;
-
-    private Shader[] shades = new Shader[4];
-    private Path[] paths = new Path[4];
-
-    private Paint paint;
-
-    private InsetShadowDrawable(int viewWidth, int viewHeight, float dx, float dy, float blurRadius, float spread, int shadowColor, float[] radii) {
-      this.blurRadius = blurRadius;
-      this.shadowColor = shadowColor;
-
-      this.width = viewWidth + 2 * dx;
-      this.height = viewHeight + 2 * dy;
-
-      this.shadowXSize = dx + spread;
-      this.shadowYSize = dy + spread;
-
-      this.radii = radii;
-
-      setBounds(0, 0, viewWidth, viewHeight);
-      prepare();
-    }
-
-    private void prepare() {
-      /*
-       *  A +++++++++++++++++++++++++ B
-       *  +  E ------------------- F  +
-       *  +  |                     |  +
-       *  +  |                     |  +
-       *  +  |                     |  +
-       *  +  H ------------------- G  +
-       *  D +++++++++++++++++++++++++ C
-       */
-
-      PointF a = new PointF(0, 0);
-      PointF b = new PointF(width, 0);
-      PointF c = new PointF(b.x, height);
-      PointF d = new PointF(a.x, c.y);
-
-      PointF e = new PointF(shadowXSize, shadowYSize);
-      PointF f = new PointF(b.x - shadowXSize, e.y);
-      PointF g = new PointF(f.x, c.y - shadowYSize);
-      PointF h = new PointF(e.x, g.y);
-
-      Shader ltr = new LinearGradient(e.x - blurRadius, e.y, e.x, e.y, shadowColor, Color.TRANSPARENT, Shader.TileMode.CLAMP);
-      Shader ttb = new LinearGradient(e.x, e.y - blurRadius, e.x, e.y, shadowColor, Color.TRANSPARENT, Shader.TileMode.CLAMP);
-      Shader rtl = new LinearGradient(g.x + blurRadius, g.y, g.x, g.y, shadowColor, Color.TRANSPARENT, Shader.TileMode.CLAMP);
-      Shader btt = new LinearGradient(g.x, g.y + blurRadius, g.x, g.y, shadowColor, Color.TRANSPARENT, Shader.TileMode.CLAMP);
-
-      shades[LEFT_TO_RIGHT] = ltr;
-      shades[TOP_TO_BOTTOM] = ttb;
-      shades[RIGHT_TO_LEFT] = rtl;
-      shades[BOTTOM_TO_TOP] = btt;
-
-      Path ltrPath = new Path();
-      ltrPath.moveTo(a.x, a.y);
-      ltrPath.lineTo(e.x, e.y);
-      ltrPath.lineTo(h.x, h.y);
-      ltrPath.lineTo(d.x, d.y);
-      ltrPath.close();
-
-      Path ttbPath = new Path();
-      ttbPath.moveTo(a.x, a.y);
-      ttbPath.lineTo(b.x, b.y);
-      ttbPath.lineTo(f.x, f.y);
-      ttbPath.lineTo(e.x, e.y);
-      ttbPath.close();
-
-      Path rtlPath = new Path();
-      rtlPath.moveTo(b.x, b.y);
-      rtlPath.lineTo(c.x, c.y);
-      rtlPath.lineTo(g.x, g.y);
-      rtlPath.lineTo(f.x, f.y);
-      rtlPath.close();
-
-      Path bttPath = new Path();
-      bttPath.moveTo(d.x, d.y);
-      bttPath.lineTo(c.x, c.y);
-      bttPath.lineTo(g.x, g.y);
-      bttPath.lineTo(h.x, h.y);
-      bttPath.close();
-
-      paths[LEFT_TO_RIGHT] = ltrPath;
-      paths[TOP_TO_BOTTOM] = ttbPath;
-      paths[RIGHT_TO_LEFT] = rtlPath;
-      paths[BOTTOM_TO_TOP] = bttPath;
-
-      paint = new Paint();
-      paint.setAntiAlias(true);
-      paint.setStyle(Paint.Style.FILL);
-      paint.setColor(shadowColor);
-    }
-
-    @Override
-    public void draw(Canvas canvas) {
-      Rect bounds = canvas.getClipBounds();
-      Path border = new Path();
-      RectF rectF = new RectF(bounds);
-      border.addRoundRect(rectF, radii, Path.Direction.CCW);
-      canvas.clipPath(border);
-      //TODO: we need clip border-width too
-
-      // translate the canvas to the right place and then draw the inner shadow
-      canvas.translate(bounds.left, bounds.top);
-
-      for (int i = 0; i < 4; i++) {
-        Shader shader = shades[i];
-        Path path = paths[i];
-        paint.setShader(shader);
-        canvas.drawPath(path, paint);
-      }
-    }
-
-    @Override
-    public void setAlpha(@IntRange(from = 0, to = 255) int alpha) {
-
-    }
-
-    @Override
-    public void setColorFilter(@Nullable ColorFilter colorFilter) {
-
-    }
-
-    @Override
-    public int getOpacity() {
-      return PixelFormat.OPAQUE;
-    }
-  }
-
-  public static class BoxShadowOptions {
-    private List<IParser> optionParamParsers;
-    private int viewport = 750;
-
-    public float hShadow;
-    public float vShadow;
-    public float blur = 0f;
-    public float spread = 0f;
-    public float[] radii = new float[]{0, 0, 0, 0, 0, 0, 0, 0};
-    public int color = Color.BLACK;
-    public boolean isInset = false;
-
-    public int viewWidth = 0;
-    public int viewHeight = 0;
-    public PointF topLeft = null;
-
-    private BoxShadowOptions(int vp) {
-      if (viewport != 0) {
-        this.viewport = vp;
-      }
-      optionParamParsers = new ArrayList<>();
-
-      IParser spreadParser = new IParser() {
-        @Override
-        public void parse(String param) {
-          if (!TextUtils.isEmpty(param)) {
-            float px = WXUtils.getFloat(param, 0f);
-            spread = WXViewUtils.getRealSubPxByWidth(px, viewport);
-            WXLogUtils.w(TAG, "Experimental box-shadow attribute: spread");
-          }
-        }
-      };
-
-      IParser blurParser = new IParser() {
-        @Override
-        public void parse(String param) {
-          if (!TextUtils.isEmpty(param)) {
-            float px = WXUtils.getFloat(param, 0f);
-            blur = WXViewUtils.getRealSubPxByWidth(px, viewport);
-          }
-        }
-      };
-
-      optionParamParsers.add(blurParser);
-      optionParamParsers.add(spreadParser);
-    }
-
-    public BoxShadowOptions scale(float scale) {
-      if (scale > 0f && scale <= 1f) {
-        BoxShadowOptions scaledOptions = new BoxShadowOptions(viewport);
-        scaledOptions.hShadow = hShadow * scale;
-        scaledOptions.vShadow = vShadow * scale;
-        scaledOptions.blur = blur * scale;
-        scaledOptions.spread = spread * scale;
-        for (int i = 0; i < radii.length ; i++) {
-          scaledOptions.radii[i] = radii[i] * scale;
-        }
-        scaledOptions.viewHeight = (int) (viewHeight * scale);
-        scaledOptions.viewWidth = (int) (viewWidth * scale);
-
-        if (topLeft != null) {
-          scaledOptions.topLeft = new PointF();
-          scaledOptions.topLeft.x = topLeft.x * scale;
-          scaledOptions.topLeft.y = topLeft.y * scale;
-        }
-
-        scaledOptions.color = color;
-        scaledOptions.isInset = isInset;
-        WXLogUtils.d(TAG, "Scaled BoxShadowOptions: [" + scale + "] " + scaledOptions);
-        return scaledOptions;
-      }
-      return null;
-    }
-
-    public Rect getTargetCanvasRect() {
-      int canvasWidth = viewWidth + 2 * (int) (blur + spread + Math.abs(hShadow));
-      int canvasHeight = viewHeight + 2 * (int) (blur + spread + Math.abs(vShadow));
-      return new Rect(0, 0, canvasWidth, canvasHeight);
-    }
-
-    @Override
-    public String toString() {
-
-      String r = "[" + radii[0] + "," + radii[2] + "," + radii[4] + "," + radii[6] + "]";
-
-      final StringBuffer sb = new StringBuffer("BoxShadowOptions{");
-      sb.append("h-shadow=").append(hShadow);
-      sb.append(", v-shadow=").append(vShadow);
-      sb.append(", blur=").append(blur);
-      sb.append(", spread=").append(spread);
-      sb.append(", corner-radius=").append(r);
-      sb.append(", color=#").append(Integer.toHexString(color));
-      sb.append(", inset=").append(isInset);
-      sb.append('}');
-      return sb.toString();
-    }
-
-    private interface IParser {
-      void parse(String param);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/FontDO.java b/android/sdk/src/main/java/com/taobao/weex/utils/FontDO.java
deleted file mode 100644
index a79ade0..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/FontDO.java
+++ /dev/null
@@ -1,185 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.graphics.Typeface;
-import android.net.Uri;
-import android.text.TextUtils;
-import android.util.Base64;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.adapter.URIAdapter;
-import com.taobao.weex.common.Constants;
-import java.io.File;
-
-public class FontDO {
-  private final String mFontFamilyName;
-  private String mUrl = "";
-  private String mFilePath;
-  private int mType = TYPE_NETWORK;
-  private Typeface mTypeface;
-  private int mState = STATE_INVALID;
-
-  public final static int STATE_INVALID = -1;
-  public final static int STATE_INIT = 0;
-  public final static int STATE_LOADING = 1;
-  public final static int STATE_SUCCESS = 2;
-  public final static int STATE_FAILED = 3;
-
-  public final static int TYPE_UNKNOWN = 0;
-  public final static int TYPE_NETWORK = 1;
-  public final static int TYPE_FILE = 2;
-  public final static int TYPE_LOCAL = 3;
-  public final static int TYPE_NATIVE = 4;
-  public final static int TYPE_BASE64 = 5;
-
-
-  public FontDO (String fontFamilyName, String src, WXSDKInstance instance) {
-    this.mFontFamilyName = fontFamilyName;
-    parseSrc(src,instance);
-  }
-
-  public FontDO (String fontFamilyName, Typeface typeface) {
-    this.mFontFamilyName = fontFamilyName;
-    this.mTypeface = typeface;
-    this.mType = TYPE_NATIVE;
-    this.mState = STATE_SUCCESS;
-  }
-
-  public String getFontFamilyName() {
-    return mFontFamilyName;
-  }
-
-  private void parseSrc(String src, WXSDKInstance instance) {
-    src = (src != null )? src.trim() : "";
-
-    if (instance != null) {
-      if (instance.getCustomFontNetworkHandler() != null) {
-        String localUrl = instance.getCustomFontNetworkHandler().fetchLocal(src);
-        if (!TextUtils.isEmpty(localUrl)) {
-          src = localUrl;
-        }
-      }
-    }
-
-    if (src.isEmpty()) {
-      mState = STATE_INVALID;
-      WXLogUtils.e("TypefaceUtil", "font src is empty.");
-      return;
-    }
-
-    if (src.matches("^url\\((('.*')|(\".*\"))\\)$")) {
-      String url = src.substring(5, src.length() - 2);
-      Uri uri = Uri.parse(url);
-      if( instance != null){
-        uri = instance.rewriteUri(uri,URIAdapter.FONT);
-      }
-      mUrl = uri.toString();
-      try {
-        String scheme = uri.getScheme();
-        if (Constants.Scheme.HTTP.equals(scheme) ||
-                Constants.Scheme.HTTPS.equals(scheme)) {
-          mType = TYPE_NETWORK;
-        } else if (Constants.Scheme.FILE.equals(scheme)) {
-          mType = TYPE_FILE;
-            /**
-             * eg: file://name/A/B.ttf
-             * getPath() = "A/B.ttf",but the real absolute path is "/name/A/B.ttf"
-             * so use getEncodedSchemeSpecificPart() to replaced = "//name/A/B.ttf"
-             */
-            mUrl = uri.getEncodedSchemeSpecificPart();
-        } else if (Constants.Scheme.LOCAL.equals(scheme)){
-          mType = TYPE_LOCAL;
-        } else if (Constants.Scheme.DATA.equals(scheme)) {
-          long start = System.currentTimeMillis();
-          String[] data = mUrl.split(",");
-          if (data != null && data.length == 2) {
-            String identify = data[0];
-            if (!TextUtils.isEmpty(identify) && identify.endsWith("base64")) {
-              //Do not check mime type and charset for now
-              String base64Data = data[1];
-              if (!TextUtils.isEmpty(base64Data)) {
-                String md5 = WXFileUtils.md5(base64Data);
-                File cacheDir = new File(WXEnvironment.getApplication().getCacheDir(),
-                    "font-family");
-                if (!cacheDir.exists()) {
-                  cacheDir.mkdirs();
-                }
-                File tmpFile = new File(cacheDir, md5);
-                if(!tmpFile.exists()){
-                  tmpFile.createNewFile();
-                  WXFileUtils.saveFile(tmpFile.getPath(), Base64.decode(base64Data, Base64.DEFAULT), WXEnvironment.getApplication());
-                }
-                mUrl = tmpFile.getPath();
-                mType = TYPE_BASE64;
-                WXLogUtils.d("TypefaceUtil", "Parse base64 font cost " + (System.currentTimeMillis() - start) + " ms");
-              }
-            }
-          }
-        } else {
-          WXLogUtils.e("TypefaceUtil", "Unknown scheme for font url: " + mUrl);
-          mType = TYPE_UNKNOWN;
-        }
-        mState = STATE_INIT;
-      } catch (Exception e) {
-        mType = STATE_INVALID;
-        WXLogUtils.e("TypefaceUtil", "URI.create(mUrl) failed mUrl: " + mUrl+ "\n"+ WXLogUtils.getStackTrace(e));
-      }
-    } else {
-      mUrl = src;
-      mState = STATE_INVALID;
-    }
-
-    if(WXEnvironment.isApkDebugable()) {
-      WXLogUtils.d("TypefaceUtil", "src:" + src + ", mUrl:" + mUrl + ", mType:" + mType);
-    }
-  }
-
-  public String getUrl() {
-    return mUrl;
-  }
-
-  public int getType() {
-    return mType;
-  }
-
-  public Typeface getTypeface() {
-    return mTypeface;
-  }
-
-  public void setTypeface(Typeface typeface) {
-    this.mTypeface = typeface;
-  }
-
-  public int getState() {
-    return mState;
-  }
-
-  public void setState(int state) {
-    this.mState = state;
-  }
-
-  public String getFilePath() {
-    return mFilePath;
-  }
-
-  public void setFilePath(String mFilePath) {
-    this.mFilePath = mFilePath;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/FunctionParser.java b/android/sdk/src/main/java/com/taobao/weex/utils/FunctionParser.java
deleted file mode 100644
index 93ace90..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/FunctionParser.java
+++ /dev/null
@@ -1,240 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.support.annotation.NonNull;
-
-import java.util.LinkedHashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Parser for function like "rotate(30 ) transform(50 , 20)".
- * This class will translate the raw string presentation of a group of function(s) to give type
- * according to the {@link com.taobao.weex.utils.FunctionParser.Mapper}
- */
-public class FunctionParser<K, V> {
-
-  public static final char SPACE = ' ';
-
-  private Mapper<K, V> mapper;
-  private Lexer lexer;
-
-  /**
-   * Construct a function parser
-   * @param source the raw string representation of a group of function(s)
-   * @param mapper the mapping rule between string and corresponding type of object.
-   */
-  public FunctionParser(@NonNull String source, @NonNull Mapper<K, V> mapper) {
-    this.lexer = new Lexer(source);
-    this.mapper = mapper;
-  }
-
-  /**
-   * Start to parse the raw string. The result will be stored in a sorted map where the order
-   * is defined by the function order in the raw string.
-   * @return
-   */
-  public LinkedHashMap<K, V> parse() {
-    lexer.moveOn();
-    return definition();
-  }
-
-  private LinkedHashMap<K, V> definition() {
-    LinkedHashMap<K, V> result = new LinkedHashMap<>();
-    do {
-      result.putAll(function());
-    } while (lexer.getCurrentToken() == Token.FUNC_NAME);
-    return result;
-  }
-
-  private Map<K, V> function() {
-    List<String> list = new LinkedList<>();
-    String functionName = match(Token.FUNC_NAME);
-    match(Token.LEFT_PARENT);
-    list.add(match(Token.PARAM_VALUE));
-    while (lexer.getCurrentToken() == Token.COMMA) {
-      match(Token.COMMA);
-      list.add(match(Token.PARAM_VALUE));
-    }
-    match(Token.RIGHT_PARENT);
-    return mapper.map(functionName, list);
-  }
-
-  private String match(Token token) {
-    try {
-      if (token == lexer.getCurrentToken()) {
-        String value = lexer.getCurrentTokenValue();
-        lexer.moveOn();
-        return value;
-      }
-    } catch (Exception e) {
-      WXLogUtils.e(token + "Token doesn't match" + lexer.source);
-    }
-    return "";
-  }
-
-  private enum Token {
-    FUNC_NAME, PARAM_VALUE, LEFT_PARENT, RIGHT_PARENT, COMMA
-  }
-
-  public interface Mapper<K, V> {
-
-    /**
-     * Map one function to a specified type of object
-     * @param functionName the name of the raw function.
-     * @param raw the list of parameter of the raw function
-     * @return the expected mapping relationship, where the key in the map is the same as the
-     * key in the return value of {{@link #parse()}},
-     * and the value in the map is the type of object that expected by user.
-     */
-    Map<K, V> map(String functionName, List<String> raw);
-  }
-
-  private static class WXInterpretationException extends RuntimeException {
-
-    private WXInterpretationException(String msg) {
-      super(msg);
-    }
-  }
-
-  /**
-   * Lexer for the parser. For now,  digit, alphabet, '(', ')', '.', ',', '+', '-' and '%' is
-   * valid character, and '(', ')', ',', parameter value and function name is valid token.
-   * Parameter value is defined as "(?i)[\+-]?[0-9]+(\.[0-9]+)?(%||deg||px)?" while function
-   * name is defined as "[a-zA-Z]+".
-   *
-   * The Lexer can also be expressed using the following EBNF format.
-   * <ul>
-   *   <li>definition = {function};</li>
-   *   <li>function = name, "(", value, { ",", value } , ")";</li>
-   *   <li>name = character, {character};</li>
-   *   <li>value = identifier, {identifier};</li>
-   *   <li>identifier = character | "." | "%" | "+" | "-";</li>
-   *   <li>character = digit | letter;</li>
-   *   <li>digit =  "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9" ;</li>
-   *   <li>letter = "A" | "B" | "C" | "D" | "E" | "F" | "G" | "H" | "I" | "J" | "K" | "L" | "M" |
-   *   "N" | "O" | "P" | "Q" | "R" | "S" | "T" | "U" | "V" | "W" | "X" | "Y" | "Z" | "a" | "b" |
-   *   "c" | "d" | "e" | "f" | "g" | "h" | "i" | "j" | "k" | "l" | "m" | "n" | "o" | "p" | "q" |
-   *   "r" | "s" | "t" | "u" | "v" | "w" | "x" | "y" | "z" ;</li>
-   * </ul>
-   */
-  private static class Lexer {
-
-    private static final String LEFT_PARENT = "(";
-    private static final String RIGHT_PARENT = ")";
-    private static final String COMMA = ",";
-    private static final char A_LOWER = 'a';
-    private static final char Z_LOWER = 'z';
-    private static final char A_UPPER = 'A';
-    private static final char Z_UPPER = 'Z';
-    private static final char ZERO = '0';
-    private static final char NINE = '9';
-    private static final char DOT = '.';
-    private static final char MINUS = '-';
-    private static final char PLUS = '+';
-    private String source;
-    private Token current;
-    private String value;
-    private int pointer = 0;
-
-    private Lexer(String source) {
-      this.source = source;
-    }
-
-    private Token getCurrentToken() {
-      return current;
-    }
-
-    private String getCurrentTokenValue() {
-      return value;
-    }
-
-    private boolean moveOn() {
-      int start = pointer;
-      char curChar;
-      while (pointer < source.length()) {
-        curChar = source.charAt(pointer);
-        if (curChar == SPACE) {
-          if (start == pointer++) {
-            start++;
-          } else {
-            break;
-          }
-        } else if (isCharacterOrDigit(curChar) || curChar == DOT
-                || curChar == WXUtils.PERCENT || curChar == MINUS || curChar == PLUS) {
-          pointer++;
-        } else {
-          if (start == pointer) {
-            pointer++;
-          }
-          break;
-        }
-      }
-      if (start != pointer) {
-        String symbol = source.substring(start, pointer);
-        moveOn(symbol);
-        return true;
-      } else {
-        current = null;
-        value = null;
-        return false;
-      }
-    }
-
-    private void moveOn(String token) {
-      if (LEFT_PARENT.equals(token)) {
-        current = Token.LEFT_PARENT;
-        value = LEFT_PARENT;
-      } else if (RIGHT_PARENT.equals(token)) {
-        current = Token.RIGHT_PARENT;
-        value = RIGHT_PARENT;
-      } else if (COMMA.equals(token)) {
-        current = Token.COMMA;
-        value = COMMA;
-      } else if (isFuncName(token)) {
-        current = Token.FUNC_NAME;
-        value = token;
-      } else {
-        current = Token.PARAM_VALUE;
-        value = token;
-      }
-    }
-
-    private boolean isFuncName(CharSequence funcName) {
-      char letter;
-      for (int i = 0; i < funcName.length(); i++) {
-        letter = funcName.charAt(i);
-        if (!((A_LOWER <= letter && letter <= Z_LOWER) ||
-                (A_UPPER <= letter && letter <= Z_UPPER) ||
-                letter == MINUS)) {
-          return false;
-        }
-      }
-      return true;
-    }
-
-    private boolean isCharacterOrDigit(char letter) {
-      return (ZERO <= letter && letter <= NINE) || (A_LOWER <= letter && letter <= Z_LOWER) ||
-              (A_UPPER <= letter && letter <= Z_UPPER);
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/ImageDrawable.java b/android/sdk/src/main/java/com/taobao/weex/utils/ImageDrawable.java
deleted file mode 100644
index f6f1010..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/ImageDrawable.java
+++ /dev/null
@@ -1,155 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.utils;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapShader;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.RectF;
-import android.graphics.Shader;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.PaintDrawable;
-import android.graphics.drawable.shapes.Shape;
-import android.os.Build;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.widget.ImageView;
-
-public class ImageDrawable extends PaintDrawable {
-
-  public static Drawable createImageDrawable(@Nullable Drawable original,
-                                             @NonNull ImageView.ScaleType scaleType,
-                                             @Nullable float[] borderRadius,
-                                             int vWidth,
-                                             int vHeight,
-                                             boolean gif) {
-    Bitmap bm;
-    if (!gif && vWidth > 0 && vHeight > 0) {
-      if (original instanceof BitmapDrawable &&
-              (bm = ((BitmapDrawable) original).getBitmap()) != null) {
-        ImageDrawable imageDrawable;
-        imageDrawable = new ImageDrawable();
-        // fix android 9 image antialiasing
-        imageDrawable.getPaint().setFilterBitmap(true);
-        imageDrawable.bitmapWidth = bm.getWidth();
-        imageDrawable.bitmapHeight = bm.getHeight();
-        BitmapShader bitmapShader = new BitmapShader(bm, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
-        updateShaderAndSize(scaleType, vWidth, vHeight, imageDrawable, bitmapShader);
-        imageDrawable.getPaint().setShader(bitmapShader);
-        return imageDrawable;
-      } else if (original instanceof ImageDrawable) {
-        ImageDrawable imageDrawable = (ImageDrawable) original;
-        if (imageDrawable.getPaint() != null &&
-                imageDrawable.getPaint().getShader() instanceof BitmapShader) {
-          BitmapShader bitmapShader = (BitmapShader) imageDrawable.getPaint().getShader();
-          updateShaderAndSize(scaleType, vWidth, vHeight, imageDrawable, bitmapShader);
-          return imageDrawable;
-        }
-      }
-    }
-    return original;
-  }
-
-  private static void updateShaderAndSize(@NonNull ImageView.ScaleType scaleType, int vWidth, int vHeight, ImageDrawable imageDrawable, BitmapShader bitmapShader) {
-    Matrix matrix = createShaderMatrix(scaleType, vWidth, vHeight,
-            imageDrawable.bitmapWidth,
-            imageDrawable.bitmapHeight);
-    int intrinsicWidth = vWidth, intrinsicHeight = vHeight;
-    if (scaleType == ImageView.ScaleType.FIT_CENTER) {
-      RectF bitmapRect = new RectF(0, 0, imageDrawable.bitmapWidth, imageDrawable.bitmapHeight), contentRect = new RectF();
-      matrix.mapRect(contentRect, bitmapRect);
-      intrinsicWidth = (int) contentRect.width();
-      intrinsicHeight = (int) contentRect.height();
-      matrix = createShaderMatrix(scaleType, intrinsicWidth, intrinsicHeight, imageDrawable
-              .bitmapWidth, imageDrawable.bitmapHeight);
-    }
-    imageDrawable.setIntrinsicWidth(intrinsicWidth);
-    imageDrawable.setIntrinsicHeight(intrinsicHeight);
-    bitmapShader.setLocalMatrix(matrix);
-  }
-
-  @NonNull
-  private static Matrix createShaderMatrix(@NonNull ImageView.ScaleType scaleType, int vWidth,
-                                           int vHeight, int bmWidth, int bmHeight) {
-    float scale, translateX = 0, translateY = 0;
-
-    if (bmWidth * vHeight > bmHeight * vWidth) {
-      scale = vHeight / (float) bmHeight;
-      translateX = (vWidth - bmWidth * scale) * 0.5f;
-    } else {
-      scale = vWidth / (float) bmWidth;
-      translateY = (vHeight - bmHeight * scale) * 0.5f;
-    }
-
-    Matrix mMatrix = new Matrix();
-    if (scaleType == ImageView.ScaleType.FIT_XY) {
-      mMatrix.setScale(vWidth / (float) bmWidth, vHeight / (float) bmHeight);
-    } else if (scaleType == ImageView.ScaleType.FIT_CENTER) {
-      RectF src = new RectF(0, 0, bmWidth, bmHeight);
-      RectF dist = new RectF(0, 0, vWidth, vHeight);
-      mMatrix.setRectToRect(src, dist, Matrix.ScaleToFit.CENTER);
-    } else if (scaleType == ImageView.ScaleType.CENTER_CROP) {
-      mMatrix.setScale(scale, scale);
-      mMatrix.postTranslate(translateX + 0.5f, translateY + 0.5f);
-    }
-    return mMatrix;
-  }
-
-  private float[] radii;
-  private int bitmapHeight;
-  private int bitmapWidth;
-
-  private ImageDrawable() {
-
-  }
-
-  @Override
-  public void setCornerRadii(float[] radii) {
-    this.radii = radii;
-    super.setCornerRadii(radii);
-  }
-
-  @Override
-  protected void onDraw(Shape shape, Canvas canvas, Paint paint) {
-    if (Build.VERSION.SDK_INT == Build.VERSION_CODES.LOLLIPOP) {
-      // fix api 21 PaintDrawable crash
-      paint.setAntiAlias(false);
-    }
-    super.onDraw(shape, canvas, paint);
-  }
-
-  public
-  @Nullable
-  float[] getCornerRadii() {
-    return this.radii;
-  }
-
-  public int getBitmapHeight() {
-    return bitmapHeight;
-  }
-
-  public int getBitmapWidth() {
-    return bitmapWidth;
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/ImgURIUtil.java b/android/sdk/src/main/java/com/taobao/weex/utils/ImgURIUtil.java
deleted file mode 100644
index db8a538..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/ImgURIUtil.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.utils;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.drawable.Drawable;
-import android.net.Uri;
-import android.support.v4.content.res.ResourcesCompat;
-
-import java.util.List;
-
-public class ImgURIUtil {
-
-  public static Drawable getDrawableFromLoaclSrc(Context context, Uri rewrited) {
-    Resources resources = context.getResources();
-    List<String> segments = rewrited.getPathSegments();
-    if (segments.size() != 1) {
-      WXLogUtils.e("Local src format is invalid.");
-      return null;
-    }
-    int id = resources.getIdentifier(segments.get(0), "drawable", context.getPackageName());
-    return id == 0 ? null : ResourcesCompat.getDrawable(resources, id, null);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/LogLevel.java b/android/sdk/src/main/java/com/taobao/weex/utils/LogLevel.java
deleted file mode 100644
index a590820..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/LogLevel.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.util.Log;
-
-/**
- * Created by lixinke on 16/5/11.
- */
-public enum LogLevel {
-  OFF("off",8, Log.ASSERT),
-  WTF("wtf", 7, Log.ASSERT),
-  TLOG("tlog",6,Log.ERROR), //Add For Son Process
-  ERROR("error", 5, Log.ERROR),
-  WARN("warn", 4, Log.WARN),
-  INFO("info", 3, Log.INFO),
-  DEBUG("debug", 2, Log.DEBUG),
-  VERBOSE("verbose", 1, Log.VERBOSE),
-  ALL("all", 0, Log.VERBOSE),;
-  String name;
-  int value;
-  int priority;
-
-  LogLevel(String name, int value,int priority) {
-    this.name = name;
-    this.value = value;
-    this.priority = priority;
-  }
-  public String getName(){
-    return name;
-  }
-  public int getValue(){
-    return value;
-  }
-  public int getPriority(){
-    return priority;
-  }
-  public int compare(LogLevel level){
-    return value-level.value;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/OsVersion.java b/android/sdk/src/main/java/com/taobao/weex/utils/OsVersion.java
deleted file mode 100644
index 7c53095..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/OsVersion.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-/**
- * Android OS version utilities.
- */
-public class OsVersion {
-  private static boolean sIsAtLeastJB_MR2;
-
-
-  static {
-    final int v = getApiVersion();
-    sIsAtLeastJB_MR2 = v >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR2;
-  }
-
-  /**
-   * @return True if the version of Android that we're running on is at
-   * least Jelly Bean MR2(API level 18).
-   */
-  public static boolean isAtLeastJB_MR2() {
-    return sIsAtLeastJB_MR2;
-  }
-
-  /**
-   * @return The Android API version of the running OS.
-   */
-  public static int getApiVersion() {
-    return android.os.Build.VERSION.SDK_INT;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/SingleFunctionParser.java b/android/sdk/src/main/java/com/taobao/weex/utils/SingleFunctionParser.java
deleted file mode 100644
index c67b323..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/SingleFunctionParser.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.utils;
-
-import android.support.annotation.NonNull;
-
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Map;
-
-public class SingleFunctionParser<V> extends FunctionParser<String, List<V>> {
-
-  public interface FlatMapper<V> {
-
-    V map(String raw);
-  }
-
-  public interface NonUniformMapper<V>{
-    List<V> map(List<String> raw);
-  }
-
-  /**
-   * Construct a function parser for uniform parameters.
-   * @param source the raw string representation of a group of function(s)
-   * @param mapper the mapping rule between string and corresponding type of object.
-   */
-  public SingleFunctionParser(@NonNull String source, @NonNull final FlatMapper<V> mapper) {
-    super(source, new Mapper<String, List<V>>() {
-      @Override
-      public Map<String, List<V>> map(String functionName, List<String> raw) {
-        Map<String, List<V>> map = new HashMap<String, List<V>>();
-        List<V> list = new LinkedList<V>();
-        for (String item : raw) {
-          list.add(mapper.map(item));
-        }
-        map.put(functionName, list);
-        return map;
-      }
-    });
-  }
-
-  /**
-   * Construct a function parser for non-uniform parameters.
-   * @param source the raw string representation of a group of function(s)
-   * @param mapper the mapping rule between string and corresponding type of object.
-   */
-  public SingleFunctionParser(@NonNull String source, @NonNull final NonUniformMapper<V> mapper) {
-    super(source, new Mapper<String, List<V>>() {
-      @Override
-      public Map<String, List<V>> map(String functionName, List<String> raw) {
-        Map<String, List<V>> map = new HashMap<String, List<V>>();
-        map.put(functionName, mapper.map(raw));
-        return map;
-      }
-    });
-  }
-
-  public List<V> parse(String functionName) {
-    Map<String, List<V>> map = parse();
-    if(map.containsKey(functionName)){
-      return map.get(functionName);
-    }
-    return null;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/StaticLayoutProxy.java b/android/sdk/src/main/java/com/taobao/weex/utils/StaticLayoutProxy.java
deleted file mode 100644
index ac1d660..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/StaticLayoutProxy.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.text.Layout;
-import android.text.StaticLayout;
-import android.text.TextDirectionHeuristic;
-import android.text.TextDirectionHeuristics;
-import android.text.TextPaint;
-
-import java.lang.reflect.Constructor;
-
-/**
- * Created by moxun on 2017/9/26.
- */
-
-public class StaticLayoutProxy {
-  private static Constructor<StaticLayout> layoutConstructor;
-  public static StaticLayout create(CharSequence source, TextPaint paint,
-                                    int width,
-                                    Layout.Alignment align, float spacingmult, float spacingadd,
-                                    boolean includepad, boolean forceRtl) {
-    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR2 && forceRtl) {
-      TextDirectionHeuristic textDir = TextDirectionHeuristics.RTL;
-      StaticLayout rtlLayout =  createInternal(source, paint, width, align, textDir, spacingmult, spacingadd, includepad);
-      if (rtlLayout != null) {
-        return rtlLayout;
-      } else {
-        return new StaticLayout(source, paint, width, align, spacingmult, spacingadd, includepad);
-      }
-    }
-    return new StaticLayout(source, paint, width, align, spacingmult, spacingadd, includepad);
-  }
-
-  private static StaticLayout createInternal(CharSequence source, TextPaint paint,
-                                             int width, Layout.Alignment align, TextDirectionHeuristic textDir,
-                                             float spacingmult, float spacingadd,
-                                             boolean includepad) {
-    if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.JELLY_BEAN_MR2) {
-      return null;
-    } else {
-      try {
-        if (layoutConstructor == null) {
-          Class<StaticLayout> clazz = StaticLayout.class;
-          Constructor<StaticLayout> constructor = clazz.getConstructor(CharSequence.class, TextPaint.class,
-                  int.class, Layout.Alignment.class, TextDirectionHeuristic.class,
-                  float.class, float.class,
-                  boolean.class);
-          layoutConstructor = constructor;
-        }
-        if (layoutConstructor != null) {
-          return layoutConstructor.newInstance(source, paint, width,
-                  align, textDir, spacingmult, spacingadd, includepad);
-        }
-
-      } catch (Throwable e) {
-        e.printStackTrace();
-      }
-    }
-    return null;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/Trace.java b/android/sdk/src/main/java/com/taobao/weex/utils/Trace.java
deleted file mode 100644
index cfe307e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/Trace.java
+++ /dev/null
@@ -1,113 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.annotation.TargetApi;
-import android.os.Build;
-
-/**
- * Hepler class for systrace.
- *
- * Note that this will run only on JBMR2 or later.
- *
- * Trace will be enabled in debug production and be disabled in release
- * production, see build.gradle.
- * If you want to enable it in release, just set sEnabled to true.
- */
-public class Trace {
-  private static final String TAG = "Weex_Trace";
-  private abstract static class AbstractTrace {
-    abstract void beginSection(String sectionName);
-    abstract void endSection();
-  }
-
-  private static final AbstractTrace sTrace;
-  private static final boolean sEnabled;
-
-  // Pick the correct trace class to handle tracing.
-  static {
-    // If you want to enable it in release, just set sEnabled to true.
-    // If you turn sEnabled on, weex would trace logs on Java side
-    // as well as on V8 side, please take care of turning sEnabled on
-    // to avoid performance impact.
-    // FIXME: weex sdk may use another build files to build and cause
-    // compiling errors if these build files don't contain any
-    // ENABLE_TRACE, just comment out the line below.
-    //sEnabled = com.taobao.weappplus_sdk.BuildConfig.ENABLE_TRACE;
-    sEnabled = false;
-
-    if (sEnabled == true && OsVersion.isAtLeastJB_MR2()) {
-      sTrace = new TraceJBMR2();
-    } else {
-      sTrace = new TraceDummy();
-    }
-  }
-
-  public static final boolean getTraceEnabled() {
-    return sEnabled;
-  }
-
-  /**
-   * Writes a trace message to indicate that a given section of code has begun.
-   * This call must be followed by a corresponding call to {@link #endSection()}
-   * on the same thread.
-   *
-   * <p class="note"> If sectionName contains '|', '\n' and '\0', these characters
-   * will be repaced with a space character.
-   *
-   * @param sectionName The name of code section to appear in the trace.
-   */
-  public static void beginSection(String sectionName) {
-    android.util.Log.i(TAG, "beginSection() " + sectionName);
-    sTrace.beginSection(sectionName);
-  }
-
-  /**
-   * Writes a trace message to indicate that a given section of code has ended.
-   * This call must be preceeded by a corresponding call to {@link #beginSection(String)}
-   * on the same thread.
-   */
-  public static void endSection() {
-    sTrace.endSection();
-    android.util.Log.i(TAG, "endSection()");
-  }
-
-  @TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR2)
-  private static final class TraceJBMR2 extends AbstractTrace {
-    @Override
-    void beginSection(String sectionName) {
-      android.os.Trace.beginSection(sectionName);
-    }
-
-    @Override
-    void endSection() {
-      android.os.Trace.endSection();
-    }
-  }
-
-  private static final class TraceDummy extends AbstractTrace {
-    @Override
-    void beginSection(String sectionName) {
-    }
-
-    @Override
-    void endSection() {
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/TypefaceUtil.java b/android/sdk/src/main/java/com/taobao/weex/utils/TypefaceUtil.java
deleted file mode 100644
index a6ad566..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/TypefaceUtil.java
+++ /dev/null
@@ -1,298 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.content.Intent;
-import android.graphics.Paint;
-import android.graphics.Typeface;
-import android.net.Uri;
-import android.support.v4.content.LocalBroadcastManager;
-import android.text.TextUtils;
-import android.util.Log;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.common.WXRequest;
-import com.taobao.weex.common.WXResponse;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.font.FontAdapter;
-
-import java.io.File;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-/**
- * Created by sospartan on 7/13/16.
- */
-public class TypefaceUtil {
-  public static final String FONT_CACHE_DIR_NAME = "font-family";
-  private final static String TAG = "TypefaceUtil";
-  private final static Map<String, FontDO> sCacheMap = new HashMap<>(); //Key: fontFamilyName
-
-  public static final String ACTION_TYPE_FACE_AVAILABLE = "type_face_available";
-
-  public static void putFontDO(FontDO fontDO) {
-    if (fontDO != null && !TextUtils.isEmpty(fontDO.getFontFamilyName())) {
-      sCacheMap.put(fontDO.getFontFamilyName(), fontDO);
-    }
-  }
-
-  public static void registerNativeFont(Map<String, Typeface> fonts) {
-    if (fonts != null && fonts.size() > 0) {
-      for (Map.Entry<String, Typeface> font : fonts.entrySet()) {
-        FontDO fontDO = new FontDO(font.getKey(), font.getValue());
-        putFontDO(fontDO);
-        if (WXEnvironment.isApkDebugable()){
-          WXLogUtils.d("TypefaceUtil", "register new typeface: " + font.getKey());
-        }
-      }
-    }
-  }
-
-  public static FontDO getFontDO(String fontFamilyName) {
-    return sCacheMap.get(fontFamilyName);
-  }
-
-  public static void removeFontDO(String fontFamilyName) {
-    sCacheMap.remove(fontFamilyName);
-  }
-
-  public static void applyFontStyle(Paint paint, int style, int weight, String family) {
-    int oldStyle;
-    Typeface typeface = paint.getTypeface();
-    if (typeface == null) {
-      oldStyle = 0;
-    } else {
-      oldStyle = typeface.getStyle();
-    }
-
-    int want = 0;
-    if ((weight == Typeface.BOLD)
-            || ((oldStyle & Typeface.BOLD) != 0 && weight == WXStyle.UNSET)) {
-      want |= Typeface.BOLD;
-    }
-
-    if ((style == Typeface.ITALIC)
-            || ((oldStyle & Typeface.ITALIC) != 0 && style == WXStyle.UNSET)) {
-      want |= Typeface.ITALIC;
-    }
-
-    if (family != null) {
-      typeface = getOrCreateTypeface(family, want);
-    }
-
-    if (typeface != null) {
-      paint.setTypeface(Typeface.create(typeface, want));
-    } else {
-      paint.setTypeface(Typeface.defaultFromStyle(want));
-    }
-  }
-
-  public static Typeface getOrCreateTypeface(String family, int style) {
-    FontDO fontDo = sCacheMap.get(family);
-    if (fontDo != null && fontDo.getTypeface() != null) {
-      return fontDo.getTypeface();
-    }
-
-    return Typeface.create(family, style);
-  }
-
-  private static void loadFromAsset(FontDO fontDo,String path){
-    try {
-      Typeface typeface = Typeface.createFromAsset(WXEnvironment.getApplication().getAssets(), path);
-      if (typeface != null) {
-        if(WXEnvironment.isApkDebugable()) {
-          WXLogUtils.d(TAG, "load asset file success");
-        }
-        fontDo.setState(FontDO.STATE_SUCCESS);
-        fontDo.setTypeface(typeface);
-      } else {
-        WXLogUtils.e(TAG, "Font asset file not found " + fontDo.getUrl());
-      }
-    } catch (Exception e) {
-      WXLogUtils.e(TAG, e.toString());
-    }
-  }
-
-  public static void loadTypeface(final FontDO fontDo, boolean notify) {
-    if (fontDo != null && fontDo.getTypeface() == null &&
-            (fontDo.getState() == FontDO.STATE_FAILED || fontDo.getState() == FontDO.STATE_INIT)) {
-      fontDo.setState(FontDO.STATE_LOADING);
-      if (fontDo.getType() == FontDO.TYPE_LOCAL) {
-        Uri uri = Uri.parse(fontDo.getUrl());
-        loadFromAsset(fontDo,uri.getPath().substring(1));//exclude slash
-      } else if (fontDo.getType() == FontDO.TYPE_NETWORK) {
-        final String url = fontDo.getUrl();
-        final String fontFamily = fontDo.getFontFamilyName();
-        final String fileName = WXFileUtils.md5(url);
-        //url.replace('/', '_').replace(':', '_');
-        File dir = new File(getFontCacheDir());
-        if(!dir.exists()){
-          dir.mkdirs();
-        }
-        final String fullPath =  dir.getAbsolutePath()+ File.separator +fileName;
-        if (!loadLocalFontFile(fullPath, fontFamily, false)) {
-          downloadFontByNetwork(url, fullPath, fontFamily);
-        }
-      } else if (fontDo.getType() == FontDO.TYPE_FILE || fontDo.getType() == FontDO.TYPE_BASE64) {
-        boolean result = loadLocalFontFile(fontDo.getUrl(), fontDo.getFontFamilyName(), false);
-        if (!result) {
-          fontDo.setState(FontDO.STATE_FAILED);
-        }
-      }
-      return;
-    }
-    if(notify){
-         notifyFontAvailable(false, fontDo);
-    }
-  }
-
-  private static void downloadFontByNetwork(final String url, final String fullPath, final String fontFamily) {
-    IWXHttpAdapter adapter = WXSDKManager.getInstance().getIWXHttpAdapter();
-    if (adapter == null) {
-      WXLogUtils.e(TAG, "downloadFontByNetwork() IWXHttpAdapter == null");
-      return;
-    }
-    WXRequest request = new WXRequest();
-    request.url = url;
-    request.method = "GET";
-    adapter.sendRequest(request, new IWXHttpAdapter.OnHttpListener() {
-      @Override
-      public void onHttpStart() {
-        if(WXEnvironment.isApkDebugable()) {
-          WXLogUtils.d(TAG, "downloadFontByNetwork begin url:" + url);
-        }
-      }
-
-      @Override
-      public void onHeadersReceived(int statusCode, Map<String, List<String>> headers) {
-
-      }
-
-      @Override
-      public void onHttpUploadProgress(int uploadProgress) {
-
-      }
-
-      @Override
-      public void onHttpResponseProgress(int loadedLength) {
-
-      }
-
-      @Override
-      public void onHttpFinish(WXResponse response) {
-        int statusCode = 0;
-        if (!TextUtils.isEmpty(response.statusCode)) {
-          try {
-            statusCode = Integer.parseInt(response.statusCode);
-          } catch (NumberFormatException e) {
-            statusCode = 0;
-            WXLogUtils.e(TAG, "IWXHttpAdapter onHttpFinish statusCode:" + response.statusCode);
-          }
-        }
-        boolean result;
-        if (statusCode >= 200 && statusCode <= 299 && response.originalData != null) {
-          result = WXFileUtils.saveFile(fullPath, response.originalData, WXEnvironment.getApplication());
-          if (result) {
-            result = loadLocalFontFile(fullPath, fontFamily, true);
-          } else {
-            if(WXEnvironment.isApkDebugable()) {
-              WXLogUtils.d(TAG, "downloadFontByNetwork() onHttpFinish success, but save file failed.");
-            }
-          }
-        } else {
-          result = false;
-        }
-
-        if (!result) {
-          FontDO fontDO = sCacheMap.get(fontFamily);
-          if (fontDO != null) {
-            fontDO.setState(FontDO.STATE_FAILED);
-          }
-        }
-      }
-    });
-  }
-
-  private static boolean loadLocalFontFile(final String path, final String fontFamily, boolean hasNetworkDowload) {
-    if (TextUtils.isEmpty(path) || TextUtils.isEmpty(fontFamily)) {
-      return false;
-    }
-    try {
-      File file = new File(path);
-      if (!file.exists()) {
-        return false;
-      }
-      Typeface typeface = Typeface.createFromFile(path);
-      if (typeface != null) {
-        final FontDO fontDo = sCacheMap.get(fontFamily);
-        if (fontDo != null) {
-          fontDo.setState(FontDO.STATE_SUCCESS);
-          fontDo.setTypeface(typeface);
-          fontDo.setFilePath(path);
-          if(WXEnvironment.isApkDebugable()) {
-            WXLogUtils.d(TAG, "load local font file success");
-          }
-
-          if(hasNetworkDowload) {
-            /**
-             * wxtext may be measured when font not load, when register broadcast receiver,
-             * this broadcast has been send, which cause textview not rendered right.
-             * delay broadcast ensure text will render right
-             * */
-            WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(new Runnable() {
-              @Override
-              public void run() {
-               notifyFontAvailable(true, fontDo);
-              }
-            }, 100);
-          }else{
-             notifyFontAvailable(true, fontDo);
-          }
-          return true;
-        }
-      } else {
-        WXLogUtils.e(TAG, "load local font file failed, can't create font.");
-      }
-    } catch (Exception e) {
-      WXLogUtils.e(TAG, e.toString());
-    }
-    return false;
-  }
-
-  private static void notifyFontAvailable(boolean sendBroadcast, FontDO fontDO){
-    if(sendBroadcast){
-      Intent intent = new Intent(ACTION_TYPE_FACE_AVAILABLE);
-      intent.putExtra("fontFamily", fontDO.getFontFamilyName());
-      intent.putExtra("filePath", fontDO.getFilePath());
-      intent.putExtra("fontUrl", fontDO.getUrl());
-      LocalBroadcastManager.getInstance(WXEnvironment.getApplication()).sendBroadcast(intent);
-    }
-    FontAdapter fontAdapter = WXSDKManager.getInstance().getFontAdapter();
-    if(fontAdapter != null){
-        fontAdapter.onFontLoad(fontDO.getFontFamilyName(), fontDO.getUrl(), fontDO.getFilePath());
-    }
-  }
-
-  private static String getFontCacheDir() {
-    return WXEnvironment.getApplication().getCacheDir() + "/" + FONT_CACHE_DIR_NAME;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXDataStructureUtil.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXDataStructureUtil.java
deleted file mode 100644
index ee28e45..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXDataStructureUtil.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import java.util.HashMap;
-
-public class WXDataStructureUtil {
-
-  /**
-   * The largest power of two that can be represented as an {@code int}.
-   */
-  private static final int MAX_POWER_OF_TWO = 1 << (Integer.SIZE - 2);
-
-  /**
-   * Creates a {@code HashMap} instance, with a high enough "initial capacity" that it <i>should</i>
-   * hold {@code expectedSize} elements without growth. This behavior cannot be broadly guaranteed,
-   * but it is observed to be true for OpenJDK 1.7. It also can't be guaranteed that the method
-   * isn't inadvertently <i>oversizing</i> the returned map.
-   *
-   * @param expectedSize the number of entries you expect to add to the returned map
-   * @return a new, empty {@code HashMap} with enough capacity to hold {@code expectedSize} entries
-   * without resizing
-   * @throws IllegalArgumentException if {@code expectedSize} is negative
-   */
-  public static <K, V> HashMap<K, V> newHashMapWithExpectedSize(int expectedSize) {
-    return new HashMap<>(capacity(expectedSize));
-  }
-
-  /**
-   * Returns a capacity that is sufficient to keep the map from being resized as long as it grows no
-   * larger than expectedSize and the load factor is >= its default (0.75).
-   */
-  private static int capacity(int expectedSize) {
-    if (expectedSize < 3) {
-      checkNonnegative(expectedSize, "expectedSize");
-      return expectedSize + 1;
-    }
-    if (expectedSize < MAX_POWER_OF_TWO) {
-      // This is the calculation used in JDK8 to resize when a putAll
-      // happens; it seems to be the most conservative calculation we
-      // can make.  0.75 is the default load factor.
-      return (int) ((float) expectedSize / 0.75F + 1.0F);
-    }
-    return Integer.MAX_VALUE; // any large value
-  }
-
-  private static int checkNonnegative(int value, String name) {
-    if (value < 0) {
-      throw new IllegalArgumentException(name + " cannot be negative but was: " + value);
-    }
-    return value;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXDeviceUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXDeviceUtils.java
deleted file mode 100644
index c5dd78b..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXDeviceUtils.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.content.Context;
-import android.os.Build;
-
-public class WXDeviceUtils {
-
-
-    public static boolean isAutoResize(Context context){
-        if(context == null){
-            return false;
-        }
-        return isMateX(context) || isGalaxyFold(context);
-    }
-
-    /**
-     * Mate X
-     * */
-    public static boolean isMateX(Context context) {
-        return "HUAWEI".equalsIgnoreCase(Build.BRAND) && ("unknownRLI".equalsIgnoreCase(Build.DEVICE) || ("HWTAH".equalsIgnoreCase(Build.DEVICE)));
-    }
-
-
-    /**
-     * Galaxy Fopld
-     * */
-    public static boolean isGalaxyFold(Context context) {
-
-        if("samsung".equalsIgnoreCase(Build.BRAND) && "SM-F9000".equalsIgnoreCase(Build.MODEL)) {
-            return true;
-        }
-
-        return false;
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXDomUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXDomUtils.java
deleted file mode 100644
index bfd0ea5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXDomUtils.java
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.utils;
-
-import android.support.annotation.NonNull;
-import com.taobao.weex.dom.CSSConstants;
-import com.taobao.weex.dom.CSSShorthand.EDGE;
-import com.taobao.weex.dom.WXStyle;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.dom.CSSShorthand;
-
-public class WXDomUtils {
-
-  /**
-   * Get the content width of the dom.
-   * @return the width of the dom that excludes left-padding, left-border-width,
-   * right-border-width and right-padding.
-   */
-  public static float getContentWidth(WXComponent component) {
-    float rawWidth = component.getLayoutWidth();
-    float leftPadding, rightPadding, leftBorder, rightBorder;
-    CSSShorthand padding = component.getPadding();
-    CSSShorthand border = component.getBorder();
-
-    if (!CSSConstants.isUndefined((leftPadding = padding.get(CSSShorthand.EDGE.LEFT)))) {
-      rawWidth -= leftPadding;
-    }
-    if (!CSSConstants.isUndefined((rightPadding = padding.get(CSSShorthand.EDGE.RIGHT)))) {
-      rawWidth -= rightPadding;
-    }
-
-    if (!CSSConstants.isUndefined(leftBorder = border.get(CSSShorthand.EDGE.LEFT))) {
-      rawWidth -= leftBorder;
-    }
-    if (!CSSConstants.isUndefined(rightBorder = border.get(CSSShorthand.EDGE.RIGHT))) {
-      rawWidth -= rightBorder;
-    }
-    return rawWidth;
-  }
-
-  /**
-   * Get the content height of the dom.
-   * @return the height of the dom that excludes top-padding, top-border-width, bottom-padding
-   * and bottom-border-width.
-   */
-  public static float getContentHeight(WXComponent component) {
-    float rawHeight = component.getLayoutHeight();
-    float topPadding, bottomPadding, topBorder, bottomBorder;
-    CSSShorthand padding = component.getPadding();
-    CSSShorthand border = component.getBorder();
-
-    if (!CSSConstants.isUndefined((topPadding = padding.get(CSSShorthand.EDGE.TOP)))) {
-      rawHeight -= topPadding;
-    }
-    if (!CSSConstants.isUndefined((bottomPadding = padding.get(CSSShorthand.EDGE.BOTTOM)))) {
-      rawHeight -= bottomPadding;
-    }
-
-    if (!CSSConstants.isUndefined(topBorder = border.get(CSSShorthand.EDGE.TOP))) {
-      rawHeight -= topBorder;
-    }
-    if (!CSSConstants.isUndefined(bottomBorder = border.get(CSSShorthand.EDGE.BOTTOM))) {
-      rawHeight -= bottomBorder;
-    }
-    return rawHeight;
-  }
-
-  public static float getContentWidth(
-      @NonNull CSSShorthand padding,
-      @NonNull CSSShorthand border,
-      float layoutWidth){
-    float leftPadding, rightPadding, leftBorder, rightBorder;
-
-    if (!CSSConstants.isUndefined((leftPadding = padding.get(EDGE.LEFT)))) {
-      layoutWidth -= leftPadding;
-    }
-    if (!CSSConstants.isUndefined((rightPadding = padding.get(EDGE.RIGHT)))) {
-      layoutWidth -= rightPadding;
-    }
-
-    if (!CSSConstants.isUndefined(leftBorder = border.get(EDGE.LEFT))) {
-      layoutWidth -= leftBorder;
-    }
-    if (!CSSConstants.isUndefined(rightBorder = border.get(EDGE.RIGHT))) {
-      layoutWidth -= rightBorder;
-    }
-    return layoutWidth;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXExceptionUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXExceptionUtils.java
deleted file mode 100644
index 1bf7d7f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXExceptionUtils.java
+++ /dev/null
@@ -1,240 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Map.Entry;
-import java.util.Set;
-import java.util.concurrent.CopyOnWriteArraySet;
-
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.adapter.IWXJSExceptionAdapter;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXErrorCode.ErrorGroup;
-import com.taobao.weex.common.WXJSExceptionInfo;
-import com.taobao.weex.common.WXPerformance;
-import com.taobao.weex.performance.WXAnalyzerDataTransfer;
-import com.taobao.weex.performance.WXInstanceApm;
-import com.taobao.weex.performance.WXStateRecord;
-
-/**
- * Created on 2017/10/13.
- */
-
-public class WXExceptionUtils {
-
-    private static Set<String> sGlobalExceptionRecord = new CopyOnWriteArraySet<String>();
-
-	/**
-	 * degradeUrl for degrade case
-	 */
-	public static String degradeUrl = "BundleUrlDefaultDegradeUrl";
-
-	private static boolean checkNeedReportCauseRepeat(String instanceId,WXErrorCode errCode,String exception){
-
-	    if (TextUtils.isEmpty(exception)){
-	        return true;
-        }
-
-        if (null != errCode && errCode.getErrorGroup() != ErrorGroup.JS){
-	        return true;
-        }
-
-        if (TextUtils.isEmpty(instanceId)){
-            instanceId = "instanceIdNull";
-        }
-
-        String targetException = exception.length() > 200 ?exception.substring(0,200) : exception;
-        Set<String> recordExceptionHistory= null;
-
-        WXSDKInstance instance =  WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
-        if (null == instance){
-            recordExceptionHistory = sGlobalExceptionRecord;
-        }else {
-            recordExceptionHistory =  instance.getApmForInstance().exceptionRecord;
-        }
-
-        if (null == recordExceptionHistory){
-            return true;
-        }
-
-        if (recordExceptionHistory.contains(targetException)){
-            return false;
-        }
-        recordExceptionHistory.add(targetException);
-        return true;
-    }
-
-
-
-
-	/**
-	 * commitCriticalExceptionRT eg:JsRuntime Exception or JsFramework Init Exception
-	 * @param instanceId
-	 * @param errCode
-	 * @param function
-	 * @param exception
-	 * @param extParams
-	 */
-	public static void commitCriticalExceptionRT(@Nullable final String instanceId,
-												 @Nullable final WXErrorCode errCode,
-												 @Nullable final String function,
-												 @Nullable final String exception,
-												 @Nullable final Map<String,String> extParams ) {
-
-        try {
-            WXLogUtils.e("weex","commitCriticalExceptionRT :"+errCode+"exception"+exception);
-            WXStateRecord.getInstance().recordException(instanceId,exception);
-            IWXConfigAdapter configAdapter = WXSDKManager.getInstance().getWxConfigAdapter();
-            boolean doCheck = true;
-            if (null != configAdapter){
-                String value = configAdapter.getConfig("wxapm","check_repeat_report","true");
-                doCheck = "true".equalsIgnoreCase(value);
-            }
-            boolean doReport =true;
-            if (doCheck){
-                doReport = checkNeedReportCauseRepeat(instanceId,errCode,exception);
-            }
-            if (!doReport){
-                return;
-            }
-        }catch (Throwable e){
-            e.printStackTrace();
-        }
-
-
-		commitCriticalExceptionWithDefaultUrl(
-		    "BundleUrlDefault",
-            instanceId,
-            errCode,
-            function,
-            exception,
-            extParams
-        );
-	}
-
-    public static void commitCriticalExceptionWithDefaultUrl(
-        @Nullable final String defaultUrl,
-        @Nullable final String instanceId,
-        @Nullable final WXErrorCode errCode,
-        @Nullable final String function,
-        @Nullable final String exception,
-        @Nullable final Map<String,String> extParams
-    ){
-        IWXJSExceptionAdapter adapter = WXSDKManager.getInstance().getIWXJSExceptionAdapter();
-        WXSDKInstance instance = null;
-        WXJSExceptionInfo exceptionCommit;
-        String bundleUrlCommit = TextUtils.isEmpty(defaultUrl)?"BundleUrlDefault":defaultUrl;
-        String instanceIdCommit = "InstanceIdDefalut";
-        String exceptionMsgCommit = exception;
-        Map<String, String> commitMap = extParams;
-        if (null == commitMap){
-            commitMap = new HashMap<>();
-        }
-        commitMap.put("wxSdkInitStartTime", String.valueOf(WXEnvironment.sSDKInitStart));
-        commitMap.put("wxSDKInitCostTime", String.valueOf(WXEnvironment.sSDKInitTime));
-        commitMap.put("wxSDKCurExceptionTime", String.valueOf(System.currentTimeMillis()));
-        commitMap.put("wxUseRuntimeApi",String.valueOf(WXEnvironment.sUseRunTimeApi));
-        if (!TextUtils.isEmpty(instanceId)) {
-            instanceIdCommit = instanceId;
-            instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
-
-            if (null != instance) {
-                bundleUrlCommit = instance.getApmForInstance().reportPageName;
-                Object loadLength = instance.getApmForInstance().extInfo.get(WXInstanceApm.VALUE_BUNDLE_LOAD_LENGTH);
-                String loadLengthStr = (loadLength instanceof Integer)?String.valueOf(loadLength):"unknownLength";
-                commitMap.put(WXInstanceApm.VALUE_BUNDLE_LOAD_LENGTH,loadLengthStr);
-                commitMap.put("templateInfo",instance.getTemplateInfo());
-                if (TextUtils.isEmpty(bundleUrlCommit) || bundleUrlCommit.equals(WXPerformance.DEFAULT)) {
-                    if (!TextUtils.equals(degradeUrl, "BundleUrlDefaultDegradeUrl")) {
-                        bundleUrlCommit = degradeUrl;
-                    } else
-                        bundleUrlCommit = WXSDKInstance.requestUrl;
-                }
-                for (Map.Entry<String,String> entry: instance.getContainerInfo().entrySet()){
-                    commitMap.put(entry.getKey(),entry.getValue());
-                }
-                commitMap.put("wxStageList",convertStageToStr(instance));
-                String bundleTemplate = instance.getTemplate();
-                if (null == bundleTemplate){
-                    bundleTemplate = "has recycle by gc";
-                }else {
-                    int length = bundleTemplate.length();
-                    bundleTemplate = bundleTemplate.substring(0,Math.min(length,300));
-                }
-                commitMap.put("wxTemplateOfBundle",bundleTemplate);
-
-                Long pageStartTime = instance.getApmForInstance().stageMap.get(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_START);
-                if (null == pageStartTime){
-                    pageStartTime = instance.getApmForInstance().stageMap.get(WXInstanceApm.KEY_PAGE_STAGES_RENDER_ORGIGIN);
-                }
-                if (null != pageStartTime){
-                    commitMap.put("wxUseTime", String.valueOf(WXUtils.getFixUnixTime() - pageStartTime));
-                }
-            }
-        } else {//instance is null for instance id is null
-            if (commitMap.size() > 0) {
-                bundleUrlCommit = TextUtils.isEmpty(commitMap.get("weexUrl")) ? commitMap.get("weexUrl")
-                    : commitMap.get("bundleUrl");
-            }
-        }
-
-        String illegalValue = commitMap.get("errorCode");
-        if (null != illegalValue && illegalValue.length()>200){
-            commitMap.remove("errorCode");
-        }
-
-        exceptionCommit = new WXJSExceptionInfo(instanceIdCommit, bundleUrlCommit, errCode, function, exceptionMsgCommit, commitMap);
-        if (adapter != null) {
-            adapter.onJSException(exceptionCommit);
-        }
-
-        WXAnalyzerDataTransfer.transferError(exceptionCommit, instanceId);
-    }
-
-    private static String convertStageToStr(WXSDKInstance instance) {
-        if (null == instance || null == instance.getApmForInstance() || instance.getApmForInstance().stageMap.isEmpty()) {
-            return "noStageRecord";
-        }
-        List<Entry<String, Long>> list = new ArrayList<>(instance.getApmForInstance().stageMap.entrySet());
-        Collections.sort(list, new Comparator<Entry<String, Long>>() {
-            @Override
-            public int compare(Entry<String, Long> o1, Entry<String, Long> o2) {
-                return (int)(o1.getValue() - o2.getValue());
-            }
-        });
-
-        StringBuilder builder = new StringBuilder();
-        for (Map.Entry<String, Long> entry : list) {
-            builder.append(entry.getKey()).append(':').append(entry.getValue()).append("->");
-        }
-        return builder.toString();
-    }
-
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXFileUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXFileUtils.java
deleted file mode 100644
index 094ce98..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXFileUtils.java
+++ /dev/null
@@ -1,301 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.content.Context;
-import android.text.TextUtils;
-import android.util.Base64;
-
-import java.io.BufferedInputStream;
-import java.io.BufferedReader;
-import java.io.Closeable;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.InputStreamReader;
-import java.io.UnsupportedEncodingException;
-import java.math.BigInteger;
-import java.security.MessageDigest;
-import java.security.NoSuchAlgorithmException;
-import java.util.zip.ZipEntry;
-import java.util.zip.ZipFile;
-import java.util.zip.ZipInputStream;
-
-import static com.taobao.weex.utils.WXSoInstallMgrSdk._cpuType;
-
-public class WXFileUtils {
-
-  /**
-   * Load file in device directory, if not exist, load from asset directory.
-   * @param path FilePath
-   * @param context Weex Context
-   * @return the Content of the file
-   */
-  public static String loadFileOrAsset(String path, Context context) {
-    if (!TextUtils.isEmpty(path)) {
-      File file = new File(path);
-      if (file.exists()) {
-        try {
-          FileInputStream fis = new FileInputStream(file);
-          return readStreamToString(fis);
-        } catch (FileNotFoundException e) {
-          e.printStackTrace();
-        }
-      } else {
-        return loadAsset(path, context);
-      }
-    }
-    return "";
-  }
-
-  /**
-   * Load file in asset directory.
-   * @param path FilePath
-   * @param context Weex Context
-   * @return the Content of the file
-   */
-  public static String loadAsset(String path, Context context) {
-    if (context == null || TextUtils.isEmpty(path)) {
-      return null;
-    }
-    InputStream inputStream = null;
-    try {
-      inputStream = context.getAssets().open(path);
-      return readStreamToString(inputStream);
-    } catch (IOException e) {
-      e.printStackTrace();
-    }
-    return "";
-  }
-
-  public static String readStreamToString(InputStream inputStream) {
-    BufferedReader bufferedReader = null;
-    try {
-      StringBuilder builder = new StringBuilder(inputStream.available() + 10);
-      bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
-      char[] data = new char[4096];
-      int len = -1;
-      while ((len = bufferedReader.read(data)) > 0) {
-        builder.append(data, 0, len);
-      }
-
-      return builder.toString();
-    } catch (IOException e) {
-      e.printStackTrace();
-      WXLogUtils.e("", e);
-    } finally {
-      try {
-        if (bufferedReader != null)
-          bufferedReader.close();
-      } catch (IOException e) {
-        WXLogUtils.e("WXFileUtils loadAsset: ", e);
-      }
-      try {
-        if (inputStream != null)
-          inputStream.close();
-      } catch (IOException e) {
-        WXLogUtils.e("WXFileUtils loadAsset: ", e);
-      }
-    }
-
-    return "";
-  }
-
-  public static byte[] readBytesFromAssets(String path, Context context) {
-    if (context == null || TextUtils.isEmpty(path)) {
-      return null;
-    }
-    InputStream inputStream = null;
-    try {
-      inputStream = context.getAssets().open(path);
-      byte[] data = new byte[4096];
-      int length = inputStream.read(data);
-      byte[] result = new byte[length];
-      System.arraycopy(data, 0, result, 0, length);
-      return result;
-    } catch (IOException e) {
-      e.printStackTrace();
-    }
-    return null;
-  }
-
-  public static boolean saveFile(String path, byte[] content, Context context) {
-    if (TextUtils.isEmpty(path) || content == null || context == null) {
-      return false;
-    }
-    FileOutputStream outStream = null;
-    try {
-      outStream = new FileOutputStream(path);
-      outStream.write(content);
-      return true;
-    } catch (Exception e) {
-      WXLogUtils.e("WXFileUtils saveFile: " + WXLogUtils.getStackTrace(e));
-    } finally {
-      if (outStream != null) {
-        try {
-          outStream.close();
-        } catch (IOException e) {
-          e.printStackTrace();
-        }
-      }
-    }
-    return false;
-  }
-
-  public static String md5(String  template){
-    try {
-      if(template == null){
-        return  "";
-      }
-      return  md5(template.getBytes("UTF-8"));
-    } catch (UnsupportedEncodingException e) {
-      return  "";
-    }
-  }
-
-  public static String md5(byte[] bts){
-    try {
-      MessageDigest digest = MessageDigest.getInstance("MD5");
-      digest.update(bts);
-      BigInteger bigInt = new BigInteger(1, digest.digest());
-      return  bigInt.toString(16);
-    } catch (NoSuchAlgorithmException e) {;
-      return  "";
-    }
-  }
-
-  public static String base64Md5(String  template){
-    try {
-      if(template == null){
-        return  "";
-      }
-      return  base64Md5(template.getBytes("UTF-8"));
-    } catch (UnsupportedEncodingException e) {
-      return  "";
-    }
-  }
-
-  public static String base64Md5(byte[] bts){
-    try {
-      MessageDigest digest = MessageDigest.getInstance("MD5");
-      digest.update(bts);
-      return Base64.encodeToString(digest.digest(), Base64.NO_WRAP);
-    } catch (NoSuchAlgorithmException e) {;
-      return  "";
-    }
-  }
-
-  public static void extractSo(String apkFile, String path) throws IOException {
-    ZipFile zip = new ZipFile(apkFile);
-    InputStream zipInputStream = new BufferedInputStream(new FileInputStream(apkFile));
-    ZipInputStream zin = new ZipInputStream(zipInputStream);
-    ZipEntry zipEntry;
-    while ((zipEntry = zin.getNextEntry()) != null) {
-      if(zipEntry.isDirectory()){
-        continue;
-      }
-      if (zipEntry.getName().contains("lib/" + _cpuType() + "/") &&
-              (zipEntry.getName().contains("weex") || zipEntry.getName().equals("libJavaScriptCore.so"))) {
-        String[] fileNames = zipEntry.getName().split("/");
-        String fileName = fileNames[fileNames.length - 1];
-        InputStream inputStream = zip.getInputStream(zipEntry);
-        byte[] data = new byte[1024];
-        File zipFile = new File(path + "/" + fileName);
-        if(zipFile.exists()) {
-          zipFile.delete();
-        }
-
-        zipFile.createNewFile();
-
-        FileOutputStream outputStream =new FileOutputStream(zipFile);
-        while (inputStream.read(data) != -1) {
-          outputStream.write(data);
-        }
-        outputStream.close();
-
-      }
-    }
-    zin.closeEntry();
-  }
-
-  public static void copyFile(File oldFile, File newFile) {
-    FileInputStream inputStream = null;
-    FileOutputStream outputStream = null;
-    try {
-      inputStream = new FileInputStream(oldFile);
-      byte[] data = new byte[1024];
-      outputStream = new FileOutputStream(newFile);
-      while (inputStream.read(data) != -1) {
-        outputStream.write(data);
-      }
-      inputStream.close();
-      outputStream.close();
-    } catch (Exception e) {
-      WXLogUtils.e("copyFile " + e.getMessage() + ": " + oldFile.getAbsolutePath() + ": " + newFile.getAbsolutePath());
-      if (inputStream != null) {
-        try {
-          inputStream.close();
-        } catch (IOException e1) {
-          e1.printStackTrace();
-        }
-      }
-
-      if (outputStream != null) {
-        try {
-          outputStream.close();
-        } catch (IOException e1) {
-          e1.printStackTrace();
-        }
-      }
-    }
-  }
-
-  public static void copyFileWithException(File oldFile,File newFile ) throws Exception{
-    FileInputStream inputStream = null;
-    FileOutputStream outputStream = null;
-    try {
-      inputStream = new FileInputStream(oldFile);
-      byte[] data = new byte[1024];
-      outputStream = new FileOutputStream(newFile);
-      while (inputStream.read(data) != -1) {
-        outputStream.write(data);
-      }
-    }catch (Exception e){
-      throw e;
-    }finally {
-      closeIo(inputStream);
-      closeIo(outputStream);
-    }
-  }
-
-  public static void closeIo(Closeable c){
-    if (null == c){
-      return;
-    }
-    try {
-      c.close();
-    }catch (Throwable e){
-      e.printStackTrace();
-    }
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXInterception.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXInterception.java
deleted file mode 100644
index c667c94..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXInterception.java
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import java.lang.reflect.InvocationHandler;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-import java.lang.reflect.Proxy;
-
-public class WXInterception {
-
-  private WXInterception() {
-  }
-
-  @SuppressWarnings("unchecked")
-  public static <T> T proxy(final Object delegatee, final Class<T> interface_class, final InterceptionHandler<T> handler) throws IllegalArgumentException {
-    if (delegatee instanceof Intercepted) {
-      return (T) delegatee;
-    }
-    handler.setDelegate((T) delegatee);
-    return (T) Proxy.newProxyInstance(WXInterception.class.getClassLoader(), new Class<?>[]{interface_class, Intercepted.class}, handler);
-  }
-
-  @SuppressWarnings("unchecked")
-  public static <T> T proxy(final Object delegatee, final InterceptionHandler<T> handler, final Class<?>... interfaces) throws IllegalArgumentException {
-    //if (Proxy.isProxyClass(delegatee.getClass())) return (T) delegatee;
-    handler.setDelegate((T) delegatee);
-    return (T) Proxy.newProxyInstance(WXInterception.class.getClassLoader(), interfaces, handler);
-  }
-
-  private interface Intercepted {
-
-  }        // A mark to identify our proxy class
-
-  /**
-   * Derive this class and override {@link #invoke(Object, Method, Object[])} to implement an
-   * interception handler.
-   */
-  public abstract static class InterceptionHandler<T> implements InvocationHandler {
-
-    private T mDelegate;
-
-    /**
-     * Derived class should override this method and call <code>super.invoke(...)</code> to delegate the
-     * procedure to original delegate instance if needed.
-     *
-     * @param proxy is ignored, instead the actual delegate instance will be used to invoke this method on.
-     */
-    @Override
-    public Object invoke(final Object proxy, final Method method, final Object[] args) throws Throwable {
-      try {
-        return method.invoke(delegate(), args);
-      } catch (IllegalArgumentException e) {/* Should never happen */
-        WXLogUtils.e("", e);
-        return null;
-      } catch (IllegalAccessException e) {/* Should never happen */
-        WXLogUtils.e("", e);
-        return null;
-      } catch (InvocationTargetException e) {
-        throw e.getTargetException();
-      }
-    }
-
-    protected T delegate() {
-      return mDelegate;
-    }
-
-    void setDelegate(final T delegate) {
-      mDelegate = delegate;
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXJsonUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXJsonUtils.java
deleted file mode 100644
index cb8e2a7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXJsonUtils.java
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-
-import android.support.annotation.NonNull;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONObject;
-import com.alibaba.fastjson.serializer.SerializerFeature;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.common.WXRuntimeException;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-
-/**
- * Tool for parse JSON
- */
-public class WXJsonUtils {
-
-
-  public @NonNull static <T> List<T> getList(String json, Class<T> clazz) {
-    List<T> result = null;
-    try {
-      result = JSONObject.parseArray(json, clazz);
-    } catch (Exception e) {
-      e.printStackTrace();
-      result = new ArrayList<>();
-    }
-    return result;
-  }
-
-  public @NonNull static String fromObjectToJSONString(Object obj, boolean WriteNonStringKeyAsString){
-    try {
-      if(WriteNonStringKeyAsString) {
-        return JSON.toJSONString(obj, SerializerFeature.WriteNonStringKeyAsString);
-      }else {
-        return JSON.toJSONString(obj);
-      }
-    }catch(Exception e){
-      if(WXEnvironment.isApkDebugable()){
-        throw new WXRuntimeException("fromObjectToJSONString parse error!");
-      }
-      WXLogUtils.e("fromObjectToJSONString error:", e);
-      return "{}";
-    }
-  }
-  public @NonNull static String fromObjectToJSONString(Object obj) {
-
-    return fromObjectToJSONString(obj,false);
-  }
-
-  /**
-   * Put the map info in the JSONObject to the container.
-   * This method check for null value in the JSONObject
-   * and won't put the null value in the container.
-   * As {@link ConcurrentHashMap#putAll(Map)} will throws an exception if the key or value to
-   * be put is null, it is necessary to invoke this method as replacement of
-   * {@link Map#putAll(Map)}
-   * @param container container to contain the JSONObject.
-   * @param rawValue jsonObject, contains map info.
-   */
-  public static void putAll(Map<String, Object> container, JSONObject rawValue) {
-    String key;
-    Object value;
-    for (Map.Entry<String, Object> entry : rawValue.entrySet()) {
-      key = entry.getKey();
-      value = entry.getValue();
-      if (key != null && value != null) {
-        container.put(key, value);
-      }
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXLogUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXLogUtils.java
deleted file mode 100644
index d8bc7a9..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXLogUtils.java
+++ /dev/null
@@ -1,344 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.support.annotation.Nullable;
-import android.text.TextUtils;
-import android.util.Log;
-
-import com.alibaba.fastjson.JSON;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.performance.WXStateRecord;
-import com.taobao.weex.utils.tools.LogDetail;
-
-import java.io.IOException;
-import java.io.PrintWriter;
-import java.io.StringWriter;
-import java.lang.reflect.Method;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-
-import static com.taobao.weex.utils.tools.TimeCalculator.TIMELINE_TAG;
-
-public class WXLogUtils {
-
-  public static final String WEEX_TAG = "weex";
-  public static final String WEEX_PERF_TAG = "weex_perf";
-
-  private static final String CLAZZ_NAME_LOG_UTIL = "com.taobao.weex.devtools.common.LogUtil";
-
-  private static StringBuilder builder = new StringBuilder(50);
-  private static HashMap<String, Class> clazzMaps = new HashMap<>(2);
-  private static List<JsLogWatcher> jsLogWatcherList;
-  private static LogWatcher sLogWatcher;
-
-  static {
-    clazzMaps.put(CLAZZ_NAME_LOG_UTIL, loadClass(CLAZZ_NAME_LOG_UTIL));
-    jsLogWatcherList = new ArrayList<>();
-  }
-
-  private static Class loadClass(String clazzName) {
-    Class<?> clazz = null;
-    try {
-      clazz = Class.forName(clazzName);
-      if (clazz != null) {
-        clazzMaps.put(clazzName, clazz);
-      }
-    } catch (ClassNotFoundException e) {
-      // ignore
-    }
-    return clazz;
-  }
-
-  public static void renderPerformanceLog(String type, long time) {
-    if (WXEnvironment.isApkDebugable() || WXEnvironment.isPerf()) {
-//      builder.setLength(0);
-//      builder.append("[render time]").append(type).append(":").append(time);
-//      Log.d(WEEX_PERF_TAG, builder.substring(0));
-//      writeConsoleLog("debug", builder.substring(0));
-    }
-  }
-
-  private static void log(String tag, String msg, LogLevel level){
-    if(TextUtils.isEmpty(msg) || TextUtils.isEmpty(tag) || level == null || TextUtils.isEmpty(level.getName())){
-      return;
-    }
-    if (level == LogLevel.ERROR && !TextUtils.isEmpty(msg) && msg.contains("IPCException")){
-      WXStateRecord.getInstance().recordIPCException("ipc",msg);
-    }
-
-    if(sLogWatcher !=null){
-      sLogWatcher.onLog(level.getName(), tag, msg);
-    }
-
-    if (WXEnvironment.isApkDebugable()) {
-      if(level.getValue() - WXEnvironment.sLogLevel.getValue() >= 0) {
-        Log.println(level.getPriority(), tag, msg);
-        writeConsoleLog(level.getName(), msg);
-      }
-      // if not debug level then print log
-    }else {
-      if(level.getValue() - LogLevel.WARN.getValue() >=0 && level.getValue() - WXEnvironment.sLogLevel.getValue() >= 0){
-        Log.println(level.getPriority(),tag, msg);
-      }
-    }
-  }
-
-  public static void v(String msg) {
-    v(WEEX_TAG,msg);
-  }
-
-  public static void d(String msg) {
-    d(WEEX_TAG,msg);
-  }
-
-  public static void d(String tag, byte[] msg) {
-    d(tag, new String(msg));
-  }
-
-  public static void i(String msg) {
-    i(WEEX_TAG,msg);
-  }
-
-  public static void i(String tag, byte[] msg) {
-    i(tag, new String(msg));
-  }
-
-  public static void info(String msg) {
-    i(WEEX_TAG, msg);
-  }
-
-  public static void w(String msg) {
-    w(WEEX_TAG, msg);
-  }
-
-  public static void w(String tag, byte[] msg) {
-    w(tag, new String(msg));
-  }
-
-  public static void e(String msg) {
-    e(WEEX_TAG,msg);
-  }
-
-  public static void e(String tag, byte[] msg) {
-    e(tag, new String(msg));
-  }
-
-  public static void performance(String instanceId, byte[]msg) {
-//    String s = new String(msg);
-//    if(!TextUtils.isEmpty(instanceId)) {
-//      WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-//      if(sdkInstance != null) {
-//        int i = s.indexOf(",");
-//        if(i >=0 && i < s.length()) {
-//          String substring = s.substring(s.indexOf(",") + 1);
-//          LogDetail logDetail = JSON.parseObject(substring,LogDetail.class);
-//          sdkInstance.mTimeCalculator.addLog(logDetail);
-//        }
-//      }
-//    }
-//    Log.e(TIMELINE_TAG, "from WeexCore" + s);
-  }
-
-  public static void wtf(String msg){
-    wtf(WEEX_TAG, msg);
-  }
-
-  public static void d(String tag, String msg) {
-
-    if(!TextUtils.isEmpty(tag) && !TextUtils.isEmpty(msg)){
-      log(tag, msg, LogLevel.DEBUG);
-
-      if(WXEnvironment.isApkDebugable()){//sLogLevel in debug mode is "LogLevel.DEBUG"
-        if ("jsLog".equals(tag) && jsLogWatcherList != null && jsLogWatcherList.size() > 0) {
-          for (JsLogWatcher jsLogWatcher : jsLogWatcherList) {
-            if (msg.endsWith("__DEBUG")) {
-              jsLogWatcher.onJsLog(Log.DEBUG, msg.replace("__DEBUG", ""));
-            } else if (msg.endsWith("__INFO")) {
-              jsLogWatcher.onJsLog(Log.DEBUG, msg.replace("__INFO", ""));
-            } else if (msg.endsWith("__WARN")) {
-              jsLogWatcher.onJsLog(Log.DEBUG, msg.replace("__WARN", ""));
-            } else if (msg.endsWith("__ERROR")) {
-              jsLogWatcher.onJsLog(Log.DEBUG, msg.replace("__ERROR", ""));
-            } else {
-              jsLogWatcher.onJsLog(Log.DEBUG, msg);
-            }
-          }
-        }
-      }
-    }
-  }
-
-  private static LogLevel getLogLevel(String level) {
-    switch (level.trim()){
-      case "__ERROR":
-        return LogLevel.ERROR;
-      case "__WARN":
-        return LogLevel.WARN;
-      case "__INFO":
-        return LogLevel.INFO;
-      case "__LOG":
-        return LogLevel.INFO;
-      case "__DEBUG":
-        return LogLevel.DEBUG;
-    }
-    return LogLevel.DEBUG;
-  }
-
-  public static void i(String tag, String msg) {
-    log(tag, msg,LogLevel.INFO);
-  }
-
-  public static void v(String tag, String msg) {
-    log(tag, msg,LogLevel.VERBOSE);
-  }
-
-  public static void w(String tag, String msg) {
-    log(tag, msg,LogLevel.WARN);
-  }
-
-  public static void e(String tag, String msg) {
-    log(tag, msg,LogLevel.ERROR);
-  }
-
-  public static void wtf(String tag, String msg){
-    log(tag, msg, LogLevel.WTF);
-  }
-
-  /**
-   * 'p' for 'Performance', use {@link #WEEX_PERF_TAG}
-   * @param msg
-   */
-  public static void p(String msg) {
-    d(WEEX_PERF_TAG,msg);
-  }
-
-  public static void d(String prefix, Throwable e) {
-    if (WXEnvironment.isApkDebugable()) {
-      d(prefix + getStackTrace(e));
-    }
-  }
-
-  public static void i(String prefix, Throwable e) {
-    if (WXEnvironment.isApkDebugable()) {
-      info(prefix + getStackTrace(e));
-    }
-  }
-
-  public static void v(String prefix, Throwable e) {
-    if (WXEnvironment.isApkDebugable()) {
-      v(prefix + getStackTrace(e));
-    }
-  }
-
-  public static void w(String prefix, Throwable e) {
-    w(prefix + getStackTrace(e));
-
-  }
-
-  public static void e(String prefix, Throwable e) {
-    e(prefix + getStackTrace(e));
-
-  }
-
-  public static void wtf(String prefix, Throwable e){
-    if (WXEnvironment.isApkDebugable()) {
-      wtf(prefix + getStackTrace(e));
-    }
-  }
-
-  /**
-   * 'p' for 'Performance', use {@link #WEEX_PERF_TAG}
-   */
-  public static void p(String prefix, Throwable e) {
-    if (WXEnvironment.isApkDebugable()) {
-      p(prefix + getStackTrace(e));
-    }
-  }
-
-  public static void eTag(String tag, Throwable e) {
-    if (WXEnvironment.isApkDebugable()) {
-      e(tag, getStackTrace(e));
-    }
-  }
-
-  public static String getStackTrace(@Nullable Throwable e) {
-    if (e == null) {
-      return "";
-    }
-    StringWriter sw = null;
-    PrintWriter pw = null;
-    try {
-      sw = new StringWriter();
-      pw = new PrintWriter(sw);
-      e.printStackTrace(pw);
-      pw.flush();
-      sw.flush();
-    } finally {
-      if (sw != null) {
-        try {
-          sw.close();
-        } catch (IOException e1) {
-          e1.printStackTrace();
-        }
-      }
-      if (pw != null) {
-        pw.close();
-      }
-    }
-    return sw.toString();
-  }
-
-
-
-  private static void writeConsoleLog(String level, String message) {
-    if (WXEnvironment.isApkDebugable()) {
-      try {
-        Class<?> clazz = clazzMaps.get(CLAZZ_NAME_LOG_UTIL);
-        if (clazz != null) {
-          Method m = clazz.getMethod("log", String.class, String.class);
-          m.invoke(clazz, level, message);
-        }
-      } catch (Exception e) {
-        Log.d(WEEX_TAG, "LogUtil not found!");
-      }
-    }
-  }
-
-  public static void setJsLogWatcher(JsLogWatcher watcher) {
-    if (!jsLogWatcherList.contains(watcher)) {
-      jsLogWatcherList.add(watcher);
-    }
-  }
-
-  public static void setLogWatcher(LogWatcher watcher) {
-    sLogWatcher = watcher;
-  }
-
-  public interface JsLogWatcher {
-    void onJsLog(int level, String log);
-  }
-
-  public interface LogWatcher {
-    void onLog(String level, String tag, String msg);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXMap.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXMap.java
deleted file mode 100644
index a3b6088..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXMap.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import java.io.Serializable;
-import java.util.HashMap;
-
-public class WXMap extends HashMap<String, String> implements Serializable {
-
-  public String put(String key, byte[] value) {
-    return super.put(key, new String(value));
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXReflectionUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXReflectionUtils.java
deleted file mode 100644
index 31ecd2f..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXReflectionUtils.java
+++ /dev/null
@@ -1,142 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.text.TextUtils;
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-
-import java.lang.reflect.Field;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Type;
-import java.math.BigDecimal;
-
-public class WXReflectionUtils {
-
-  public static Object parseArgument(Type paramClazz, Object value) {
-    if(value != null){
-      if(value.getClass() == paramClazz){
-        return  value;
-      }
-      if(paramClazz instanceof  Class){
-        if( ((Class<?>) paramClazz).isAssignableFrom(value.getClass()))   {
-          return value;
-        }
-      }
-    }
-    if (paramClazz == String.class) {
-      return value instanceof String ? value : JSON.toJSONString(value);
-    } else if (paramClazz == int.class) {
-      return value.getClass().isAssignableFrom(int.class) ? value : WXUtils.getInt(value);
-    } else if (paramClazz == long.class) {
-      return value.getClass().isAssignableFrom(long.class) ? value : WXUtils.getLong(value);
-    } else if (paramClazz == double.class) {
-      return value.getClass().isAssignableFrom(double.class) ? value : WXUtils.getDouble(value);
-    } else if (paramClazz == float.class) {
-      return value.getClass().isAssignableFrom(float.class) ? value : WXUtils.getFloat(value);
-    } else if (paramClazz == JSONArray.class && value != null && value.getClass() == JSONArray.class) {
-      return  value;
-    } else if (paramClazz == JSONObject.class && value != null && value.getClass() == JSONObject.class) {
-      return  value;
-    } else {
-      return JSON.parseObject(value instanceof String ? (String) value : JSON.toJSONString(value), paramClazz);
-    }
-  }
-
-
-  public static void setValue(Object obj, String fieldName, Object value) {
-    if (obj == null || TextUtils.isEmpty(fieldName)) {
-      return;
-    }
-
-    try {
-      // Field field = obj.getClass().getDeclaredField(fieldName);
-      Field field = getDeclaredField(obj, fieldName);
-
-      Object realValue = value;
-      if (value instanceof BigDecimal || value instanceof Number || value instanceof String) {
-        if (field.getType() == Float.class || field.getType() == float.class) {
-          realValue = Float.parseFloat(value.toString());
-        } else if (field.getType() == Double.class || field.getType() == double.class) {
-          realValue = Double.parseDouble(value.toString());
-        } else if (field.getType() == Integer.class || field.getType() == int.class) {
-          realValue = (int) Double.parseDouble(value.toString());
-        } else if (field.getType() == Boolean.class || field.getType() == boolean.class) {
-          realValue = Boolean.valueOf(value.toString());
-        }
-      }
-
-      if (field.getType() == boolean.class || field.getType() == Boolean.class) {
-        if (value != null) {
-          realValue = Boolean.valueOf(value.toString());
-        }
-      }
-
-      setProperty(obj, field, realValue);
-    } catch (Exception e) {
-      return;
-    }
-  }
-
-  /**
-   * get field form object and it's parent
-   */
-  public static Field getDeclaredField(Object object, String fieldName) {
-    Field field = null;
-
-    Class<?> clazz = object.getClass();
-
-    for (; clazz != Object.class; clazz = clazz.getSuperclass()) {
-      try {
-        field = clazz.getDeclaredField(fieldName);
-        return field;
-      } catch (Exception e) {
-
-      }
-    }
-
-    return null;
-  }
-
-  /**
-   * Set property(field) of the specified object.
-   * @param bean The object which has the given property
-   * @param field The field to be set
-   * @param value The value to be set to the field
-   * @throws IllegalAccessException
-   * @throws InvocationTargetException
-   * @throws NoSuchMethodException
-   */
-  public static void setProperty(Object bean, Field field, Object value) throws IllegalAccessException,
-          InvocationTargetException,
-          NoSuchMethodException {
-
-    if (bean == null || field == null) {
-      return;
-    }
-
-    try {
-      field.setAccessible(true);
-      field.set(bean, value);
-    } catch (Exception e) {
-    }
-
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXResourceUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXResourceUtils.java
deleted file mode 100644
index c368689..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXResourceUtils.java
+++ /dev/null
@@ -1,451 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.graphics.Color;
-import android.graphics.LinearGradient;
-import android.graphics.Shader;
-import android.support.annotation.NonNull;
-import android.text.TextUtils;
-import android.util.Pair;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Locale;
-import java.util.Map;
-import java.util.StringTokenizer;
-
-/**
- * Class for parse color
- */
-public class WXResourceUtils {
-
-  private final static Map<String, Integer> colorMap = new HashMap<>();
-  private final static int RGB_SIZE = 3;
-  private final static int RGBA_SIZE = 4;
-  private final static int HEX = 16;
-  private final static int COLOR_RANGE = 255;
-  private final static String RGB = "rgb";
-  private final static String RGBA = "rgba";
-  private final static SingleFunctionParser.FlatMapper<Integer> FUNCTIONAL_RGB_MAPPER =
-          new SingleFunctionParser.FlatMapper<Integer>() {
-            @Override
-            public Integer map(String raw) {
-              int color = WXUtils.parseUnitOrPercent(raw, COLOR_RANGE);
-              if (color < 0) {
-                color = 0;
-              } else if (color > COLOR_RANGE) {
-                color = COLOR_RANGE;
-              }
-              return color;
-            }
-          };
-
-  private final static SingleFunctionParser.NonUniformMapper<Number> FUNCTIONAL_RGBA_MAPPER =
-          new SingleFunctionParser.NonUniformMapper<Number>() {
-            @Override
-            public List<Number> map(List<String> raw) {
-              List<Number> result = new ArrayList<>(RGBA_SIZE);
-              int i, color;
-              for (i = 0; i < RGB_SIZE; i++) {
-                color = WXUtils.parseUnitOrPercent(raw.get(i), COLOR_RANGE);
-                if (color < 0) {
-                  color = 0;
-                } else if (color > COLOR_RANGE) {
-                  color = COLOR_RANGE;
-                }
-                result.add(color);
-              }
-              result.add(Float.valueOf(raw.get(i)));
-              return result;
-            }
-          };
-
-  static {
-    colorMap.put("aliceblue", 0XFFF0F8FF);
-    colorMap.put("antiquewhite", 0XFFFAEBD7);
-    colorMap.put("aqua", 0XFF00FFFF);
-    colorMap.put("aquamarine", 0XFF7FFFD4);
-    colorMap.put("azure", 0XFFF0FFFF);
-    colorMap.put("beige", 0XFFF5F5DC);
-    colorMap.put("bisque", 0XFFFFE4C4);
-    colorMap.put("black", 0XFF000000);
-    colorMap.put("blanchedalmond", 0XFFFFEBCD);
-    colorMap.put("blue", 0XFF0000FF);
-    colorMap.put("blueviolet", 0XFF8A2BE2);
-    colorMap.put("brown", 0XFFA52A2A);
-    colorMap.put("burlywood", 0XFFDEB887);
-    colorMap.put("cadetblue", 0XFF5F9EA0);
-    colorMap.put("chartreuse", 0XFF7FFF00);
-    colorMap.put("chocolate", 0XFFD2691E);
-    colorMap.put("coral", 0XFFFF7F50);
-    colorMap.put("cornflowerblue", 0XFF6495ED);
-    colorMap.put("cornsilk", 0XFFFFF8DC);
-    colorMap.put("crimson", 0XFFDC143C);
-    colorMap.put("cyan", 0XFF00FFFF);
-    colorMap.put("darkblue", 0XFF00008B);
-    colorMap.put("darkcyan", 0XFF008B8B);
-    colorMap.put("darkgoldenrod", 0XFFB8860B);
-    colorMap.put("darkgray", 0XFFA9A9A9);
-    colorMap.put("darkgreen", 0XFF006400);
-    colorMap.put("darkkhaki", 0XFFBDB76B);
-    colorMap.put("darkmagenta", 0XFF8B008B);
-    colorMap.put("darkolivegreen", 0XFF556B2F);
-    colorMap.put("darkorange", 0XFFFF8C00);
-    colorMap.put("darkorchid", 0XFF9932CC);
-    colorMap.put("darkred", 0XFF8B0000);
-    colorMap.put("darksalmon", 0XFFE9967A);
-    colorMap.put("darkseagreen", 0XFF8FBC8F);
-    colorMap.put("darkslateblue", 0XFF483D8B);
-    colorMap.put("darkslategray", 0XFF2F4F4F);
-    colorMap.put("darkslategrey", 0XFF2F4F4F);
-    colorMap.put("darkturquoise", 0XFF00CED1);
-    colorMap.put("darkviolet", 0XFF9400D3);
-    colorMap.put("deeppink", 0XFFFF1493);
-    colorMap.put("deepskyblue", 0XFF00BFFF);
-    colorMap.put("dimgray", 0XFF696969);
-    colorMap.put("dimgrey", 0XFF696969);
-    colorMap.put("dodgerblue", 0XFF1E90FF);
-    colorMap.put("firebrick", 0XFFB22222);
-    colorMap.put("floralwhite", 0XFFFFFAF0);
-    colorMap.put("forestgreen", 0XFF228B22);
-    colorMap.put("fuchsia", 0XFFFF00FF);
-    colorMap.put("gainsboro", 0XFFDCDCDC);
-    colorMap.put("ghostwhite", 0XFFF8F8FF);
-    colorMap.put("gold", 0XFFFFD700);
-    colorMap.put("goldenrod", 0XFFDAA520);
-    colorMap.put("gray", 0XFF808080);
-    colorMap.put("grey", 0XFF808080);
-    colorMap.put("green", 0XFF008000);
-    colorMap.put("greenyellow", 0XFFADFF2F);
-    colorMap.put("honeydew", 0XFFF0FFF0);
-    colorMap.put("hotpink", 0XFFFF69B4);
-    colorMap.put("indianred", 0XFFCD5C5C);
-    colorMap.put("indigo", 0XFF4B0082);
-    colorMap.put("ivory", 0XFFFFFFF0);
-    colorMap.put("khaki", 0XFFF0E68C);
-    colorMap.put("lavender", 0XFFE6E6FA);
-    colorMap.put("lavenderblush", 0XFFFFF0F5);
-    colorMap.put("lawngreen", 0XFF7CFC00);
-    colorMap.put("lemonchiffon", 0XFFFFFACD);
-    colorMap.put("lightblue", 0XFFADD8E6);
-    colorMap.put("lightcoral", 0XFFF08080);
-    colorMap.put("lightcyan", 0XFFE0FFFF);
-    colorMap.put("lightgoldenrodyellow", 0XFFFAFAD2);
-    colorMap.put("lightgray", 0XFFD3D3D3);
-    colorMap.put("lightgrey", 0XFFD3D3D3);
-    colorMap.put("lightgreen", 0XFF90EE90);
-    colorMap.put("lightpink", 0XFFFFB6C1);
-    colorMap.put("lightsalmon", 0XFFFFA07A);
-    colorMap.put("lightseagreen", 0XFF20B2AA);
-    colorMap.put("lightskyblue", 0XFF87CEFA);
-    colorMap.put("lightslategray", 0XFF778899);
-    colorMap.put("lightslategrey", 0XFF778899);
-    colorMap.put("lightsteelblue", 0XFFB0C4DE);
-    colorMap.put("lightyellow", 0XFFFFFFE0);
-    colorMap.put("lime", 0XFF00FF00);
-    colorMap.put("limegreen", 0XFF32CD32);
-    colorMap.put("linen", 0XFFFAF0E6);
-    colorMap.put("magenta", 0XFFFF00FF);
-    colorMap.put("maroon", 0XFF800000);
-    colorMap.put("mediumaquamarine", 0XFF66CDAA);
-    colorMap.put("mediumblue", 0XFF0000CD);
-    colorMap.put("mediumorchid", 0XFFBA55D3);
-    colorMap.put("mediumpurple", 0XFF9370DB);
-    colorMap.put("mediumseagreen", 0XFF3CB371);
-    colorMap.put("mediumslateblue", 0XFF7B68EE);
-    colorMap.put("mediumspringgreen", 0XFF00FA9A);
-    colorMap.put("mediumturquoise", 0XFF48D1CC);
-    colorMap.put("mediumvioletred", 0XFFC71585);
-    colorMap.put("midnightblue", 0XFF191970);
-    colorMap.put("mintcream", 0XFFF5FFFA);
-    colorMap.put("mistyrose", 0XFFFFE4E1);
-    colorMap.put("moccasin", 0XFFFFE4B5);
-    colorMap.put("navajowhite", 0XFFFFDEAD);
-    colorMap.put("navy", 0XFF000080);
-    colorMap.put("oldlace", 0XFFFDF5E6);
-    colorMap.put("olive", 0XFF808000);
-    colorMap.put("olivedrab", 0XFF6B8E23);
-    colorMap.put("orange", 0XFFFFA500);
-    colorMap.put("orangered", 0XFFFF4500);
-    colorMap.put("orchid", 0XFFDA70D6);
-    colorMap.put("palegoldenrod", 0XFFEEE8AA);
-    colorMap.put("palegreen", 0XFF98FB98);
-    colorMap.put("paleturquoise", 0XFFAFEEEE);
-    colorMap.put("palevioletred", 0XFFDB7093);
-    colorMap.put("papayawhip", 0XFFFFEFD5);
-    colorMap.put("peachpuff", 0XFFFFDAB9);
-    colorMap.put("peru", 0XFFCD853F);
-    colorMap.put("pink", 0XFFFFC0CB);
-    colorMap.put("plum", 0XFFDDA0DD);
-    colorMap.put("powderblue", 0XFFB0E0E6);
-    colorMap.put("purple", 0XFF800080);
-    colorMap.put("rebeccapurple", 0XFF663399);
-    colorMap.put("red", 0XFFFF0000);
-    colorMap.put("rosybrown", 0XFFBC8F8F);
-    colorMap.put("royalblue", 0XFF4169E1);
-    colorMap.put("saddlebrown", 0XFF8B4513);
-    colorMap.put("salmon", 0XFFFA8072);
-    colorMap.put("sandybrown", 0XFFF4A460);
-    colorMap.put("seagreen", 0XFF2E8B57);
-    colorMap.put("seashell", 0XFFFFF5EE);
-    colorMap.put("sienna", 0XFFA0522D);
-    colorMap.put("silver", 0XFFC0C0C0);
-    colorMap.put("skyblue", 0XFF87CEEB);
-    colorMap.put("slateblue", 0XFF6A5ACD);
-    colorMap.put("slategray", 0XFF708090);
-    colorMap.put("slategrey", 0XFF708090);
-    colorMap.put("snow", 0XFFFFFAFA);
-    colorMap.put("springgreen", 0XFF00FF7F);
-    colorMap.put("steelblue", 0XFF4682B4);
-    colorMap.put("tan", 0XFFD2B48C);
-    colorMap.put("teal", 0XFF008080);
-    colorMap.put("thistle", 0XFFD8BFD8);
-    colorMap.put("tomato", 0XFFFF6347);
-    colorMap.put("turquoise", 0XFF40E0D0);
-    colorMap.put("violet", 0XFFEE82EE);
-    colorMap.put("wheat", 0XFFF5DEB3);
-    colorMap.put("white", 0XFFFFFFFF);
-    colorMap.put("whitesmoke", 0XFFF5F5F5);
-    colorMap.put("yellow", 0XFFFFFF00);
-    colorMap.put("yellowgreen", 0XFF9ACD32);
-    colorMap.put("transparent", 0x00000000);
-  }
-
-  public static int getColor(String color) {
-    return getColor(color, Integer.MIN_VALUE);
-  }
-
-  public static int getColor(String color, int defaultColor) {
-    if (TextUtils.isEmpty(color)) {
-      return defaultColor;
-    }
-    color = color.trim(); //remove non visible codes
-
-    Integer cache = WXUtils.sCache.get(color);
-    if(cache!=null){
-      return cache;
-    }
-    else {
-      int resultColor = defaultColor;
-      Pair<Boolean, Integer> result;
-      ColorConvertHandler[] handlers = ColorConvertHandler.values();
-      for (ColorConvertHandler handler : handlers) {
-        try {
-          result = handler.handle(color);
-          if (result.first) {
-            resultColor = result.second;
-            WXUtils.sCache.put(color, resultColor);
-            break;
-          }
-        } catch (RuntimeException e) {
-          WXLogUtils.v("Color_Parser", WXLogUtils.getStackTrace(e));
-        }
-      }
-      return resultColor;
-    }
-  }
-
-  /**
-   * Assembly gradients
-   * @param image gradient values contains direction、colors
-   * @param width component width
-   * @param height component height
-   * @return gradient shader
-   */
-  public static Shader getShader(String image, float width, float height) {
-    List<String> valueList = parseGradientValues(image);
-    if (valueList != null && valueList.size() == 3) {
-      float[] points = parseGradientDirection(valueList.get(0), width, height);
-      Shader shader = new LinearGradient(points[0], points[1],
-              points[2], points[3],
-              getColor(valueList.get(1), Color.WHITE), getColor(valueList.get(2), Color.WHITE),
-              Shader.TileMode.CLAMP);
-      return shader;
-    }
-    return null;
-  }
-
-  /**
-   * parse gradient values contains direction、colors
-   * @param image gradient values
-   * @return split values by comma
-   */
-  @NonNull
-  private static List<String> parseGradientValues(String image) {
-    if (TextUtils.isEmpty(image)) {
-      return null;
-    }
-    image.trim();
-    if(image.startsWith("linear-gradient")){
-      String valueStr = image.substring(image.indexOf("(") + 1, image.lastIndexOf(")"));
-      StringTokenizer tokenizer = new StringTokenizer(valueStr, ",");
-      List<String> values = new ArrayList<>();
-      String temp = null;
-      while (tokenizer.hasMoreTokens()) {
-        String token = tokenizer.nextToken();
-        if (token.contains("(")) {
-          temp = token + ",";
-          continue;
-        }
-        if (token.contains(")")) {
-          temp += token;
-          values.add(temp);
-          temp = null;
-          continue;
-        }
-        if (temp != null) {
-          temp += (token + ",");
-          continue;
-        }
-        values.add(token);
-      }
-      return values;
-    }
-    return null;
-  }
-
-  /**
-   * parse gradient direction
-   * @param direction gradient direction
-   * @param width component width
-   * @param height component height
-   * @return gradient points
-   */
-  private static float[] parseGradientDirection(String direction, float width, float height) {
-    int x1 = 0, y1 = 1, x2 = 2, y2 = 3;
-    float[] points = {0, 0, 0, 0};
-
-    if (!TextUtils.isEmpty(direction)) {
-      direction = direction.replaceAll("\\s*", "").toLowerCase(Locale.ROOT);
-    }
-
-    switch (direction) {
-      //to right
-      case "toright":
-        points[x2] = width;
-        break;
-      //to left
-      case "toleft":
-        points[x1] = width;
-        break;
-      //to bottom
-      case "tobottom":
-        points[y2] = height;
-        break;
-      //to top
-      case "totop":
-        points[y1] = height;
-        break;
-      //to bottom right
-      case "tobottomright":
-        points[x2] = width;
-        points[y2] = height;
-        break;
-      //to top left
-      case "totopleft":
-        points[x1] = width;
-        points[y1] = height;
-        break;
-    }
-    return points;
-  }
-
-  public static boolean isNamedColor(String name) {
-    return colorMap.containsKey(name);
-  }
-
-  enum ColorConvertHandler {
-    NAMED_COLOR_HANDLER {
-      @Override
-      @NonNull Pair<Boolean, Integer> handle(String rawColor) {
-        if (colorMap.containsKey(rawColor)) {
-          return new Pair<>(Boolean.TRUE, colorMap.get(rawColor));
-        } else {
-          return new Pair<>(Boolean.FALSE, Color.TRANSPARENT);
-        }
-      }
-    },
-    RGB_HANDLER {
-      @Override
-      @NonNull Pair<Boolean, Integer> handle(String rawColor) {
-        if (rawColor.length() == 4) {
-          //#eee, #333
-          int r, g, b;
-          r = Integer.parseInt(rawColor.substring(1, 2), HEX);
-          g = Integer.parseInt(rawColor.substring(2, 3), HEX);
-          b = Integer.parseInt(rawColor.substring(3, 4), HEX);
-          return new Pair<>(Boolean.TRUE, Color.rgb(r + (r << 4), g + (g << 4), b + (b << 4)));
-        } else if (rawColor.length() == 7 || rawColor.length() == 9) {
-          //#eeeeee, #333333
-          return new Pair<>(Boolean.TRUE, Color.parseColor(rawColor));
-        } else {
-          return new Pair<>(Boolean.FALSE, Color.TRANSPARENT);
-        }
-      }
-    },
-    FUNCTIONAL_RGB_HANDLER {
-      @Override
-      @NonNull Pair<Boolean, Integer> handle(String rawColor) {
-        SingleFunctionParser<Integer> functionParser = new SingleFunctionParser<>(rawColor, FUNCTIONAL_RGB_MAPPER);
-        List<Integer> rgb = functionParser.parse(RGB);
-        if (null != rgb && rgb.size() == RGB_SIZE) {
-          return new Pair<>(Boolean.TRUE, Color.rgb(rgb.get(0), rgb.get(1), rgb.get(2)));
-        } else {
-          return new Pair<>(Boolean.FALSE, Color.TRANSPARENT);
-        }
-      }
-    },
-
-    FUNCTIONAL_RGBA_HANDLER {
-      @Override
-      @NonNull Pair<Boolean, Integer> handle(String rawColor) {
-        SingleFunctionParser<Number> functionParser = new SingleFunctionParser<>(rawColor, FUNCTIONAL_RGBA_MAPPER);
-        List<Number> rgba = functionParser.parse(RGBA);
-        if (rgba.size() == RGBA_SIZE) {
-          return new Pair<>(Boolean.TRUE, Color.argb(
-                  parseAlpha(rgba.get(3).floatValue()),
-                  rgba.get(0).intValue(),
-                  rgba.get(1).intValue(),
-                  rgba.get(2).intValue()));
-        } else {
-          return new Pair<>(Boolean.FALSE, Color.TRANSPARENT);
-        }
-      }
-    };
-
-    /**
-     * Parse color to #RRGGBB or #AARRGGBB. The parsing algorithm depends on sub-class.
-     *
-     * @param rawColor color, maybe functional RGB(RGBA), #RGB, keywords color or transparent
-     * @return #RRGGBB or #AARRGGBB
-     */
-    @NonNull abstract Pair<Boolean, Integer> handle(String rawColor);
-
-    /**
-     * Parse alpha gradient of color from range 0-1 to range 0-255
-     *
-     * @param alpha the alpha value, in range 0-1
-     * @return the alpha value, in range 0-255
-     */
-    private static int parseAlpha(float alpha) {
-      return (int) (alpha * COLOR_RANGE);
-    }
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXSoInstallMgrSdk.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXSoInstallMgrSdk.java
deleted file mode 100644
index dff071e..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXSoInstallMgrSdk.java
+++ /dev/null
@@ -1,607 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.annotation.SuppressLint;
-import android.app.Application;
-import android.content.Context;
-import android.content.pm.ApplicationInfo;
-import android.os.Build;
-import android.text.TextUtils;
-import com.taobao.weex.IWXStatisticsListener;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.adapter.IWXSoLoaderAdapter;
-import com.taobao.weex.adapter.IWXUserTrackAdapter;
-import com.taobao.weex.common.WXErrorCode;
-import dalvik.system.PathClassLoader;
-import java.io.File;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.lang.reflect.Field;
-import java.nio.ByteBuffer;
-import java.nio.channels.FileChannel;
-import java.util.Enumeration;
-import java.util.Locale;
-import java.util.zip.ZipEntry;
-import java.util.zip.ZipException;
-import java.util.zip.ZipFile;
-
-
-/**
- * Utility class for managing so library, including load native library and version management.
- * <ol>
- *   <li>Load library<br>
- *     It Will try to use {@link System#loadLibrary(String)} to load native library. If it successes,
- *     the Android Framework will be responsible for managing library and library version.
- *     If it fails in case of some ceratin armebi-v7a architecture device, it will try to extract
- *     native library from apk and copy it the data directory of the app. Then load it using
- *     {@link System#load(String)}.
- *     </li>
- *  <li>
- *       Version control for extracting native library from apk.
- *  </li>
- * </ol>
- */
-public class WXSoInstallMgrSdk {
-
-  final static String LOGTAG = "INIT_SO";
-  //below is the CPU string types
-  private final static String ARMEABI = "armeabi"; //default
-  private final static String X86 = "x86";
-  private final static String MIPS = "mips";
-  private final static String STARTUPSO = "/libweexjsb.so";
-  private final static String STARTUPSOANDROID15 = "/libweexjst.so";
-
-  static Application mContext = null;
-  private static IWXSoLoaderAdapter mSoLoader = null;
-  private static IWXStatisticsListener mStatisticsListener = null;
-
-  private static String mAbi = null;
-
-  public static void init(Application c,
-                          IWXSoLoaderAdapter loader,
-                          IWXStatisticsListener listener) {
-    mContext = c;
-    mSoLoader = loader;
-    mStatisticsListener = listener;
-  }
-
-  public static boolean isX86(){
-    String cpuType = _cpuType();
-    return cpuType.equalsIgnoreCase(X86);
-  }
-
-  public static boolean isCPUSupport(){
-    String cpuType = _cpuType();
-    return !cpuType.equalsIgnoreCase(MIPS);
-  }
-
-  /**
-   * Load so library.
-   *
-   * If a library loader adapter exists, use this adapter to load library,
-   * otherwise use {@link System#loadLibrary(String)} to load library.
-   * If failed to load library, try to extract the so library and load it
-   * from arembi in the .apk
-   *
-   * @param libName library name, like webp, not necessary to be libwep.so
-   * @param version the version of the so library
-   */
-  public static boolean initSo(String libName, int version, IWXUserTrackAdapter utAdapter) {
-    String cpuType = _cpuType();
-    if (cpuType.equalsIgnoreCase(MIPS) ) {
-      WXExceptionUtils.commitCriticalExceptionRT(null,
-              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
-              "initSo", "[WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT] for android cpuType is MIPS",
-              null);
-      return false;
-    }
-
-    // copy startup so
-    if (WXEnvironment.CORE_SO_NAME.equals(libName)) {
-      copyStartUpSo();
-    }
-
-
-    boolean InitSuc = false;
-      try {
-        // If a library loader adapter exists, use this adapter to load library
-        // instead of System.loadLibrary.
-        if (mSoLoader != null) {
-          mSoLoader.doLoadLibrary("c++_shared");
-        } else {
-          System.loadLibrary("c++_shared");
-        }
-      } catch (Exception | Error e) {
-        WXExceptionUtils.commitCriticalExceptionRT(null,
-                WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
-                "initSo",
-                        "load c++_shared failed Detail Error is: " +e.getMessage(),
-                null);
-
-        if(WXEnvironment.isApkDebugable()) {
-          throw e;
-        }
-      }
-
-      /**
-       * Load library with {@link System#loadLibrary(String)}
-       */
-      try {
-        // If a library loader adapter exists, use this adapter to load library
-        // instead of System.loadLibrary.
-        if (mSoLoader != null) {
-          mSoLoader.doLoadLibrary(libName);
-        } else {
-          System.loadLibrary(libName);
-        }
-
-        InitSuc = true;
-      } catch (Exception | Error e2) {
-        if (cpuType.contains(ARMEABI) || cpuType.contains(X86)) {
-          WXExceptionUtils.commitCriticalExceptionRT(null,
-                  WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
-                  "initSo", libName + "[WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT] for android cpuType is " +cpuType +
-                          "\n Detail Error is: " +e2.getMessage(),
-                  null);
-        }
-
-        if(WXEnvironment.isApkDebugable()) {
-          throw e2;
-        }
-        InitSuc = false;
-      }
-
-//      try {
-
-//        if (!InitSuc) {
-//
-//          //File extracted from apk already exists.
-//          if (isExist(libName, version)) {
-//            boolean res = _loadUnzipSo(libName, version, utAdapter);
-//            if (res) {
-//              return res;
-//            } else {
-//              //Delete the corrupt so library, and extract it again.
-//              removeSoIfExit(libName, version);
-//            }
-//          }
-//
-//          //Fail for loading file from libs, extract so library from so and load it.
-//          if (cpuType.equalsIgnoreCase(MIPS)) {
-//            return false;
-//          } else {
-//            try {
-//              InitSuc = unZipSelectedFiles(libName, version, utAdapter);
-//            } catch (IOException e2) {
-//              e2.printStackTrace();
-//            }
-//          }
-//
-//        }
-//      } catch (Exception | Error e) {
-//        InitSuc = false;
-//        e.printStackTrace();
-//      }
-  //  }
-    return InitSuc;
-  }
-
-  private static File _desSoCopyFile(String soName) {
-    String cpuType = _cpuType();
-    String copyPath = WXEnvironment.copySoDesDir();
-    if (TextUtils.isEmpty(copyPath)) {
-      return null;
-    }
-    File desDir = new File(copyPath, soName + "/" + cpuType);
-    return desDir;
-  }
-
-  /**
-   * copyStartUpSo
-   */
-  @SuppressLint("SdCardPath")
-  public static void copyStartUpSo() {
-    try {
-      // copy libjsb.so to cache/weex/jsb/cputype
-      String pkgName = WXEnvironment.getApplication().getPackageName();
-      String cacheFile = WXEnvironment.getApplication().getApplicationContext().getCacheDir().getPath();
-
-      // cp weexjsb any way
-      // if android api < 16 copy libweexjst.so else copy libweexjsb.so
-      boolean pieSupport = true;
-      File newfile;
-      String startSoName = WXEnvironment.CORE_JSB_SO_NAME;
-      String startSoPath = STARTUPSO;
-      if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
-        pieSupport = false;
-        startSoName = WXEnvironment.CORE_JST_SO_NAME;
-        startSoPath = STARTUPSOANDROID15;
-      }
-
-      final File copyPath = _desSoCopyFile(startSoName);
-      if(!copyPath.exists()) {
-        copyPath.mkdirs();
-      }
-      newfile = new File(copyPath, startSoPath);
-      WXEnvironment.CORE_JSB_SO_PATH = newfile.getAbsolutePath();
-      String jsb = WXEnvironment.getDefaultSettingValue(startSoName, "-1");
-      if(newfile.exists() && TextUtils.equals(WXEnvironment.getAppVersionName(), jsb)) {
-        // no update so skip copy
-        return;
-      }
-
-      String path = "/data/data/" + pkgName + "/lib";
-      if (cacheFile != null && cacheFile.indexOf("/cache") > 0) {
-        path = cacheFile.replace("/cache", "/lib");
-      }
-      File oldfile = null;
-      if (pieSupport) {
-        oldfile = new File(path, STARTUPSO);
-      } else {
-        oldfile = new File(path , STARTUPSOANDROID15);
-      }
-
-
-      if (!oldfile.exists()) {
-        try {
-          String weexjsb = ((PathClassLoader) (WXSoInstallMgrSdk.class.getClassLoader())).findLibrary(startSoName);
-          oldfile = new File(weexjsb);
-        } catch (Throwable throwable) {
-          // do nothing
-        }
-      }
-
-
-      if(!oldfile.exists()) {
-        String extractSoPath = WXEnvironment.extractSo();
-        oldfile = new File(extractSoPath, STARTUPSO);
-      }
-
-      if (oldfile.exists()) {
-        WXFileUtils.copyFile(oldfile, newfile);
-      }
-      WXEnvironment.writeDefaultSettingsValue(startSoName, WXEnvironment.getAppVersionName());
-    } catch (Throwable e) {
-      e.printStackTrace();
-    }
-  }
-
-  public static void copyJssRuntimeSo(){
-    boolean tryUseRunTimeApi = WXUtils.checkGreyConfig("wxapm","use_runtime_api","0");
-    WXLogUtils.e("weex", "tryUseRunTimeApi ? "+ tryUseRunTimeApi);
-    if (!tryUseRunTimeApi){
-      return;
-    }
-    try {
-      WXLogUtils.e("weex", "copyJssRuntimeSo: ");
-      File toPath = _desSoCopyFile(WXEnvironment.CORE_JSS_SO_NAME);
-      if(!toPath.exists()) {
-        toPath.mkdirs();
-      }
-      File targetFile = new File(toPath,"libweexjss.so");
-
-      /** 1. check so and versionCode. if update, then rm old jss.so(runtime) in pkg/libs, and copy new so from apk **/
-      String keyVersionCode = "app_version_code_weex";
-      String defaultSettingValue = WXEnvironment.getDefaultSettingValue(keyVersionCode, "-1");
-
-
-      if (targetFile.exists()){
-        if (!TextUtils.equals(WXEnvironment.getAppVersionName(),defaultSettingValue)){
-          targetFile.delete();
-        }else {
-          WXEnvironment.CORE_JSS_RUNTIME_SO_PATH= targetFile.getAbsolutePath();
-          WXEnvironment.sUseRunTimeApi = true;
-          WXLogUtils.e("weex", "copyJssRuntimeSo exist:  return");
-          return;
-        }
-      }
-      /** 2. copy jss(runtime) so **/
-      String fromPath =  ((PathClassLoader) (WXSoInstallMgrSdk.class.getClassLoader())).findLibrary("weexjssr");
-      if (TextUtils.isEmpty(fromPath)){
-        return;
-      }
-      targetFile.createNewFile();
-      WXFileUtils.copyFileWithException(new File(fromPath),targetFile);
-      /**3. update flag **/
-      WXEnvironment.CORE_JSS_RUNTIME_SO_PATH= targetFile.getAbsolutePath();
-      WXEnvironment.writeDefaultSettingsValue(keyVersionCode,WXEnvironment.getAppVersionName());
-      WXEnvironment.sUseRunTimeApi = true;
-      WXLogUtils.e("weex", "copyJssRuntimeSo: cp end and return ");
-    }catch (Throwable e){
-      e.printStackTrace();
-      WXEnvironment.sUseRunTimeApi = false;
-      WXLogUtils.e("weex", "copyJssRuntimeSo:  exception" + e);
-    }
-  }
-
-  private static String _getFieldReflectively(Build build, String fieldName) {
-    try {
-      final Field field = Build.class.getField(fieldName);
-      return field.get(build).toString();
-    } catch (Exception ex) {
-      return "Unknown";
-    }
-  }
-
-  public static String _cpuType() {
-    if(TextUtils.isEmpty(mAbi)) {
-      try {
-        mAbi = Build.CPU_ABI;
-      }catch (Throwable e){
-        e.printStackTrace();
-        mAbi = ARMEABI;
-      }
-      if (TextUtils.isEmpty(mAbi)){
-        mAbi = ARMEABI;
-      }
-      mAbi = mAbi.toLowerCase(Locale.ROOT);
-    }
-    return mAbi;
-  }
-
-  /**
-   *
-   * @param libName lib name
-   * @param size  the right size of lib
-   * @return true for valid  ; false for InValid
-   */
-  static boolean checkSoIsValid(String libName, long size) {
-    Context context = mContext;
-    if (null == context) {
-      return false;
-    }
-    try{
-      long start=System.currentTimeMillis();
-      if(WXSoInstallMgrSdk.class.getClassLoader() instanceof PathClassLoader ) {
-
-        String path = ((PathClassLoader) (WXSoInstallMgrSdk.class.getClassLoader())).findLibrary(libName);
-        if(TextUtils.isEmpty(path) ){
-          return false;
-        }
-        File file = new File(path);
-
-        if (!file.exists() || size == file.length()) {
-          WXLogUtils.w("weex so size check path :" + path+"   "+(System.currentTimeMillis() - start));
-          return true;
-        } else {
-          return false;
-        }
-      }
-    }catch(Throwable e ){
-      WXExceptionUtils.commitCriticalExceptionRT(null,
-              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
-              "checkSoIsValid", "[WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT] for " +
-                      "weex so size check fail exception :"+e.getMessage(),
-              null);
-      WXLogUtils.e("weex so size check fail exception :"+e.getMessage());
-    }
-
-    return true;
-  }
-
-  /**
-   * Concatenate the path of the so library, including directory.
-   * @param libName the raw name of the lib
-   * @param version the version of the so library
-   * @return the path of the so library
-   */
-  @SuppressLint("SdCardPath")
-  static String _targetSoFile(String libName, int version) {
-    Context context = mContext;
-    if (null == context) {
-      return "";
-    }
-
-    String path = "/data/data/" + context.getPackageName() + "/files";
-
-    File f = context.getFilesDir();
-    if (f != null) {
-      path = f.getPath();
-    }
-    return path + "/lib" + libName + "bk" + version + ".so";
-
-  }
-
-  /**
-   * Remove the so library if it had been extracted.
-   * @param libName
-   * @param version
-   */
-  static void removeSoIfExit(String libName, int version) {
-
-    String file = _targetSoFile(libName, version);
-    File a = new File(file);
-    if (a.exists()) {
-      a.delete();
-    }
-
-  }
-
-  /**
-   * Tell whether the so is extracted.
-   */
-  static boolean isExist(String libName, int version) {
-
-    String file = _targetSoFile(libName, version);
-    File a = new File(file);
-    return a.exists();
-
-  }
-
-
-  /**
-   * Load .so library
-   */
-  @SuppressLint("UnsafeDynamicallyLoadedCode")
-  static boolean _loadUnzipSo(String libName,
-                              int version,
-                              IWXUserTrackAdapter utAdapter) {
-    boolean initSuc = false;
-    try {
-      if (isExist(libName, version)) {
-        // If a library loader adapter exists, use this adapter to load library
-        // instead of System.load.
-        if (mSoLoader != null) {
-          mSoLoader.doLoad(_targetSoFile(libName, version));
-        } else {
-          System.load(_targetSoFile(libName, version));
-        }
-      }
-      initSuc = true;
-    } catch (Throwable e) {
-      initSuc = false;
-      WXExceptionUtils.commitCriticalExceptionRT(null,
-              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT,
-              "_loadUnzipSo", "[WX_KEY_EXCEPTION_SDK_INIT_WX_ERR_COPY_FROM_APK] " +
-                      "\n Detail Msg is : " +  e.getMessage(),
-              null);
-      WXLogUtils.e("", e);
-    }
-    return initSuc;
-  }
-
-  static boolean unZipSelectedFiles(String libName,
-                                    int version,
-                                    IWXUserTrackAdapter utAdapter) throws ZipException, IOException {
-    String sourcePath = "lib/armeabi/lib" + libName + ".so";
-
-    String zipPath = "";
-    Context context = mContext;
-    if (context == null) {
-      return false;
-    }
-
-    ApplicationInfo aInfo = context.getApplicationInfo();
-    if (null != aInfo) {
-      zipPath = aInfo.sourceDir;
-    }
-
-    ZipFile zf;
-    zf = new ZipFile(zipPath);
-    try {
-
-      for (Enumeration<?> entries = zf.entries(); entries.hasMoreElements(); ) {
-        ZipEntry entry = ((ZipEntry) entries.nextElement());
-        if (entry.getName().startsWith(sourcePath)) {
-
-          InputStream in = null;
-          FileOutputStream os = null;
-          FileChannel channel = null;
-          int total = 0;
-          try {
-
-            //Make sure the old library is deleted.
-            removeSoIfExit(libName, version);
-
-            //Copy file
-            in = zf.getInputStream(entry);
-            os = context.openFileOutput("lib" + libName + "bk" + version + ".so",
-                    Context.MODE_PRIVATE);
-            channel = os.getChannel();
-
-            byte[] buffers = new byte[1024];
-            int realLength;
-
-            while ((realLength = in.read(buffers)) > 0) {
-              //os.write(buffers);
-              channel.write(ByteBuffer.wrap(buffers, 0, realLength));
-              total += realLength;
-
-            }
-          } finally {
-            if (in != null) {
-              try {
-                in.close();
-              } catch (Exception e) {
-                e.printStackTrace();
-              }
-            }
-
-            if (channel != null) {
-              try {
-                channel.close();
-              } catch (Exception e) {
-                e.printStackTrace();
-              }
-            }
-
-            if (os != null) {
-              try {
-                os.close();
-              } catch (Exception e) {
-                e.printStackTrace();
-              }
-            }
-
-            if (zf != null) {
-              zf.close();
-              zf = null;
-            }
-          }
-
-          if (total > 0) {
-            return _loadUnzipSo(libName, version, utAdapter);
-          } else {
-            return false;
-          }
-        }
-      }
-    } catch (java.io.IOException e) {
-      e.printStackTrace();
-      WXExceptionUtils.commitCriticalExceptionRT(null,
-              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT,
-              "unZipSelectedFiles", "[WX_KEY_EXCEPTION_SDK_INIT_unZipSelectedFiles] " +
-                      "\n Detail msg is: " + e.getMessage(),
-              null);
-
-    } finally {
-
-      if (zf != null) {
-        zf.close();
-        zf = null;
-      }
-    }
-    return false;
-  }
-
-  /**
-   * Using {@Code WXExceptionUtils.commitCriticalExceptionRT}  insted
-   */
-//  static void commit(IWXUserTrackAdapter utAdapter, String errCode, String errMsg) {
-//    if (mStatisticsListener != null) {
-//      mStatisticsListener.onException("0", errCode, errMsg);
-//    }
-//
-//    if (utAdapter == null) {
-//      return;
-//    }
-//    if (errCode != null && errMsg != null) {
-//      WXPerformance p = new WXPerformance();
-//      p.errCode = errCode;
-//      p.errMsg = errMsg;
-//      utAdapter.commit(null, null, WXEnvironment.ENVIRONMENT, p, null);
-//    } else {
-//      utAdapter.commit(null, null, WXEnvironment.ENVIRONMENT, null, null);
-//
-//    }
-//  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXUtils.java
deleted file mode 100644
index 95bdfae..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXUtils.java
+++ /dev/null
@@ -1,597 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.app.ActivityManager;
-import android.content.Context;
-import android.content.res.Configuration;
-import android.os.Looper;
-import android.os.SystemClock;
-import android.support.annotation.Nullable;
-import android.support.v4.util.LruCache;
-import android.text.TextUtils;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.adapter.IWXConfigAdapter;
-import com.taobao.weex.common.Constants;
-
-public class WXUtils {
-
-  final static LruCache<String, Integer> sCache = new LruCache<>(64);
-  public static final char PERCENT = '%';
-  private static final int HUNDRED =100;
-  /**
-   * Tell whether current thread is UI(main) thread.
-   * @return true for UI(main) thread
-   */
-  public static boolean isUiThread() {
-    return Thread.currentThread().getId() == Looper.getMainLooper().getThread().getId();
-  }
-
-  public static boolean isUndefined(float value) {
-    return Float.isNaN(value);
-  }
-
-
-  public static float getFloatByViewport(Object value, int viewport) {
-    if (value == null) {
-      return Float.NaN;
-    }
-    String temp = value.toString().trim();
-    if (Constants.Name.AUTO.equals(temp)
-            || Constants.Name.UNDEFINED.equals(temp)
-            || TextUtils.isEmpty(temp)) {
-      WXLogUtils.e("Argument Warning ! value is " + temp + "And default Value:" + Float.NaN);
-      return Float.NaN;
-    }
-
-    if (temp.endsWith("wx")) {
-      try {
-        return transferWx(temp, viewport);
-      } catch (NumberFormatException e) {
-        WXLogUtils.e("Argument format error! value is " + value, e);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    } else if (temp.endsWith("px")) {
-      try {
-        temp = temp.substring(0, temp.indexOf("px"));
-        return Float.parseFloat(temp);
-      } catch (NumberFormatException nfe) {
-        WXLogUtils.e("Argument format error! value is " + value, nfe);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    } else {
-      try {
-        return Float.parseFloat(temp);
-      } catch (NumberFormatException nfe) {
-        WXLogUtils.e("Argument format error! value is " + value, nfe);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }
-    return Float.NaN;
-  }
-
-  public static float getFloat(Object value) {
-    return getFloat(value, Float.NaN);
-  }
-
-  public static Float getFloat(Object value, @Nullable Float df) {
-    if (value == null) {
-      return df;
-    }
-
-    String temp = value.toString().trim();
-    if(Constants.Name.AUTO.equals(temp)
-            || Constants.Name.UNDEFINED.equals(temp)
-            || TextUtils.isEmpty(temp)){
-      WXLogUtils.e("Argument Warning ! value is " + temp + "And default Value:"+Float.NaN);
-      return df;
-    }
-    if (temp.endsWith("wx")) {
-      try {
-        return transferWx(temp, 750);
-      } catch (NumberFormatException e) {
-        WXLogUtils.e("Argument format error! value is " + value, e);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }else if (temp.endsWith("px")) {
-      try {
-        temp = temp.substring(0, temp.indexOf("px"));
-        return Float.parseFloat(temp);
-      } catch (NumberFormatException nfe) {
-        WXLogUtils.e("Argument format error! value is " + value, nfe);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }else {
-      try {
-        return Float.parseFloat(temp);
-      } catch (NumberFormatException nfe) {
-        WXLogUtils.e("Argument format error! value is " + value, nfe);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }
-    return df;
-  }
-
-  private static float transferWx(String stringWithWXPostfix, int viewport) {
-    if(null == stringWithWXPostfix) {
-      return 0;
-    }
-    String temp = stringWithWXPostfix;
-    if(stringWithWXPostfix.endsWith("wx")) {
-      temp = stringWithWXPostfix.substring(0, stringWithWXPostfix.indexOf("wx"));
-    }
-    Float f = Float.parseFloat(temp);
-    float density = WXEnvironment.sApplication.getResources().getDisplayMetrics().density;
-    return density * f * viewport / WXViewUtils.getScreenWidth();
-  }
-
-  public static float fastGetFloat(String raw, int precision){
-    if(!TextUtils.isEmpty(raw)){
-      boolean positive=true;
-      int loc=0;
-      if(raw.charAt(0)=='-'){
-        positive=false;
-        loc++;
-      }
-      else if(raw.charAt(0)=='+'){
-        loc++;
-      }
-
-      char digit;
-      float result=0;
-      while (loc<raw.length() && (digit=raw.charAt(loc))>='0'&&digit<='9'){
-        result=result*10+digit-'0';
-        loc++;
-      }
-
-      if(loc<raw.length()){
-        if(raw.charAt(loc)=='.'){
-          loc++;
-          int remainderLength=10;
-          int counter=0;
-          while(loc<raw.length() &&
-                  counter<precision &&
-                  ((digit=raw.charAt(loc))>='0'&& digit<='9')){
-            result+=(digit-'0')/(float)remainderLength;
-            remainderLength*=10;
-            loc++;
-            counter++;
-          }
-        }
-        else{
-          // throw new NumberFormatException("Illegal separator");
-        }
-      }
-
-      if(!positive)
-        result*=-1;
-      return result;
-    }
-    return 0;
-    // throw new NumberFormatException("NullNumber");
-  }
-
-  /**
-   * Parse string representation of float. This method intend to be faster than
-   * {@link Float#parseFloat(String)}, but less accuracy.
-   * @param raw
-   * @return
-   */
-  public static float fastGetFloat(String raw){
-    return fastGetFloat(raw, Integer.MAX_VALUE);
-  }
-
-  public static int parseInt(String value) {
-    try {
-      if (!TextUtils.isEmpty(value) && !value.contains(".")) {
-        return Integer.parseInt(value);
-      }
-    } catch (NumberFormatException e) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(WXLogUtils.getStackTrace(e));
-      }
-    }
-    return 0;
-  }
-
-  public static int parseInt(Object value) {
-    return parseInt(String.valueOf(value));
-  }
-
-  public static float parseFloat(Object value) {
-    return parseFloat(String.valueOf(value));
-  }
-
-  public static float parseFloat(String value) {
-    try {
-      if (!TextUtils.isEmpty(value) && !TextUtils.equals(value, "null")) {
-        return Float.parseFloat(value);
-      } else {
-        if (WXEnvironment.isApkDebugable()) {
-          WXLogUtils.e("WXUtils parseFloat illegal value is " + value);
-        }
-      }
-    } catch (NumberFormatException e) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.e(WXLogUtils.getStackTrace(e));
-      }
-    }
-    return 0;
-  }
-
-  public static int getInt(Object value) {
-    return getInteger(value, 0);
-  }
-
-  public static @Nullable Integer getInteger(@Nullable Object value, @Nullable Integer df) {
-
-    if (value == null) {
-      return df;
-    }
-
-    String temp = value.toString().trim();
-    String key = temp;
-    Integer cache = sCache.get(key);
-    if (cache != null) {
-      return cache;
-    } else {
-      Integer ret = df;
-      String suffix = "";
-      if (temp.length() >= 2) {
-        suffix = temp.substring(temp.length() - 2, temp.length());
-      }
-
-      if (TextUtils.equals("wx", suffix)) {
-        if (WXEnvironment.isApkDebugable()) {
-          WXLogUtils
-              .w("the value of " + value
-                  + " use wx unit, which will be not supported soon after.");
-        }
-        try {
-          ret = (int)transferWx(temp, 750);
-        } catch (NumberFormatException e) {
-          WXLogUtils.e("Argument format error! value is " + value, e);
-        } catch (Exception e) {
-          WXLogUtils.e("Argument error! value is " + value, e);
-        }
-      } else if (TextUtils.equals("px", suffix)) {
-        try {
-          temp = temp.substring(0, temp.length() - 2);
-          if (!TextUtils.isEmpty(temp) && temp.contains(".")) {
-            ret = (int)WXUtils.parseFloat(temp);
-          } else {
-            ret = Integer.parseInt(temp);
-          }
-        } catch (NumberFormatException nfe) {
-          WXLogUtils.e("Argument format error! value is " + value, nfe);
-        } catch (Exception e) {
-          WXLogUtils.e("Argument error! value is " + value, e);
-        }
-      } else {
-        try {
-          if (!TextUtils.isEmpty(temp)) {
-            if (temp.contains(".")) {
-              ret = (int)WXUtils.parseFloat(temp);
-            } else {
-              ret = Integer.parseInt(temp);
-            }
-          } else {
-            if (WXEnvironment.isApkDebugable()) {
-              WXLogUtils.e("Argument value is null, df is" + df);
-            }
-          }
-        } catch (NumberFormatException nfe) {
-          if (WXEnvironment.isApkDebugable()) {
-            WXLogUtils.w("The parameter format is not supported", nfe);
-          }
-        } catch (Exception e) {
-          WXLogUtils.e("Argument error! value is " + value, e);
-        }
-      }
-      if (ret != null && !ret.equals(df)) {
-        sCache.put(key, ret);
-      }
-      return ret;
-    }
-  }
-
-  /**
-   * Looks like no longer usage exists, Mark deprecate first.
-   * @param value
-   * @return
-   */
-  @Deprecated
-  public static long getLong(Object value) {
-    if (value == null) {
-      return 0;
-    }
-    long result = 0;
-    String temp = value.toString().trim();
-    if (temp.endsWith("wx")) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.w("the value of " + value + " use wx unit, which will be not supported soon after.");
-      }
-      try {
-        return (long)transferWx(temp, 750);
-      } catch (NumberFormatException e) {
-        WXLogUtils.e("Argument format error! value is " + value, e);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }else if (temp.endsWith("px")) {
-      try {
-        temp = temp.substring(0, temp.indexOf("px"));
-        return Long.parseLong(temp);
-      } catch (NumberFormatException nfe) {
-        WXLogUtils.e("Argument format error! value is " + value, nfe);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }else {
-      try {
-        return Long.parseLong(temp);
-      } catch (NumberFormatException nfe) {
-        WXLogUtils.e("Argument format error! value is " + value, nfe);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }
-    return result;
-  }
-
-  /**
-   * Looks like no longer usage exists, Mark deprecate first.
-   * @param value
-   * @return
-   */
-  @Deprecated
-  public static double getDouble(Object value) {
-    if (value == null) {
-      return 0;
-    }
-    double result = 0;
-    String temp = value.toString().trim();
-    if (temp.endsWith("wx")) {
-      if (WXEnvironment.isApkDebugable()) {
-        WXLogUtils.w("the value of " + value + " use wx unit, which will be not supported soon after.");
-      }
-      try {
-        return transferWx(temp, 750);
-      } catch (NumberFormatException e) {
-        WXLogUtils.e("Argument format error! value is " + value, e);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }else if (temp.endsWith("px")) {
-      try {
-        temp = temp.substring(0, temp.indexOf("px"));
-        return Double.parseDouble(temp);
-      } catch (NumberFormatException nfe) {
-        WXLogUtils.e("Argument format error! value is " + value, nfe);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }else {
-      try {
-        return Double.parseDouble(temp);
-      } catch (NumberFormatException nfe) {
-        WXLogUtils.e("Argument format error! value is " + value, nfe);
-      } catch (Exception e) {
-        WXLogUtils.e("Argument error! value is " + value, e);
-      }
-    }
-
-    return result;
-  }
-
-  @Deprecated
-  public static boolean isTabletDevice() {
-    try{
-      return (WXEnvironment.getApplication().getResources().getConfiguration().screenLayout & Configuration.SCREENLAYOUT_SIZE_MASK) >= Configuration.SCREENLAYOUT_SIZE_LARGE;
-    }catch (Exception e){
-      //
-    }
-    return false;
-  }
-
-  public static Boolean getBoolean(@Nullable Object value, @Nullable Boolean df) {
-
-    if (value == null)
-      return df;
-    if (TextUtils.equals("false",value.toString())) {
-      return false;
-    } else if (TextUtils.equals("true",value.toString())) {
-      return true;
-    }
-    return df;
-  }
-
-  public static long getAvailMemory(Context context){
-    ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
-    ActivityManager.MemoryInfo mi = new ActivityManager.MemoryInfo();
-    am.getMemoryInfo(mi);
-    //mi.availMem;
-    //return Formatter.formatFileSize(context, mi.availMem);
-    WXLogUtils.w("app AvailMemory ---->>>"+mi.availMem/(1024*1024));
-    return mi.availMem/(1024*1024);
-  }
-
-  public static String getString(@Nullable Object value,@Nullable String df) {
-
-    if (value == null)
-      return df;
-
-    String originValue;
-    if (value instanceof String) {
-      originValue = (String) value;
-    } else {
-      originValue = value.toString();
-    }
-
-    return originValue;
-  }
-
-  public static int parseUnitOrPercent(String raw, int unit) {
-    int suffix;
-    if ((suffix = raw.lastIndexOf(WXUtils.PERCENT)) != -1) {
-      return parsePercent(raw.substring(0, suffix), unit);
-    }
-    else {
-      return WXUtils.parseInt(raw);
-    }
-  }
-
-  private static int parsePercent(String raw, int unit){
-    return (int)(Float.parseFloat(raw) / HUNDRED * unit);
-  }
-
-  /**
-   * Get a banner data in JSON format from a bundle content.
-   * A bundle banner looks like below:
-   * \/*!count
-   *  * {
-   *  *   version: "0.2.1.20170104-release",
-   *  *   create: "20170207171112",
-   *  *   git: "banner--772c915",
-   *  *   digest: "c709b7f91867e371b24f54d6aeea232a"
-   *  * }
-   *  !*\/
-   *
-   * @param content a bundle content
-   * @return
-   */
-  public static String getBundleBanner(String content) {
-    final String commentBegin = "/*!";
-    final String commentEnd = "!*/";
-    final String asteriskRegex = "\\*";
-    final String replacement = "";
-
-    int offsetCountBegin = content.indexOf(commentBegin);
-    if (offsetCountBegin == -1) {
-      return null;
-    }
-    offsetCountBegin += commentBegin.length();
-    int offsetCountEnd = indexLineBreak(content, offsetCountBegin);
-    if (offsetCountEnd == -1) {
-      return null;
-    }
-    String countStr = content.substring(offsetCountBegin, offsetCountEnd);
-    int count = Integer.parseInt(countStr);
-
-    String commentBody = content.substring(offsetCountEnd + 1, offsetCountEnd + 1 + count);
-    int offsetBodyEnd = commentBody.lastIndexOf(commentEnd);
-    if (offsetBodyEnd == -1) {
-      return null;
-    }
-    commentBody = commentBody.substring(0, offsetBodyEnd);
-
-    StringBuilder commentBodyBuilder = new StringBuilder();
-    String[] items = splitLineBreak(commentBody);
-
-    for (String item : items) {
-      commentBodyBuilder.append(item.replaceFirst(asteriskRegex, replacement));
-    }
-
-    return commentBodyBuilder.toString();
-  }
-
-  private static int indexLineBreak(String str, int fromIndex) {
-    final String lineBreakIos = "\r";
-    final String lineBreakUnix = "\n";
-    final String linebreakWin = "\r\n";
-
-    int index = str.indexOf(lineBreakIos, fromIndex);
-    if (index == -1) {
-      index = str.indexOf(lineBreakUnix, fromIndex);
-    }
-    if (index == -1) {
-      index = str.indexOf(linebreakWin, fromIndex);
-    }
-
-    return index;
-  }
-
-  private static String[] splitLineBreak(String str) {
-    final String lineBreakIos = "\r";
-    final String lineBreakUnix = "\n";
-    final String linebreakWin = "\r\n";
-    String[] items = str.split(lineBreakIos);
-
-    if (items.length == 1) {
-      items = str.split(lineBreakUnix);
-    }
-    if (items.length == 1) {
-      items = str.split(linebreakWin);
-    }
-
-    return items;
-  }
-
-
-  
-  /**
-   * get number
-   * */
-  public static int getNumberInt(Object value, int defaultValue){
-    if(value == null){
-      return  defaultValue;
-    }
-    if(value instanceof  Number){
-      return  ((Number) value).intValue();
-    }
-    try{
-      String number = value.toString();
-      if(number.indexOf('.') >= 0) {
-        return (int) Float.parseFloat(value.toString());
-      }else{
-        return  Integer.parseInt(number);
-      }
-    }catch (Exception e){return  defaultValue;}
-  }
-
-  public static boolean checkGreyConfig(String group,String key,String defaultValue){
-      IWXConfigAdapter configAdapter = WXSDKManager.getInstance().getWxConfigAdapter();
-      if (null == configAdapter) {
-        return false;
-      }
-      double randomValue = Math.random() * 100;
-      double max = 100;
-      try {
-        String configValue = configAdapter.getConfig(group, key, defaultValue);
-        max = Double.valueOf(configValue);
-      } catch (Exception e) {
-        e.printStackTrace();
-      }
-      return randomValue < max;
-  }
-
-  private static final long sInterval = System.currentTimeMillis() - SystemClock.uptimeMillis();
-
-  public static long getFixUnixTime(){
-    return  sInterval + SystemClock.uptimeMillis();
-  }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXViewToImageUtil.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXViewToImageUtil.java
deleted file mode 100755
index b486fb5..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXViewToImageUtil.java
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.content.Context;
-import android.content.Intent;
-import android.graphics.Bitmap;
-import android.graphics.Color;
-import android.net.Uri;
-import android.os.Environment;
-import android.os.Handler;
-import android.os.Looper;
-import android.provider.MediaStore;
-import android.support.annotation.ColorInt;
-import android.view.View;
-
-import com.taobao.weex.WXSDKManager;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.io.IOException;
-
-/**
- * Created by miomin on 7/25/17.
- */
-public class WXViewToImageUtil {
-
-    public static int mBackgroundColor = Color.TRANSPARENT;
-
-    /**
-     * Generate image and return path via callback
-     */
-    public static void generateImage(final View imageView, final int width,
-                                     @ColorInt final int backgroundColor, final OnImageSavedCallback mOnImageSavedCallback) {
-
-        mBackgroundColor = backgroundColor;
-
-        // Only one save image task occurs at the same time
-        WXSDKManager.getInstance().getWXWorkThreadManager().post(new Thread(new Runnable() {
-            @Override
-            public void run() {
-                // Generate bitmap from ImageView
-                Bitmap bitmap = getBitmapFromImageView(imageView, width);
-
-                if (bitmap == null) {
-                    if (mOnImageSavedCallback != null) {
-                        mOnImageSavedCallback.onSaveFailed("Image is empty");
-                    }
-                    return;
-                }
-
-                // Sava bitmap to gallery
-                final String destPath = saveBitmapToGallery(imageView.getContext(), bitmap, mOnImageSavedCallback);
-
-                new Handler(Looper.getMainLooper()).post(new Runnable() {
-                    @Override
-                    public void run() {
-                        if (mOnImageSavedCallback != null) {
-                            mOnImageSavedCallback.onSaveSucceed(destPath);
-                            imageView.getContext().sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.parse(destPath)));
-                        }
-                    }
-                });
-            }
-        }));
-    }
-
-    /**
-     * Save bitmap to gallery
-     * @return image save path
-     */
-    public static String saveBitmapToGallery(Context context, Bitmap bitmap, final OnImageSavedCallback mOnImageSavedCallback) {
-
-        // Save image
-        File appDir = new File(Environment.getExternalStorageDirectory(), "Weex");
-        if (!appDir.exists()) {
-            appDir.mkdir();
-        }
-
-        String fileName = System.currentTimeMillis() + ".jpg";
-        File file = new File(appDir, fileName);
-
-        try {
-            FileOutputStream fos = new FileOutputStream(file);
-            bitmap.compress(Bitmap.CompressFormat.JPEG, 100, fos);
-            fos.flush();
-            fos.close();
-        } catch (FileNotFoundException e) {
-            if (mOnImageSavedCallback != null)
-                mOnImageSavedCallback.onSaveFailed("Image creation failed due to system reason");
-            e.printStackTrace();
-        } catch (IOException e) {
-            if (mOnImageSavedCallback != null)
-                mOnImageSavedCallback.onSaveFailed("Android IOException");
-            e.printStackTrace();
-        }
-
-        // Insert the image file into the system gallery
-        try {
-            MediaStore.Images.Media.insertImage(context.getContentResolver(),
-                    file.getAbsolutePath(), fileName, null);
-        } catch (FileNotFoundException e) {
-            e.printStackTrace();
-        }
-
-        // Notify the system gallery update
-        context.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.parse("file://" + appDir.getAbsolutePath() + "/" + fileName)));
-
-        return file.getAbsolutePath();
-    }
-
-    /**
-     * Save state callback
-     */
-    public interface OnImageSavedCallback {
-        void onSaveSucceed(String path);
-        void onSaveFailed(String errorDesc);
-    }
-
-    /**
-     * Get bitmap from imageview
-     */
-    public static Bitmap getBitmapFromImageView(final View view, int width) {
-        if (view.getWidth() <= 0 || view.getHeight() <= 0) {
-            view.measure(View.MeasureSpec.makeMeasureSpec(width, View.MeasureSpec.EXACTLY),
-                    View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED));
-            view.layout(0, 0, view.getMeasuredWidth(), view.getMeasuredHeight());
-        }
-
-        view.setDrawingCacheEnabled(true);
-        Bitmap bitmap = view.getDrawingCache();
-        return bitmap;
-    }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXViewUtils.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXViewUtils.java
deleted file mode 100644
index e6c0ee7..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXViewUtils.java
+++ /dev/null
@@ -1,598 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.annotation.SuppressLint;
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.PixelFormat;
-import android.graphics.Point;
-import android.graphics.RectF;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.ColorDrawable;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.LayerDrawable;
-import android.os.Build;
-import android.os.Build.VERSION_CODES;
-import android.support.annotation.IntDef;
-import android.support.annotation.NonNull;
-import android.support.annotation.Nullable;
-import android.util.DisplayMetrics;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewGroup.LayoutParams;
-import android.view.WindowManager;
-
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXErrorCode;
-import com.taobao.weex.common.WXRuntimeException;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.flat.widget.Widget;
-import com.taobao.weex.ui.flat.widget.WidgetGroup;
-import com.taobao.weex.ui.view.border.BorderDrawable;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.util.concurrent.atomic.AtomicInteger;
-
-/**
- * Utility class for views
- */
-public class WXViewUtils {
-
-  @IntDef({PixelFormat.TRANSLUCENT, PixelFormat.TRANSPARENT, PixelFormat.OPAQUE})
-  @Retention(RetentionPolicy.SOURCE)
-  public @interface Opacity {}
-
-  /**
-   * Use {@link PixelFormat#TRANSLUCENT} instead
-   */
-  @Deprecated
-  public static final int TRANSLUCENT = PixelFormat.TRANSLUCENT;
-
-  /**
-   * Use {@link PixelFormat#TRANSPARENT} instead.
-   */
-  @Deprecated
-  public static final int TRANSPARENT = PixelFormat.TRANSPARENT;
-
-  /**
-   * Use {@link PixelFormat#OPAQUE} instead
-   */
-  @Deprecated
-  public static final int OPAQUE = PixelFormat.OPAQUE;
-
-  public static final int DIMENSION_UNSET = -1;
-  private static final boolean mUseWebPx = false;
-
-  private static final AtomicInteger sNextGeneratedId = new AtomicInteger(1);
-
-  @SuppressLint("NewApi")
-  public static int generateViewId() {
-
-    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR1) {
-      for (;;) {
-        final int result = sNextGeneratedId.get();
-        // aapt-generated IDs have the high byte nonzero; clamp to the range under that.
-        int newValue = result + 1;
-        if (newValue > 0x00FFFFFF)
-          newValue = 1; // Roll over to 1, not 0.
-        if (sNextGeneratedId.compareAndSet(result, newValue)) {
-          return result;
-        }
-      }
-    } else {
-      return View.generateViewId();
-    }
-  }
-
-  private static int mScreenWidth;
-  private static int mScreenHeight;
-
-
-  public static int getWeexHeight(String instanceId){
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (instance != null) {
-      int weexHeight = instance.getWeexHeight();
-      if (weexHeight >= 0 || weexHeight == -2) {
-        return weexHeight;
-      }
-      else {
-        return getScreenHeight(WXEnvironment.sApplication);
-      }
-    }
-    return -3;
-  }
-
-
-
-  public static int getWeexWidth(String instanceId){
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    if (instance != null) {
-      int weexWidth = instance.getWeexWidth();
-      if (weexWidth >= 0 || weexWidth == -2) {
-        return weexWidth;
-      }
-      else {
-        return getScreenWidth(WXEnvironment.sApplication);
-      }
-    }
-    return -3;
-  }
-
-  @Deprecated
-  public static int getScreenWidth( ) {
-    return getScreenWidth(WXEnvironment.sApplication);
-  }
-
-  @Deprecated
-  public static int setScreenWidth(int screenWidth) {
-    return mScreenWidth = screenWidth;
-  }
-
-  public static float getScreenDensity(Context ctx){
-    if(ctx != null){
-      try{
-        Resources res = ctx.getResources();
-        return res.getDisplayMetrics().density;
-      }catch (Exception e){
-        WXLogUtils.e("getScreenDensityDpi exception:"+e.getMessage());
-      }
-    }
-    return Constants.Value.DENSITY;
-  }
-
-  public static void updateApplicationScreen(Context context){
-    if(context == null || WXEnvironment.sApplication == null){
-        return;
-    }
-    DisplayMetrics metrics = context.getResources().getDisplayMetrics();
-    DisplayMetrics displayMetrics = WXEnvironment.sApplication.getResources().getDisplayMetrics();
-    displayMetrics.heightPixels = metrics.heightPixels;
-    displayMetrics.widthPixels = metrics.widthPixels;
-    displayMetrics.density = metrics.density;
-    displayMetrics.densityDpi = metrics.densityDpi;
-    displayMetrics.scaledDensity = metrics.scaledDensity;
-    displayMetrics.xdpi = metrics.xdpi;
-  }
-
-  public static int getScreenWidth(Context ctx) {
-    if(ctx!=null){
-      Resources res = ctx.getResources();
-      mScreenWidth = res.getDisplayMetrics().widthPixels;
-      if(WXEnvironment.SETTING_FORCE_VERTICAL_SCREEN){
-        mScreenHeight = res
-                .getDisplayMetrics()
-                .heightPixels;
-        mScreenWidth = mScreenHeight > mScreenWidth ? mScreenWidth : mScreenHeight;
-      }
-    } else if(WXEnvironment.isApkDebugable()){
-      throw new WXRuntimeException("Error Context is null When getScreenHeight");
-    }
-    return mScreenWidth;
-  }
-
-
-  public static int getStatusBarHeight(Context context){
-      Resources resources = context.getResources();
-      int resourceId = resources.getIdentifier("status_bar_height", "dimen", "android");
-      if (resourceId > 0) {
-        int statusBarHeight = resources.getDimensionPixelSize(resourceId);
-        return statusBarHeight;
-      }
-      return -1;
-  }
-
-
-  @Deprecated
-  public static int getScreenHeight() {
-    return getScreenHeight(WXEnvironment.sApplication);
-  }
-
-
-  public static int getScreenHeight(String instanceId){
-    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
-    return instance.isFullScreenHeightEnabled()?getFullScreenHeight(WXEnvironment.sApplication):getScreenHeight(WXEnvironment.sApplication);
-  }
-
-//get screen height with status bar on full screen
-  public static int getFullScreenHeight(Context cxt) {
-    if(cxt!=null){
-      WindowManager wm;
-      Resources res = cxt.getResources();
-      if(Build.VERSION.SDK_INT >= 17 && (wm = (WindowManager)cxt.getSystemService(Context.WINDOW_SERVICE)) != null
-              && wm.getDefaultDisplay() != null){
-        Point size = new Point();
-        wm.getDefaultDisplay().getRealSize(size);
-        mScreenHeight = size.y;
-      }
-      else {
-        mScreenHeight = cxt.getResources().getDisplayMetrics().heightPixels;
-      }
-      if(WXEnvironment.SETTING_FORCE_VERTICAL_SCREEN){
-        mScreenWidth = res
-                .getDisplayMetrics()
-                .widthPixels;
-        mScreenHeight = mScreenHeight > mScreenWidth ? mScreenHeight : mScreenWidth;
-      }
-    } else if (WXEnvironment.isApkDebugable()){
-      throw new WXRuntimeException("Error Context is null When getScreenHeight");
-    }
-    return mScreenHeight;
-  }
-//  get screen height without status bar
-  public static int getScreenHeight(Context cxt) {
-    if(cxt!=null){
-      Resources res = cxt.getResources();
-      mScreenHeight = res.getDisplayMetrics().heightPixels;
-      if(WXEnvironment.SETTING_FORCE_VERTICAL_SCREEN){
-        mScreenWidth = res
-                .getDisplayMetrics()
-                .widthPixels;
-        mScreenHeight = mScreenHeight > mScreenWidth ? mScreenHeight : mScreenWidth;
-      }
-    } else if (WXEnvironment.isApkDebugable()){
-      throw new WXRuntimeException("Error Context is null When getScreenHeight");
-    }
-    return mScreenHeight;
-  }
-
-
-  /**
-   * Convert distance from JS,CSS to native. As the JS considers the width of the screen is 750px.
-   * There must be a transform when accessing distance from JS,CSS and use it.
-   * Basically, this method calculates a scale factor(ScreenWidth/750) and use apply this scale
-   * factor to JS,CSS distance.
-   * @param pxValue the raw distance from JS or CSS. The result will be rounded to a closet int.
-   * @return the actual distance in the screen.
-   */
-
-  @Deprecated
-  public static float getRealPxByWidth(float pxValue) {
-    return getRealPxByWidth(pxValue,750);
-  }
-  public static float getRealPxByWidth(float pxValue,int customViewport) {
-    if (Float.isNaN(pxValue)) {
-      return pxValue;
-    }
-    if (mUseWebPx) {
-      return (float) Math.rint(pxValue);
-    } else {
-      float realPx = (pxValue * getScreenWidth() / customViewport);
-      return realPx > 0.005 && realPx < 1 ? 1 : (float) Math.rint(realPx);
-    }
-  }
-
-  @Deprecated
-  public static float getRealSubPxByWidth(float pxValue) {
-    return getRealSubPxByWidth(pxValue,750);
-  }
-
-  public static float getRealSubPxByWidth(float pxValue,int customViewport) {
-    if (Float.isNaN(pxValue)) {
-      return pxValue;
-    }
-    if (mUseWebPx) {
-      return (float) Math.rint(pxValue);
-    } else {
-      float realPx = (pxValue * getScreenWidth() / customViewport);
-      return realPx > 0.005 && realPx < 1 ? 1 : realPx;
-    }
-  }
-
-  /**
-   *  Internal interface that just for debug, you should never call this method because of accuracy loss obviously
-   */
-  @Deprecated
-  public static float getWeexPxByReal(float pxValue) {
-    return getWeexPxByReal(pxValue,750);
-  }
-
-  public static float getWeexPxByReal(float pxValue,int customViewport) {
-    if (Float.isNaN(pxValue)) {
-      return pxValue;
-    }
-    if (mUseWebPx) {
-      return (float) Math.rint(pxValue);
-    } else {
-      return pxValue * customViewport / getScreenWidth();
-    }
-  }
-
-  @Deprecated
-  public static float getRealPxByWidth2(float pxValue) {
-    return getRealPxByWidth2(pxValue,750);
-  }
-  public static int getRealPxByWidth2(float pxValue,int customViewport) {
-    if (mUseWebPx) {
-      return (int) pxValue;
-    } else {
-      float realPx = (pxValue * getScreenWidth() / customViewport);
-      return realPx > 0.005 && realPx < 1 ? 1 : (int) realPx - 1;
-    }
-  }
-
-  /**
-   * Convert distance from native to JS,CSS. As the JS considers the width of the screen is 750px.
-   * There must be a transform when return distance to JS,CSS.
-   * Basically, this method calculates a scale factor(ScreenWidth/750) and use apply this scale
-   * factor to native distance.
-   * @param pxValue the raw distance of native. The result will be rounded to a closet int.
-   * @return the distance in JS,CSS where the screenWidth is 750 px.
-   */
-  @Deprecated
-  public static float getWebPxByWidth(float pxValue) {
-    return getWebPxByWidth(pxValue,750);
-  }
-
-  public static float getWebPxByWidth(float pxValue,int customViewport) {
-    if (pxValue < -1.9999 && pxValue > -2.005) {
-      return Float.NaN;
-    }
-    if (mUseWebPx) {
-      return pxValue;
-    } else {
-      float realPx = (pxValue * customViewport / getScreenWidth());
-      return realPx > 0.005 && realPx < 1 ? 1 : realPx;
-    }
-  }
-
-
-  /**
-   * Convert dp to px
-   * @param dpValue the dp value to be converted
-   * @return the px value
-   */
-  public static int dip2px(float dpValue) {
-    float scale = 2;
-    try {
-      scale = WXEnvironment.getApplication().getResources()
-              .getDisplayMetrics().density;
-    } catch (Exception e) {
-      WXLogUtils.e("[WXViewUtils] dip2px:", e);
-    }
-    float finalPx = (dpValue * scale + 0.5f);
-    return finalPx > 0 && finalPx < 1 ? 1 : (int) finalPx;
-  }
-
-  public static boolean onScreenArea(View view) {
-    if (view == null || view.getVisibility() != View.VISIBLE) {
-      return false;
-    }
-
-    int[] p = new int[2];
-    view.getLocationOnScreen(p);
-    LayoutParams lp = view.getLayoutParams();
-    int viewH = 0;
-    if (lp != null) {
-      viewH = lp.height;
-    } else {
-      viewH = view.getHeight();
-    }
-
-    return (p[1] > 0 && (p[1] - WXViewUtils.getScreenHeight(WXEnvironment.sApplication) < 0))
-            || (viewH + p[1] > 0 && p[1] <= 0);
-  }
-
-  /**
-   * Multiplies the color with the given alpha.
-   *
-   * @param color color to be multiplied
-   * @param alpha value between 0 and 255
-   * @return multiplied color
-   */
-  public static int multiplyColorAlpha(int color, int alpha) {
-    if (alpha == 255) {
-      return color;
-    }
-    if (alpha == 0) {
-      return color & 0x00FFFFFF;
-    }
-    alpha = alpha + (alpha >> 7); // make it 0..256
-    int colorAlpha = color >>> 24;
-    int multipliedAlpha = colorAlpha * alpha >> 8;
-    return (multipliedAlpha << 24) | (color & 0x00FFFFFF);
-  }
-
-  @Opacity
-  public static int getOpacityFromColor(int color) {
-    int colorAlpha = color >>> 24;
-    if (colorAlpha == 255) {
-      return PixelFormat.OPAQUE;
-    } else if (colorAlpha == 0) {
-      return PixelFormat.TRANSPARENT;
-    } else {
-      return PixelFormat.TRANSLUCENT;
-    }
-  }
-
-  @SuppressWarnings("deprecation")
-  public static void setBackGround(View view, Drawable drawable, WXComponent component) {
-    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN){
-      view.setBackgroundDrawable(drawable);
-    }
-    else{
-      try {
-        view.setBackground(drawable);
-      } catch (Exception e) {
-        if (component == null)
-          return;
-        WXExceptionUtils.commitCriticalExceptionRT(component.getInstanceId(),
-                WXErrorCode.WX_RENDER_ERR_TEXTURE_SETBACKGROUND,
-                component.getComponentType() + " setBackGround for android view",
-                WXErrorCode.WX_RENDER_ERR_TEXTURE_SETBACKGROUND.getErrorMsg() + ": TextureView doesn't support displaying a background drawable!",
-                null);
-      }
-    }
-  }
-
-  public static @Nullable
-  BorderDrawable getBorderDrawable(@NonNull View view){
-    Drawable drawable=view.getBackground();
-    if(drawable instanceof BorderDrawable){
-      return (BorderDrawable) drawable;
-    }
-    else if(drawable instanceof LayerDrawable){
-      if(((LayerDrawable) drawable).getNumberOfLayers()>1) {
-        Drawable innerDrawable=((LayerDrawable) drawable).getDrawable(0);
-        if(innerDrawable instanceof BorderDrawable){
-          return (BorderDrawable) innerDrawable;
-        }
-      }
-    }
-    return null;
-  }
-
-  public static void clipCanvasWithinBorderBox(View targetView, Canvas canvas) {
-    Drawable drawable;
-    if (clipCanvasDueToAndroidVersion(canvas) &&
-            clipCanvasIfAnimationExist(targetView) &&
-            ((drawable = targetView.getBackground()) instanceof BorderDrawable)) {
-      BorderDrawable borderDrawable = (BorderDrawable) drawable;
-      if (borderDrawable.isRounded()) {
-        if (clipCanvasIfBackgroundImageExist(targetView, borderDrawable)) {
-          Path path = borderDrawable.getContentPath(
-                  new RectF(0, 0, targetView.getWidth(), targetView.getHeight()));
-          canvas.clipPath(path);
-        }
-      }
-    }
-  }
-
-  public static void clipCanvasWithinBorderBox(Widget widget, Canvas canvas) {
-    BorderDrawable borderDrawable;
-    if (clipCanvasDueToAndroidVersion(canvas) &&
-            clipCanvasIfAnimationExist(null) &&
-            (borderDrawable=widget.getBackgroundAndBorder())!=null ) {
-      if (borderDrawable.isRounded() && clipCanvasIfBackgroundImageExist(widget, borderDrawable)) {
-        Path path = borderDrawable.getContentPath(
-                new RectF(0, 0, widget.getBorderBox().width(), widget.getBorderBox().height()));
-        canvas.clipPath(path);
-      }
-      else {
-        canvas.clipRect(widget.getBorderBox());
-      }
-    }
-  }
-
-  /**
-   * According to https://developer.android.com/guide/topics/graphics/hardware-accel.html#unsupported
-   API 18 or higher supports clipPath to canvas based on hardware acceleration.
-   * @param canvas
-   * @return
-   */
-  private static boolean clipCanvasDueToAndroidVersion(Canvas canvas) {
-    return Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2 ||
-            !canvas.isHardwareAccelerated();
-  }
-
-  /**
-   * According to https://code.google.com/p/android/issues/detail?id=225556&sort=-id&colspec=ID
-   * clipPath doesn't work with rotation nor scale when API level is 24.
-   * As animation will not cause redraw if hardware-acceleration enabled, clipCanvas feature has
-   * to be disabled when API level is 24 without considering the animation property.
-   */
-  private static boolean clipCanvasIfAnimationExist(View targetView) {
-    if (Build.VERSION.SDK_INT != VERSION_CODES.N) {
-      return true;
-    } else {
-      return false;
-    }
-  }
-
-  /**
-   * Due limitation in Android platform, the linear gradient in the following page will not be
-   * rounded if {@link Canvas#clipPath(Path)} of the parent view invoked when API level is lower
-   * than 21.
-   * http://dotwe.org/weex/963c9ade129f86757cecdd85651cd30e
-   * @param targetView
-   * @param borderDrawable
-   * @return
-   */
-  private static boolean clipCanvasIfBackgroundImageExist(@NonNull View targetView,
-                                                          @NonNull BorderDrawable borderDrawable) {
-    if (targetView instanceof ViewGroup) {
-      View child;
-      ViewGroup parent = ((ViewGroup) targetView);
-      int count = parent.getChildCount();
-      for (int i = 0; i < count; i++) {
-        child = parent.getChildAt(i);
-        if (child.getBackground() instanceof BorderDrawable &&
-                ((BorderDrawable) child.getBackground()).hasImage() &&
-                Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
-          return false;
-        }
-      }
-    }
-    return true;
-  }
-
-  private static boolean clipCanvasIfBackgroundImageExist(@NonNull Widget widget,
-                                                          @NonNull BorderDrawable borderDrawable) {
-    if (widget instanceof WidgetGroup) {
-      for (Widget child : ((WidgetGroup) widget).getChildren()) {
-        if (child.getBackgroundAndBorder().hasImage() &&
-                Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
-          return false;
-        }
-      }
-    }
-    return true;
-  }
-
-  public static boolean isViewVisible(View v) {
-    if (null == v){
-      return false;
-    }
-
-    boolean isAttachToWindow = Build.VERSION.SDK_INT >= VERSION_CODES.KITKAT
-        ?v.isAttachedToWindow()
-        :v.getWindowToken() != null;
-
-    if (!isAttachToWindow){
-      return false;
-    }
-    if (v.getVisibility() != View.VISIBLE || v.getAlpha()<=0){
-      return false;
-    }
-
-    Drawable bacDrawable = v.getBackground();
-    if (null == bacDrawable){
-      return true;
-    }
-    if (Build.VERSION.SDK_INT >= VERSION_CODES.KITKAT){
-      return bacDrawable.getAlpha()>0;
-    }
-    //< 4.4
-    if (bacDrawable instanceof ColorDrawable){
-      int alpha = Color.alpha(((ColorDrawable) bacDrawable).getColor());
-      return alpha >0;
-    }else if (bacDrawable instanceof BitmapDrawable){
-      Paint paint = ((BitmapDrawable) bacDrawable).getPaint();
-      return paint.getAlpha() > 0;
-    }
-    return true;
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/WXWsonJSONSwitch.java b/android/sdk/src/main/java/com/taobao/weex/utils/WXWsonJSONSwitch.java
deleted file mode 100644
index 0271bdf..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/WXWsonJSONSwitch.java
+++ /dev/null
@@ -1,128 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.support.annotation.NonNull;
-
-import com.alibaba.fastjson.JSON;
-import com.taobao.weex.bridge.WXJSObject;
-import com.taobao.weex.wson.Wson;
-import com.taobao.weex.wson.WsonUtils;
-
-/**
- * Created by furture on 2018/5/17.
- */
-
-public class WXWsonJSONSwitch {
-
-    private static final String TAG = "WXSwitch";
-
-    /**
-     * switch input data to target according to config, if not use wson return normal data
-     * */
-    public static  final byte[] convertJSONToWsonIfUseWson(byte[] json){
-        if(!USE_WSON){
-            return json;
-        }
-        if(json == null){
-            return null;
-        }
-        String str = new String(json);
-        if(str.startsWith("[")){
-            return WsonUtils.toWson(JSON.parseArray(str));
-        }
-        return WsonUtils.toWson(JSON.parse(str));
-    }
-
-    /**
-     * parse json or wson data by config switch
-     * */
-    public static final Object parseWsonOrJSON(byte[] data){
-        if(data == null){
-            return  null;
-        }
-        try{
-            if(USE_WSON){
-                return  Wson.parse(data);
-            }else{
-                return  JSON.parse(new String(data, "UTF-8"));
-            }
-        }catch (Exception e){
-            WXLogUtils.e(TAG, e);
-            if(USE_WSON){  //fallback
-                return  JSON.parse(new String(data));
-            }else{
-                return Wson.parse(data);
-            }
-        }
-    }
-
-    /**
-     * to wson or wson WXJSObject
-     * */
-    public static final WXJSObject toWsonOrJsonWXJSObject(Object tasks){
-        if(tasks == null){
-            return new WXJSObject(null);
-        }
-        if(tasks.getClass() == WXJSObject.class){
-            return (WXJSObject) tasks;
-        }
-        if(USE_WSON) {
-            return new WXJSObject(WXJSObject.WSON, Wson.toWson(tasks));
-        }else{
-            return new WXJSObject(WXJSObject.JSON, WXJsonUtils.fromObjectToJSONString(tasks));
-        }
-    }
-
-
-    public static  final Object convertWXJSObjectDataToJSON(WXJSObject object){
-        if(object.type == WXJSObject.WSON){
-            return JSON.parse(Wson.parse((byte[]) object.data).toString());
-        }else{
-            return JSON.parse(object.data.toString());
-        }
-    }
-
-
-
-    /**
-     * config whether use json or wson,  you should update this value by updateGlobalConfig(String config)
-     * in WXBridgeManager class  method
-     * */
-    public static  boolean USE_WSON = true;
-
-
-    /**wson off */
-    public static final String WSON_OFF = "wson_off";
-
-
-    public @NonNull
-    static String fromObjectToJSONString(WXJSObject obj) {
-        if(obj != null && obj.type == WXJSObject.WSON){
-            Object data = Wson.parse((byte[]) obj.data);
-            if(data != null){
-                return  data.toString();
-            }
-        }
-        return WXJsonUtils.fromObjectToJSONString(obj,false);
-    }
-
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/batch/BactchExecutor.java b/android/sdk/src/main/java/com/taobao/weex/utils/batch/BactchExecutor.java
deleted file mode 100644
index 60ac7f4..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/batch/BactchExecutor.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils.batch;
-
-/**
- * Created by sospartan on 8/24/16.
- */
-public interface BactchExecutor {
-  void post(Runnable runnable);
-
-  void setInterceptor(Interceptor interceptor);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/batch/BatchOperationHelper.java b/android/sdk/src/main/java/com/taobao/weex/utils/batch/BatchOperationHelper.java
deleted file mode 100644
index 3c79d53..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/batch/BatchOperationHelper.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils.batch;
-
-import com.taobao.weex.utils.batch.BactchExecutor;
-import com.taobao.weex.utils.batch.Interceptor;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.concurrent.CopyOnWriteArrayList;
-
-/**
- * Created by sospartan on 8/24/16.
- */
-public class BatchOperationHelper implements Interceptor {
-
-
-  private BactchExecutor mExecutor;
-  private CopyOnWriteArrayList<Runnable> sRegisterTasks = new CopyOnWriteArrayList<>();
-  private boolean isCollecting = false;
-
-  public BatchOperationHelper(BactchExecutor executor){
-    mExecutor = executor;
-    executor.setInterceptor(this);
-    isCollecting = true;
-  }
-
-  @Override
-  public boolean take(Runnable runnable) {
-    if(isCollecting){
-      sRegisterTasks.add(runnable);
-      return true;
-    }
-    return false;
-  }
-
-  /**
-   * Post all tasks to executor. Can only be called once.
-   */
-  public void flush(){
-    isCollecting = false;
-    mExecutor.post(new Runnable() {
-      @Override
-      public void run() {
-        Iterator<Runnable> iterator = sRegisterTasks.iterator();
-        while(iterator.hasNext()){
-          Runnable item = iterator.next();
-          item.run();
-//          iterator.remove();
-          sRegisterTasks.remove(item);
-        }
-      }
-    });
-    mExecutor.setInterceptor(null);
-  }
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/batch/Interceptor.java b/android/sdk/src/main/java/com/taobao/weex/utils/batch/Interceptor.java
deleted file mode 100644
index 80194ec..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/batch/Interceptor.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils.batch;
-
-/**
- * Created by sospartan on 8/24/16.
- */
-public interface Interceptor {
-  boolean take(Runnable runnable);
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/cache/RegisterCache.java b/android/sdk/src/main/java/com/taobao/weex/utils/cache/RegisterCache.java
deleted file mode 100644
index 69f18f3..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/cache/RegisterCache.java
+++ /dev/null
@@ -1,181 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils.cache;
-
-import com.taobao.weex.bridge.ModuleFactory;
-import com.taobao.weex.bridge.WXModuleManager;
-import com.taobao.weex.ui.IFComponentHolder;
-import com.taobao.weex.ui.WXComponentRegistry;
-import com.taobao.weex.ui.config.AutoScanConfigRegister;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-
-public class RegisterCache {
-    private static Map<String, ModuleCache> moduleCacheMap = new ConcurrentHashMap<>();
-    private static Map<String, ComponentCache> componentCacheMap = new ConcurrentHashMap<>();
-    private static RegisterCache registerCache;
-
-    private boolean enable = false;
-
-    private boolean enableAutoScan = true;
-
-    public static RegisterCache getInstance() {
-        if (registerCache == null) {
-            synchronized (RegisterCache.class) {
-                if (registerCache == null) {
-                    registerCache = new RegisterCache();
-                }
-            }
-        }
-        return registerCache;
-    }
-
-    private RegisterCache() {
-
-    }
-
-    private volatile boolean finished = false;
-
-    private volatile int doNotCacheSize = Integer.MAX_VALUE;
-
-    public void setEnable(boolean enable) {
-        this.enable = enable;
-    }
-
-    private boolean enableCache() {
-        return enable;
-    }
-
-    private boolean canCache() {
-        return enableCache()
-                && !finished
-                && getDoNotCacheSize() < 1;
-    }
-
-    public boolean enableAutoScan() {
-        return enableAutoScan;
-    }
-
-    public void setEnableAutoScan(boolean enableAutoScan) {
-        if(this.enableAutoScan != enableAutoScan) {
-            if(enableAutoScan) {
-                AutoScanConfigRegister.doScanConfig();
-            }
-            this.enableAutoScan = enableAutoScan;
-        }
-
-    }
-
-    private int getDoNotCacheSize() {
-        return doNotCacheSize--;
-    }
-
-    public void setDoNotCacheSize(int doNotCacheSize) {
-        this.doNotCacheSize = doNotCacheSize;
-    }
-
-    public boolean idle(boolean atCreateInstance) {
-        if (finished)
-            return true;
-
-        String message;
-        if(atCreateInstance) {
-            message = "idle from create instance";
-        } else {
-            message = "idle from external";
-        }
-
-        WXLogUtils.e(message + " cache size is " + (moduleCacheMap.size() + componentCacheMap.size()));
-
-        finished = true;
-        CacheComponentRegister();
-        CacheModuleRegister();
-        return true;
-    }
-
-    public boolean cacheModule(final String moduleName, final ModuleFactory factory, final boolean global) {
-        if (!canCache()) {
-            return false;
-        }
-        try {
-            moduleCacheMap.put(moduleName, new ModuleCache(moduleName, factory, global));
-        } catch (Exception e) {
-            return false;
-        }
-        return true;
-    }
-
-
-    public boolean cacheComponent(final String type, final IFComponentHolder holder, final Map<String, Object> componentInfo) {
-        if (!canCache()) {
-            return false;
-        }
-        try {
-            componentCacheMap.put(type, new ComponentCache(type, holder, componentInfo));
-        } catch (Exception e) {
-            return false;
-        }
-        return true;
-    }
-
-
-    private void CacheComponentRegister() {
-        if (componentCacheMap.isEmpty())
-            return;
-        WXComponentRegistry.registerComponent(componentCacheMap);
-    }
-
-
-    private void CacheModuleRegister() {
-        if (moduleCacheMap.isEmpty())
-            return;
-
-        WXModuleManager.registerModule(moduleCacheMap);
-    }
-
-    public class ModuleCache {
-        public final String name;
-        public final ModuleFactory factory;
-        public final boolean global;
-
-        ModuleCache(String moduleName, ModuleFactory factory, boolean global) {
-            this.name = moduleName;
-            this.factory = factory;
-            this.global = global;
-        }
-    }
-
-
-    public class ComponentCache {
-        public final String type;
-        public final IFComponentHolder holder;
-        public final Map<String, Object> componentInfo;
-
-        ComponentCache(String type, IFComponentHolder holder, Map<String, Object> componentInfo) {
-            this.type = type;
-            this.componentInfo = componentInfo;
-            this.holder = holder;
-        }
-    }
-
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/tools/Info.java b/android/sdk/src/main/java/com/taobao/weex/utils/tools/Info.java
deleted file mode 100644
index a9dd401..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/tools/Info.java
+++ /dev/null
@@ -1,55 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils.tools;
-
-import com.alibaba.fastjson.annotation.JSONField;
-
-public class Info{
-
-	public Info() {
-		taskInfo = new TaskInfo();
-	}
-
-	@JSONField(name="instanceId")
-	public String instanceId;
-
-	@JSONField(name="taskName")
-	public String taskName;
-
-	@JSONField(name="taskInfo")
-	public TaskInfo taskInfo;
-
-	@JSONField(name="platform")
-	public String platform;
-
-	@JSONField(name="taskId")
-	public int taskId;
-
-	@Override
- 	public String toString(){
-		return 
-			"Info : {" +
-			"instanceId = '" + instanceId + '\'' + 
-			",taskName = '" + taskName + '\'' + 
-			",taskInfo = '" + taskInfo + '\'' + 
-			",platform = '" + platform + '\'' + 
-			",taskId = '" + taskId + '\'' + 
-			"}";
-		}
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/tools/LogDetail.java b/android/sdk/src/main/java/com/taobao/weex/utils/tools/LogDetail.java
deleted file mode 100644
index c257296..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/tools/LogDetail.java
+++ /dev/null
@@ -1,86 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils.tools;
-
-import android.text.TextUtils;
-import android.util.Log;
-
-import com.alibaba.fastjson.annotation.JSONField;
-import com.taobao.weex.WXEnvironment;
-import java.util.Locale;
-
-public class LogDetail {
-    public static final String KeyWrod_Init = "Weex_Init";
-    public static final String KeyWords_Render = "Weex_Render";
-
-    public LogDetail() {
-        time = new Time();
-        info = new Info();
-    }
-
-    @JSONField(name = "time")
-    public Time time;
-
-    @JSONField(name = "Info")
-    public Info info;
-
-    @Override
-    public String toString() {
-        return
-                "taskName : " + info.taskName + " - LogDetail : {" +
-                        "time = '" + time + '\'' +
-                        ", info = '" + info + '\'' +
-                        "}";
-    }
-
-
-    public String keyWords = KeyWords_Render;
-
-    public void println() {
-        if(WXEnvironment.isPerf())
-        Log.e(TimeCalculator.TIMELINE_TAG," timeline " + this.keyWords + " java LogDetail: " + this.toString());
-    }
-
-    public void name(String name) {
-        time.constructor();
-        info.taskName = name;
-        if(!TextUtils.isEmpty(name)) {
-            String s = name.toLowerCase(Locale.ROOT);
-            if(s.contains("module")
-            || s.contains("component")
-                    || s.contains("framework")) {
-                this.keyWords = KeyWrod_Init;
-            }
-        }
-    }
-
-    public void keyWorkds(String keyWords) {
-        this.keyWords = keyWords;
-    }
-
-    public void taskStart() {
-        time.taskStart();
-    }
-
-    public void taskEnd() {
-        time.taskEnd();
-        println();
-    }
-
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/tools/LogSwitch.java b/android/sdk/src/main/java/com/taobao/weex/utils/tools/LogSwitch.java
deleted file mode 100644
index 8dc4c4a..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/tools/LogSwitch.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils.tools;
-
-public class LogSwitch {
-
-    private int low_level = 4;
-    private int medium_level = 2;
-    private int high_level = 1;
-    private int log_switch = 0;
-    private boolean showLowLevelLog = false;
-    private boolean showMediumLevelLog = false;
-    private boolean showHighLevelLog = true;
-
-
-    public void setLog_switch() {
-        // Todo
-        // read prop
-
-        if (showLowLevelLog)
-            log_switch |= low_level;
-
-        if (showMediumLevelLog) {
-            log_switch |= medium_level;
-        }
-
-        if (showHighLevelLog) {
-            log_switch |= high_level;
-        }
-    }
-
-
-    public int getLog_switch() {
-        return log_switch;
-    }
-
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/tools/TaskInfo.java b/android/sdk/src/main/java/com/taobao/weex/utils/tools/TaskInfo.java
deleted file mode 100644
index 67bae84..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/tools/TaskInfo.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils.tools;
-
-import com.alibaba.fastjson.annotation.JSONField;
-
-public class TaskInfo{
-
-	@JSONField(name="args")
-	public String args;
-
-	@JSONField(name="relateTaskId")
-	public int relateTaskId;
-
-	@Override
- 	public String toString(){
-		return 
-			"TaskInfo{" + 
-			"args = '" + args + '\'' + 
-			",relateTaskId = '" + relateTaskId + '\'' + 
-			"}";
-		}
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/tools/Time.java b/android/sdk/src/main/java/com/taobao/weex/utils/tools/Time.java
deleted file mode 100644
index edeab93..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/tools/Time.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils.tools;
-
-import com.alibaba.fastjson.annotation.JSONField;
-
-public class Time {
-
-    @JSONField(name = "taskStart")
-    public long taskStart;
-
-    @JSONField(name = "execTime")
-    public long execTime;
-
-    @JSONField(name = "constructor")
-    public long constructor;
-
-    @JSONField(name = "destructor")
-    public long destructor;
-
-    @JSONField(name = "taskEnd")
-    public long taskEnd;
-
-    @JSONField(name = "waitTime")
-    public long waitTime;
-
-    @Override
-    public String toString() {
-        return
-                "time : {" +
-                        "constructor = '" + constructor + '\'' +
-                        ",taskStart = '" + taskStart + '\'' +
-                        ",execTime = '" + execTime + '\'' +
-                        ",waitTime = '" + waitTime + '\'' +
-                        ",destructor = '" + destructor + '\'' +
-                        ",taskEnd = '" + taskEnd + '\'' +
-                        "}";
-    }
-
-
-    protected void constructor() {
-        constructor = System.currentTimeMillis();
-    }
-
-    public void execTime() {
-        execTime = taskEnd - taskStart;
-    }
-
-    public void taskStart() {
-        taskStart = System.currentTimeMillis();
-    }
-
-    public void taskEnd() {
-        taskEnd = System.currentTimeMillis();
-        execTime();
-        destructor();
-    }
-
-    private void destructor() {
-        waitTime();
-        destructor = System.currentTimeMillis();
-    }
-
-    public void waitTime() {
-        waitTime = taskStart - constructor;
-    }
-}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/com/taobao/weex/utils/tools/TimeCalculator.java b/android/sdk/src/main/java/com/taobao/weex/utils/tools/TimeCalculator.java
deleted file mode 100644
index 1e3eb2d..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/utils/tools/TimeCalculator.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.utils.tools;
-
-import android.util.Log;
-
-import com.alibaba.fastjson.JSON;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-
-import java.util.concurrent.CopyOnWriteArrayList;
-
-public class TimeCalculator {
-
-    public static final String TIMELINE_TAG = "timeline";
-
-    public static final String PLATFORM_ANDROID = "Android";
-
-    private CopyOnWriteArrayList<LogDetail> logRecorder;
-    public TimeCalculator(WXSDKInstance instance) {
-        logRecorder = new CopyOnWriteArrayList<LogDetail>();
-    }
-
-    public void addLog(LogDetail logDetail) {
-        if(!WXEnvironment.isPerf()) {
-            return;
-        }
-        logRecorder.add(logDetail);
-    }
-
-    public LogDetail createLogDetail(String name) {
-        LogDetail logDetail = new LogDetail();
-        logDetail.name(name);
-        addLog(logDetail);
-        return logDetail;
-    }
-
-    public void println() {
-        if(!WXEnvironment.isPerf()) {
-            return;
-        }
-
-        for (LogDetail l: logRecorder) {
-            Log.e(TIMELINE_TAG, JSON.toJSONString(l));
-        }
-
-    }
-
-
-    private String test = "{\"time\":{\"execTime\":0,\"constructor\":0,\"destructor\":0,\"taskStart\":0,\"taskEnd\":0,\"waitTime\":0},\"Info\":{\"taskInfo\":{\"relateTaskId\":0,\"args\":\"stringReplace\"},\"taskName\":\"stringReplace\",\"instanceId\":\"1\",\"platform\":\"stringReplace\",\"taskId\":0}}";
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/wson/Wson.java b/android/sdk/src/main/java/com/taobao/weex/wson/Wson.java
deleted file mode 100644
index b8b8992..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/wson/Wson.java
+++ /dev/null
@@ -1,820 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.wson;
-
-
-import android.support.v4.util.LruCache;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.alibaba.fastjson.annotation.JSONField;
-import com.taobao.weex.utils.WXLogUtils;
-
-import java.lang.reflect.Array;
-import java.lang.reflect.Field;
-import java.lang.reflect.Method;
-import java.lang.reflect.Modifier;
-import java.math.BigDecimal;
-import java.math.BigInteger;
-import java.nio.ByteOrder;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Calendar;
-import java.util.Collection;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-/**
- * fast binary json format for parse map and serialize map
- * Created by efurture on 2017/8/16.
- */
-public class Wson {
-
-    /**
-     * skip map null values
-     * */
-    public static final boolean WriteMapNullValue = false;
-    /**
-     * wson data type
-     * */
-    private static final byte NULL_TYPE = '0';
-
-    private static final byte STRING_TYPE = 's';
-
-    private static final byte BOOLEAN_TYPE_TRUE = 't';
-
-    private static final byte BOOLEAN_TYPE_FALSE = 'f';
-
-    private static final byte NUMBER_INT_TYPE = 'i';
-
-    private static final byte NUMBER_LONG_TYPE = 'l';
-
-    private static final byte NUMBER_BIG_INTEGER_TYPE = 'g';
-
-    private static final byte NUMBER_BIG_DECIMAL_TYPE = 'e';
-
-    private static final byte NUMBER_DOUBLE_TYPE = 'd';
-
-    private static final byte NUMBER_FLOAT_TYPE = 'F';
-
-    private static final byte ARRAY_TYPE = '[';
-
-    private static final byte MAP_TYPE = '{';
-
-    /**
-     * StringUTF-16, byte order with native byte order
-     * */
-    private static final boolean IS_NATIVE_LITTLE_ENDIAN = (ByteOrder.nativeOrder() == ByteOrder.LITTLE_ENDIAN);
-
-
-    /**
-     * parse wson data  to object, please use WXJsonUtils.parseWson
-     * @param  data  byte array
-     * */
-    public static final Object parse(byte[] data){
-        if(data == null){
-            return  null;
-        }
-        try{
-            Parser parser =  new Parser(data);
-            Object object = parser.parse();
-            parser.close();
-            return object;
-        }catch (Exception e){
-            WXLogUtils.e("parseWson", e);
-            return  null;
-        }
-    }
-
-
-    /**
-     * serialize object to wson data, please use WXJsonUtils.toWsonOrJsonWXJSObject
-     * */
-    public static final byte[] toWson(Object object){
-        if(object == null){
-            return  null;
-        }
-        Builder builder = new Builder();
-        byte[]  bts  = builder.toWson(object);
-        builder.close();
-        return bts;
-    }
-
-
-    /**
-     * wson data parser
-     * */
-    private static final class Parser {
-
-        private int position = 0;
-        private byte[] buffer;
-        private char[]  charsBuffer;
-
-        private Parser(byte[] buffer) {
-            this.buffer = buffer;
-            charsBuffer = localCharsBufferCache.get();
-            if(charsBuffer != null){
-                localCharsBufferCache.set(null);
-            }else{
-                charsBuffer = new char[512];
-            }
-        }
-
-
-        private   final Object parse(){
-            return  readObject();
-        }
-
-        private final void close(){
-            position = 0;
-            buffer = null;
-            if(charsBuffer != null){
-                localCharsBufferCache.set(charsBuffer);
-            }
-            charsBuffer = null;
-        }
-
-        private final Object readObject(){
-            byte type  = readType();
-            switch (type){
-                case STRING_TYPE:
-                    return readUTF16String();
-                case NUMBER_INT_TYPE :
-                    return  readVarInt();
-                case NUMBER_FLOAT_TYPE :
-                    return  readFloat();
-                case MAP_TYPE:
-                    return readMap();
-                case ARRAY_TYPE:
-                    return readArray();
-                case NUMBER_DOUBLE_TYPE :
-                    return readDouble();
-                case NUMBER_LONG_TYPE :
-                    return  readLong();
-                case NUMBER_BIG_INTEGER_TYPE :
-                    return  new BigInteger(readUTF16String());
-                case NUMBER_BIG_DECIMAL_TYPE :
-                    return  new BigDecimal(readUTF16String());
-                case BOOLEAN_TYPE_FALSE:
-                    return  Boolean.FALSE;
-                case BOOLEAN_TYPE_TRUE:
-                    return  Boolean.TRUE;
-                case NULL_TYPE:
-                    return  null;
-                default:
-                    throw new RuntimeException("wson unhandled type " + type + " " +
-                            position  +  " length " + buffer.length);
-            }
-        }
-
-
-
-        private final Object readMap(){
-            int size = readUInt();
-            Map<String, Object> object = new JSONObject();;
-            for(int i=0; i<size; i++){
-                String key = readMapKeyUTF16();
-                Object value = readObject();
-                object.put(key, value);
-            }
-            return object;
-        }
-
-        private final Object readArray(){
-            int length = readUInt();
-            List<Object> array = new JSONArray(length);
-            for(int i=0; i<length; i++){
-                array.add(readObject());
-            }
-            return  array;
-        }
-
-        private  final byte readType(){
-            byte type = buffer[position];
-            position ++;
-            return  type;
-        }
-
-
-        private final String readMapKeyUTF16() {
-            int length = readUInt();
-            length = length/2;
-            if(charsBuffer.length < length){
-                charsBuffer = new char[length];
-            }
-            int hash = 5381;
-            if(IS_NATIVE_LITTLE_ENDIAN){
-                for(int i=0; i<length; i++){
-                    char ch = (char) ((buffer[position] & 0xFF) +
-                            (buffer[position + 1] << 8));
-                    charsBuffer[i] = (ch);
-                    hash = ((hash << 5) + hash)  + ch;
-                    position+=2;
-                }
-            }else{
-                for(int i=0; i<length; i++){
-                    char ch = (char) ((buffer[position + 1] & 0xFF) +
-                            (buffer[position] << 8));
-                    charsBuffer[i] = (ch);
-                    hash = ((hash << 5) + hash)  + ch;
-                    position+=2;
-                }
-            }
-            int globalIndex = (globalStringBytesCache.length - 1)&hash;
-            String cache = globalStringBytesCache[globalIndex];
-            if(cache != null
-                    && cache.length() == length){
-                boolean isStringEqual  = true;
-                for(int i=0; i<length; i++){
-                    if(charsBuffer[i] != cache.charAt(i)){
-                        isStringEqual = false;
-                        break;
-                    }
-                }
-                if(isStringEqual) {
-                    return cache;
-                }
-            }
-            cache = new String(charsBuffer, 0, length);
-            if(length < 64) {
-                globalStringBytesCache[globalIndex] = cache;
-            }
-            return  cache;
-        }
-
-        private final String readUTF16String(){
-            int length = readUInt()/2;
-            if(charsBuffer.length < length){
-                charsBuffer = new char[length];
-            }
-            if(IS_NATIVE_LITTLE_ENDIAN){
-                for(int i=0; i<length; i++){
-                    char ch = (char) ((buffer[position] & 0xFF) +
-                            (buffer[position + 1] << 8));
-                    charsBuffer[i] = (ch);
-                    position+=2;
-                }
-            }else{
-                for(int i=0; i<length; i++){
-                    char ch = (char) ((buffer[position + 1] & 0xFF) +
-                            (buffer[position] << 8));
-                    charsBuffer[i] = (ch);
-                    position+=2;
-                }
-            }
-            return  new String(charsBuffer, 0, length);
-        }
-
-
-
-
-
-        private   final int readVarInt(){
-            int raw = readUInt();
-            // This undoes the trick in putVarInt()
-            int num = (((raw << 31) >> 31) ^ raw) >> 1;
-            // This extra step lets us deal with the largest signed values by treating
-            // negative results from read unsigned methods as like unsigned values.
-            // Must re-flip the top bit if the original read value had it set.
-            return num ^ (raw & (1 << 31));
-        }
-
-        private final  int readUInt(){
-            int value = 0;
-            int i = 0;
-            int b;
-            while (((b = buffer[position]) & 0x80) != 0) {
-                value |= (b & 0x7F) << i;
-                i += 7;
-                position+=1;
-                if (i > 35) {
-                    throw new IllegalArgumentException("Variable length quantity is too long");
-                }
-            }
-            position+=1;
-            return value | (b << i);
-        }
-
-        private final long readLong(){
-            long number = (((buffer[position + 7] & 0xFFL)      ) +
-                    ((buffer[position + 6] & 0xFFL) <<  8) +
-                    ((buffer[position + 5] & 0xFFL) << 16) +
-                    ((buffer[position + 4] & 0xFFL) << 24) +
-                    ((buffer[position + 3] & 0xFFL) << 32) +
-                    ((buffer[position + 2] & 0xFFL) << 40) +
-                    ((buffer[position + 1] & 0xFFL) << 48) +
-                    (((long) buffer[position])      << 56));
-            position += 8;
-            return  number;
-        }
-
-        private  final Object readDouble(){
-            double number = Double.longBitsToDouble(readLong());
-            if(number > Integer.MAX_VALUE){
-                long numberLong = (long) number;
-                double doubleLong = (numberLong);
-                if(number - doubleLong < Double.MIN_NORMAL){
-                    return numberLong;
-                }
-            }
-            return  number;
-        }
-
-        private Object readFloat() {
-            int number = (((buffer[position + 3] & 0xFF)      ) +
-                    ((buffer[position + 2] & 0xFF) <<  8) +
-                    ((buffer[position + 1] & 0xFF) << 16) +
-                    ((buffer[position  ] & 0xFF) << 24));
-            position +=4;
-            return  Float.intBitsToFloat(number);
-        }
-    }
-
-    /**
-     * wson builder
-     * */
-    private static final class Builder {
-
-        private byte[] buffer;
-        private int position;
-        private ArrayList refs;
-        private final static ThreadLocal<byte[]> bufLocal = new ThreadLocal<byte[]>();
-        private final static ThreadLocal<ArrayList> refsLocal = new ThreadLocal<ArrayList>();
-
-
-
-        private Builder(){
-            buffer =  bufLocal.get();
-            if(buffer != null) {
-                bufLocal.set(null);
-            }else{
-                buffer = new byte[1024];
-            }
-            refs = refsLocal.get();
-            if(refs != null){
-                refsLocal.set(null);
-            }else{
-                refs = new ArrayList<>(16);
-            }
-        }
-
-
-        private final byte[] toWson(Object object){
-            writeObject(object);
-            byte[] bts = new byte[position];
-            System.arraycopy(buffer, 0, bts, 0, position);
-            return  bts;
-        }
-
-        private final void close(){
-            if(buffer.length <= 1024*16){
-                bufLocal.set(buffer);
-            }
-            if(refs.isEmpty()){
-                refsLocal.set(refs);
-            }else{
-                refs.clear();
-            }
-            refs = null;
-            buffer = null;
-            position = 0;
-        }
-
-        private final void writeObject(Object object) {
-            if(object instanceof  CharSequence){
-                ensureCapacity(2);
-                writeByte(STRING_TYPE);
-                writeUTF16String((CharSequence) object);
-                return;
-            }else if (object instanceof Map){
-                if(refs.contains(object)){
-                    ensureCapacity(2);
-                    writeByte(NULL_TYPE);
-                    return;
-                }
-                refs.add(object);
-                Map map = (Map) object;
-                writeMap(map);
-                refs.remove(refs.size()-1);
-                return;
-            }else if (object instanceof List){
-                if(refs.contains(object)){
-                    ensureCapacity(2);
-                    writeByte(NULL_TYPE);
-                    return;
-                }
-                refs.add(object);
-                ensureCapacity(8);
-                List list = (List) object;
-                writeByte(ARRAY_TYPE);
-                writeUInt(list.size());
-                for(Object value : list){
-                    writeObject(value);
-                }
-                refs.remove(refs.size()-1);
-                return;
-            }else if (object instanceof Number){
-                Number number = (Number) object;
-                writeNumber(number);
-                return;
-            }else if (object instanceof  Boolean){
-                ensureCapacity(2);
-                Boolean value  = (Boolean) object;
-                if(value){
-                    writeByte(BOOLEAN_TYPE_TRUE);
-                }else{
-                    writeByte(BOOLEAN_TYPE_FALSE);
-                }
-                return;
-            }else if(object == null){
-                ensureCapacity(2);
-                writeByte(NULL_TYPE);
-                return;
-            }else if (object.getClass().isArray()){
-                if(refs.contains(object)){
-                    ensureCapacity(2);
-                    writeByte(NULL_TYPE);
-                    return;
-                }
-                refs.add(object);
-                ensureCapacity(8);
-                int length = Array.getLength(object);
-                writeByte(ARRAY_TYPE);
-                writeUInt(length);
-                for(int i=0; i<length; i++){
-                    Object value = Array.get(object, i);
-                    writeObject(value);
-                }
-                refs.remove(refs.size()-1);
-                return;
-            }else  if(object instanceof  Date){
-                ensureCapacity(10);
-                double date = ((Date)object).getTime();
-                writeByte(NUMBER_DOUBLE_TYPE);
-                writeDouble(date);
-            }else  if(object instanceof  Calendar){
-                ensureCapacity(10);
-                double date = ((Calendar)object).getTime().getTime();
-                writeByte(NUMBER_DOUBLE_TYPE);
-                writeDouble(date);
-            }else  if(object instanceof  Collection){
-                if(refs.contains(object)){
-                    ensureCapacity(2);
-                    writeByte(NULL_TYPE);
-                    return;
-                }
-                refs.add(object);
-                ensureCapacity(8);
-                Collection list = (Collection) object;
-                writeByte(ARRAY_TYPE);
-                writeUInt(list.size());
-                for(Object value : list){
-                    writeObject(value);
-                }
-                refs.remove(refs.size()-1);
-            }else{
-                if(refs.contains(object)){
-                    ensureCapacity(2);
-                    writeByte(NULL_TYPE);
-                }else {
-                    refs.add(object);
-                    if(object.getClass().isEnum()){
-                        writeObject(JSON.toJSONString(object));
-                    }else{
-                        writeAdapterObject(object);
-                    }
-                    refs.remove(refs.size()-1);
-                }
-                return;
-            }
-        }
-
-        private final void writeNumber(Number number) {
-            ensureCapacity(12);
-            if(number instanceof  Integer){
-                writeByte(NUMBER_INT_TYPE);
-                writeVarInt(number.intValue());
-                return;
-            }
-
-            if(number instanceof Float){
-                writeByte(NUMBER_FLOAT_TYPE);
-                writeFloat(number.floatValue());
-                return;
-            }
-            if(number instanceof  Double){
-                writeByte(NUMBER_DOUBLE_TYPE);
-                writeDouble(number.doubleValue());
-                return;
-            }
-
-            if(number instanceof  Long){
-                writeByte(NUMBER_LONG_TYPE);
-                writeLong(number.longValue());
-                return;
-            }
-
-            if(number instanceof  Short
-                    || number instanceof  Byte){
-                writeByte(NUMBER_INT_TYPE);
-                writeVarInt(number.intValue());
-                return;
-            }
-
-            if(number instanceof BigInteger){
-                writeByte(NUMBER_BIG_INTEGER_TYPE);
-                writeUTF16String(number.toString());
-                return;
-            }
-
-            if(number instanceof BigDecimal){
-                String value = number.toString();
-                double doubleValue = number.doubleValue();
-                if(value.equals(Double.toString(doubleValue))){
-                    writeByte(NUMBER_DOUBLE_TYPE);
-                    writeDouble(doubleValue);
-                }else {
-                    writeByte(NUMBER_BIG_DECIMAL_TYPE);
-                    writeUTF16String(value);
-                }
-                return;
-            }
-            writeByte(STRING_TYPE);
-            writeUTF16String(number.toString());
-
-        }
-
-        private final  void writeMap(Map map) {
-            if(WriteMapNullValue){
-                ensureCapacity(8);
-                writeByte(MAP_TYPE);
-                writeUInt(map.size());
-                Set<Map.Entry<Object,Object>>  entries = map.entrySet();
-                for(Map.Entry<Object,Object> entry : entries){
-                    writeMapKeyUTF16(entry.getKey().toString());
-                    writeObject(entry.getValue());
-                }
-            }else{
-                Set<Map.Entry<Object,Object>>  entries = map.entrySet();
-                int nullValueSize = 0;
-                for(Map.Entry<Object,Object> entry : entries){
-                    if(entry.getValue() == null){
-                        nullValueSize++;
-                    }
-                }
-
-                ensureCapacity(8);
-                writeByte(MAP_TYPE);
-                writeUInt(map.size()-nullValueSize);
-                for(Map.Entry<Object,Object> entry : entries){
-                    if(entry.getValue() == null){
-                        continue;
-                    }
-                    writeMapKeyUTF16(entry.getKey().toString());
-                    writeObject(entry.getValue());
-                }
-            }
-        }
-
-
-        private final void writeByte(byte type){
-            buffer[position] = type;
-            position++;
-        }
-
-        private final void writeAdapterObject(Object object){
-            if(specialClass.get(object.getClass().getName()) != null){
-                writeObject(JSON.toJSON(object));
-                return;
-            }
-            try{
-                writeMap(toMap(object));
-            }catch (Exception e){
-                specialClass.put(object.getClass().getName(), true);
-                writeObject(JSON.toJSON(object));
-            }
-        }
-
-        private  final Map  toMap(Object object){
-            Map map = new JSONObject();
-            try {
-                Class<?> targetClass = object.getClass();
-                String key = targetClass.getName();
-                List<Method> methods = getBeanMethod(key, targetClass);
-                for (Method method : methods) {
-                    String methodName = method.getName();
-                    if (methodName.startsWith(METHOD_PREFIX_GET)) {
-                        Object value = method.invoke(object);
-                        if(value != null){
-                            StringBuilder builder = new StringBuilder(method.getName().substring(3));
-                            builder.setCharAt(0, Character.toLowerCase(builder.charAt(0)));
-                            map.put(builder.toString(), (Object) value);
-                        }
-                    }else if(methodName.startsWith(METHOD_PREFIX_IS)){
-                        Object value = method.invoke(object);
-                        if(value != null){
-                            StringBuilder builder = new StringBuilder(method.getName().substring(2));
-                            builder.setCharAt(0, Character.toLowerCase(builder.charAt(0)));
-                            map.put(builder.toString(), value);
-                        }
-                    }
-                }
-                List<Field> fields = getBeanFields(key, targetClass);
-                for(Field field : fields){
-                    String fieldName = field.getName();
-                    if(map.containsKey(fieldName)){
-                        continue;
-                    }
-                    Object value  = field.get(object);
-                    if(value == null){
-                        continue;
-                    }
-                    map.put(fieldName, value);
-                }
-            }catch (Exception e){
-                if(e instanceof  RuntimeException){
-                    throw  (RuntimeException)e;
-                }else{
-                    throw  new RuntimeException(e);
-                }
-            }
-            return  map;
-        }
-
-        private  final void writeMapKeyUTF16(String value){
-            writeUTF16String(value);
-        }
-
-
-
-
-        /**
-         * writeString UTF-16
-         * */
-        private  final void writeUTF16String(CharSequence value){
-            int length = value.length();
-            ensureCapacity(length*2 + 8);
-            writeUInt(length*2);
-            if(IS_NATIVE_LITTLE_ENDIAN){
-                for(int i=0; i<length; i++){
-                    char ch = value.charAt(i);
-                    buffer[position] = (byte) (ch);
-                    buffer[position+1] = (byte) (ch >>> 8);
-                    position+=2;
-                }
-            }else{
-                for(int i=0; i<length; i++){
-                    char ch = value.charAt(i);
-                    buffer[position + 1] = (byte) (ch      );
-                    buffer[position] = (byte) (ch >>> 8);
-                    position+=2;
-                }
-            }
-        }
-
-
-        private final void writeDouble(double value){
-            writeLong(Double.doubleToLongBits(value));
-        }
-
-        private final void writeFloat(float value){
-            int val = Float.floatToIntBits(value);
-            buffer[position + 3] = (byte) (val       );
-            buffer[position + 2] = (byte) (val >>>  8);
-            buffer[position + 1] = (byte) (val >>> 16);
-            buffer[position ] = (byte) (val >>> 24);
-            position += 4;
-        }
-
-        private final void writeLong(long val){
-            buffer[position + 7] = (byte) (val       );
-            buffer[position + 6] = (byte) (val >>>  8);
-            buffer[position + 5] = (byte) (val >>> 16);
-            buffer[position + 4] = (byte) (val >>> 24);
-            buffer[position + 3] = (byte) (val >>> 32);
-            buffer[position + 2] = (byte) (val >>> 40);
-            buffer[position + 1] = (byte) (val >>> 48);
-            buffer[position    ] = (byte) (val >>> 56);
-            position += 8;
-        }
-
-        private final void writeVarInt(int value){
-            writeUInt((value << 1) ^ (value >> 31));
-        }
-
-        private final void  writeUInt(int value){
-            while ((value & 0xFFFFFF80) != 0) {
-                buffer[position] = (byte)((value & 0x7F) | 0x80);
-                position++;
-                value >>>= 7;
-            }
-            buffer[position] = (byte)(value & 0x7F);
-            position++;
-        }
-
-
-        private final void ensureCapacity(int minCapacity) {
-            minCapacity += position;
-            // overflow-conscious code
-            if (minCapacity - buffer.length > 0){
-                int oldCapacity = buffer.length;
-                int newCapacity = oldCapacity << 1;
-                if(newCapacity < 1024*16){
-                    newCapacity = 1024*16;
-                }
-                if (newCapacity - minCapacity < 0) {
-                    newCapacity = minCapacity;
-                }
-                buffer = Arrays.copyOf(buffer, newCapacity);
-            }
-        }
-    }
-
-
-    /**
-     * cache json property key, most of them all same
-     * */
-    private static final int GLOBAL_STRING_CACHE_SIZE = 2*1024;
-    private static final ThreadLocal<char[]> localCharsBufferCache = new ThreadLocal<>();
-    private static final String[] globalStringBytesCache = new String[GLOBAL_STRING_CACHE_SIZE];
-
-
-
-
-    /**
-     * lru cache, to map helper
-     * */
-    private static final String METHOD_PREFIX_GET = "get";
-    private static final String METHOD_PREFIX_IS = "is";
-    private static LruCache<String, List<Method>> methodsCache = new LruCache<>(128);
-    private static LruCache<String, List<Field>> fieldsCache = new LruCache<>(128);
-    private static LruCache<String, Boolean> specialClass = new LruCache<>(16);
-
-
-    private static final List<Method> getBeanMethod(String key, Class targetClass){
-        List<Method> methods = methodsCache.get(key);
-        if(methods == null){
-            methods = new ArrayList<>();
-            Method[]  allMethods = targetClass.getMethods();
-            for(Method method : allMethods){
-                if(method.getDeclaringClass() == Object.class){
-                    continue;
-                }
-                if( (method.getModifiers() & Modifier.STATIC) != 0){
-                    continue;
-                }
-                String methodName = method.getName();
-                if(methodName.startsWith(METHOD_PREFIX_GET)
-                        || methodName.startsWith(METHOD_PREFIX_IS)) {
-                    if(method.getAnnotation(JSONField.class) != null){
-                        throw new UnsupportedOperationException("getBeanMethod JSONField Annotation Not Handled, Use toJSON");
-                    }
-                    methods.add(method);
-                }
-            }
-            methodsCache.put(key, methods);
-        }
-        return methods;
-    }
-
-
-
-    private static  final List<Field> getBeanFields(String key, Class targetClass){
-        List<Field> fieldList = fieldsCache.get(key);
-        if(fieldList == null) {
-            Field[] fields = targetClass.getFields();
-            fieldList = new ArrayList<>(fields.length);
-            for(Field field : fields){
-                if((field.getModifiers() & Modifier.STATIC) != 0){
-                    continue;
-                }
-                if(field.getAnnotation(JSONField.class) != null){
-                    throw new UnsupportedOperationException("getBeanMethod JSONField Annotation Not Handled, Use toJSON");
-                }
-                fieldList.add(field);
-            }
-            fieldsCache.put(key, fieldList);
-        }
-        return  fieldList;
-    }
-
-}
diff --git a/android/sdk/src/main/java/com/taobao/weex/wson/WsonUtils.java b/android/sdk/src/main/java/com/taobao/weex/wson/WsonUtils.java
deleted file mode 100644
index dc51438..0000000
--- a/android/sdk/src/main/java/com/taobao/weex/wson/WsonUtils.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/**
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.wson;
-
-import com.taobao.weex.utils.WXLogUtils;
-
-/**
- * Created by furture on 2018/5/17.
- */
-
-public class WsonUtils {
-    /**
-     * total entry, with wson support, always parse json
-     * */
-    public static final Object parseWson(byte[] data){
-        if(data == null){
-            return  null;
-        }
-        try{
-            return  Wson.parse(data);
-        }catch (Exception e){
-            WXLogUtils.e("weex wson parse error ", e);
-            return  null;
-        }
-    }
-
-    public static final byte[] toWson(Object data){
-        if(data == null){
-            return  null;
-        }
-        try{
-            return  Wson.toWson(data);
-        }catch (Exception e){
-            WXLogUtils.e("weex wson to wson error ", e);
-            return  null;
-        }
-    }
-}
diff --git a/android/sdk/src/main/java/org/apache/weex/ComponentObserver.java b/android/sdk/src/main/java/org/apache/weex/ComponentObserver.java
new file mode 100644
index 0000000..f77eb7e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ComponentObserver.java
@@ -0,0 +1,50 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex;
+
+import android.view.View;
+
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by sospartan on 14/06/2017.
+ */
+
+public interface ComponentObserver {
+
+  /**
+   * Called after component is create.
+   * Notice: View is not created at this moment.
+   * @param component
+   */
+  void onCreate(WXComponent component);
+
+  /**
+   * Called before component destroy.
+   * @param component
+   */
+  void onPreDestory(WXComponent component);
+
+  /**
+   * Called when component's view is created
+   * @param component
+   * @param view
+   */
+  void onViewCreated(WXComponent component,View view);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/IWXActivityStateListener.java b/android/sdk/src/main/java/org/apache/weex/IWXActivityStateListener.java
new file mode 100644
index 0000000..0398aec
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/IWXActivityStateListener.java
@@ -0,0 +1,41 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex;
+
+/**
+ * Listener class for activity lifecycle
+ */
+
+@Deprecated
+public interface IWXActivityStateListener {
+
+  void onActivityCreate();
+
+  void onActivityStart();
+
+  void onActivityPause();
+
+  void onActivityResume();
+
+  void onActivityStop();
+
+  void onActivityDestroy();
+
+  boolean onActivityBack();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/IWXRenderListener.java b/android/sdk/src/main/java/org/apache/weex/IWXRenderListener.java
new file mode 100644
index 0000000..82f70fa
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/IWXRenderListener.java
@@ -0,0 +1,50 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex;
+
+import android.view.View;
+import org.apache.weex.common.WXRenderStrategy;
+
+public interface IWXRenderListener {
+
+  /**
+   * If {@link WXRenderStrategy#APPEND_ASYNC} is applied, this method
+   * will be invoked when the rendering of first view is finish.
+   * If {@link WXRenderStrategy#APPEND_ONCE} is applied, this method will
+   * be invoked when the rendering of the view tree is finished.
+   */
+  void onViewCreated(WXSDKInstance instance, View view);
+
+  /**
+   * Called when the render view phase of weex has finished.
+   * It can be invoked at most once in the entire life of a {@link WXSDKInstance}
+   */
+  void onRenderSuccess(WXSDKInstance instance, int width, int height);
+
+  /**
+   * Callback method, called when refresh is finished
+   */
+  void onRefreshSuccess(WXSDKInstance instance, int width, int height);
+
+  /**
+   * Report exception occurred when weex instance is running. Exception <strong>may not</strong>
+   * cause user-noticeable failure of weex.
+   */
+  void onException(WXSDKInstance instance, String errCode, String msg);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/IWXStatisticsListener.java b/android/sdk/src/main/java/org/apache/weex/IWXStatisticsListener.java
new file mode 100644
index 0000000..580b02a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/IWXStatisticsListener.java
@@ -0,0 +1,66 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex;
+
+public interface IWXStatisticsListener {
+  /**
+   * Called when weex sdk engine begin to initialize.
+   */
+   void onSDKEngineInitialize();
+
+  /**
+   * Called when begin to load js framework.
+   */
+   void onJsFrameworkStart();
+
+  /**
+   * Called when finish loading js framework.
+   */
+   void onJsFrameworkReady();
+
+  /**
+   * Called when the render view phase of first view reached.
+   */
+   void onFirstView();
+
+  /**
+   * Called when the render view phase of first screen reached.
+   */
+  void onFirstScreen();
+
+  /**
+   * Called when to start a http request.
+   */
+  void onHttpStart();
+
+  /**
+   * Called when received a http response header data.
+   */
+  void onHeadersReceived();
+
+  /**
+   * Called when to finish a http request.
+   */
+  void onHttpFinish();
+
+  /**
+   * Called when an exception occured.
+   */
+  void onException(String instanceid, String errCode, String msg);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/InitConfig.java b/android/sdk/src/main/java/org/apache/weex/InitConfig.java
new file mode 100644
index 0000000..911271b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/InitConfig.java
@@ -0,0 +1,249 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex;
+
+import android.support.annotation.NonNull;
+import org.apache.weex.adapter.ClassLoaderAdapter;
+import org.apache.weex.adapter.IDrawableLoader;
+import org.apache.weex.adapter.IWXHttpAdapter;
+import org.apache.weex.adapter.IWXImgLoaderAdapter;
+import org.apache.weex.adapter.IWXJSExceptionAdapter;
+import org.apache.weex.adapter.IWXJsFileLoaderAdapter;
+import org.apache.weex.adapter.IWXJscProcessManager;
+import org.apache.weex.adapter.IWXSoLoaderAdapter;
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.appfram.storage.IWXStorageAdapter;
+import org.apache.weex.appfram.websocket.IWebSocketAdapterFactory;
+import org.apache.weex.performance.IApmGenerator;
+import java.util.LinkedList;
+import java.util.List;
+
+/**
+ * Created by sospartan on 5/31/16.
+ */
+public class InitConfig {
+  private IWXHttpAdapter httpAdapter;
+  private IDrawableLoader drawableLoader;
+  private IWXImgLoaderAdapter imgAdapter;
+  private IWXUserTrackAdapter utAdapter;
+  private IWXStorageAdapter storageAdapter;
+  private IWXSoLoaderAdapter soLoader;
+  private URIAdapter mURIAdapter;
+  private IWebSocketAdapterFactory webSocketAdapterFactory;
+  private IWXJSExceptionAdapter mJSExceptionAdapter;
+  private String framework;
+  private ClassLoaderAdapter classLoaderAdapter;
+  private IApmGenerator apmGenerater;
+  private IWXJsFileLoaderAdapter jsFileLoaderAdapter;
+  private IWXJscProcessManager jscProcessManager;
+  private List<String> nativeLibraryList;
+
+  public IWXHttpAdapter getHttpAdapter() {
+    return httpAdapter;
+  }
+
+  public IWXImgLoaderAdapter getImgAdapter() {
+    return imgAdapter;
+  }
+
+  public IDrawableLoader getDrawableLoader() {
+    return drawableLoader;
+  }
+
+  public IWXUserTrackAdapter getUtAdapter() {
+    return utAdapter;
+  }
+
+  public IWXSoLoaderAdapter getIWXSoLoaderAdapter() {
+    return soLoader;
+  }
+
+  public String getFramework() {
+    return framework;
+  }
+
+  public IWXStorageAdapter getStorageAdapter() {
+    return storageAdapter;
+  }
+
+  public URIAdapter getURIAdapter() {
+    return mURIAdapter;
+  }
+
+  public IWebSocketAdapterFactory getWebSocketAdapterFactory() {
+    return webSocketAdapterFactory;
+  }
+
+  public ClassLoaderAdapter getClassLoaderAdapter() {
+    return classLoaderAdapter;
+  }
+
+  public IApmGenerator getApmGenerater() {
+    return apmGenerater;
+  }
+
+  public IWXJsFileLoaderAdapter getJsFileLoaderAdapter() {
+    return jsFileLoaderAdapter;
+  }
+
+  public InitConfig setClassLoaderAdapter(ClassLoaderAdapter classLoaderAdapter) {
+    this.classLoaderAdapter = classLoaderAdapter;
+    return this;
+  }
+
+  public IWXJSExceptionAdapter getJSExceptionAdapter() {
+    return mJSExceptionAdapter;
+  }
+  public IWXJscProcessManager getJscProcessManager() {
+    return jscProcessManager;
+  }
+
+  @NonNull Iterable<String> getNativeLibraryList() {
+    if(nativeLibraryList == null){
+      nativeLibraryList = new LinkedList<>();
+    }
+    return nativeLibraryList;
+  }
+
+  private InitConfig() {
+  }
+
+  public static class Builder{
+    IWXHttpAdapter httpAdapter;
+    IWXImgLoaderAdapter imgAdapter;
+    IDrawableLoader drawableLoader;
+    IWXUserTrackAdapter utAdapter;
+    IWXStorageAdapter storageAdapter;
+    IWXSoLoaderAdapter soLoader;
+    URIAdapter mURIAdapter;
+    IWXJSExceptionAdapter mJSExceptionAdapter;
+    String framework;
+    IWebSocketAdapterFactory webSocketAdapterFactory;
+    ClassLoaderAdapter classLoaderAdapter;
+    IApmGenerator apmGenerater;
+    private IWXJsFileLoaderAdapter jsFileLoaderAdapter;
+    private List<String> nativeLibraryList = new LinkedList<>();
+
+    public IWXJscProcessManager getJscProcessManager() {
+      return jscProcessManager;
+    }
+
+    public Builder setJscProcessManager(IWXJscProcessManager jscProcessManager) {
+      this.jscProcessManager = jscProcessManager;
+      return this;
+    }
+
+    IWXJscProcessManager jscProcessManager;
+
+    public Builder(){
+
+    }
+
+    public Builder setHttpAdapter(IWXHttpAdapter httpAdapter) {
+      this.httpAdapter = httpAdapter;
+      return this;
+    }
+
+    public Builder setImgAdapter(IWXImgLoaderAdapter imgAdapter) {
+      this.imgAdapter = imgAdapter;
+      return this;
+    }
+
+    public Builder setDrawableLoader(IDrawableLoader drawableLoader){
+      this.drawableLoader=drawableLoader;
+      return this;
+    }
+
+    public Builder setUtAdapter(IWXUserTrackAdapter utAdapter) {
+      this.utAdapter = utAdapter;
+      return this;
+    }
+
+    public Builder setStorageAdapter(IWXStorageAdapter storageAdapter) {
+      this.storageAdapter = storageAdapter;
+      return this;
+    }
+
+    public Builder setURIAdapter(URIAdapter URIAdapter) {
+      mURIAdapter = URIAdapter;
+      return this;
+    }
+
+    public Builder setJSExceptionAdapter(IWXJSExceptionAdapter JSExceptionAdapter) {
+      mJSExceptionAdapter = JSExceptionAdapter;
+      return this;
+    }
+
+    public Builder setSoLoader(IWXSoLoaderAdapter loader) {
+      this.soLoader = loader;
+      return this;
+    }
+
+    public Builder setFramework(String framework){
+      this.framework=framework;
+      return this;
+    }
+
+    public Builder setWebSocketAdapterFactory(IWebSocketAdapterFactory factory) {
+      this.webSocketAdapterFactory = factory;
+      return this;
+    }
+
+    public Builder setClassLoaderAdapter(ClassLoaderAdapter classLoaderAdapter) {
+      this.classLoaderAdapter = classLoaderAdapter;
+      return this;
+    }
+
+    public Builder setApmGenerater(IApmGenerator apmGenerater){
+      this.apmGenerater =apmGenerater;
+      return this;
+    }
+
+    public Builder setJsFileLoaderAdapter(IWXJsFileLoaderAdapter jsFileLoaderAdapter) {
+      this.jsFileLoaderAdapter = jsFileLoaderAdapter;
+      return this;
+    }
+
+    public Builder addNativeLibrary(String name){
+      nativeLibraryList.add(name);
+      return this;
+    }
+
+    public InitConfig build(){
+      InitConfig config =  new InitConfig();
+      config.httpAdapter = this.httpAdapter;
+      config.imgAdapter = this.imgAdapter;
+      config.drawableLoader = this.drawableLoader;
+      config.utAdapter = this.utAdapter;
+      config.storageAdapter = this.storageAdapter;
+      config.soLoader=this.soLoader;
+      config.framework=this.framework;
+      config.mURIAdapter = this.mURIAdapter;
+      config.webSocketAdapterFactory = this.webSocketAdapterFactory;
+      config.mJSExceptionAdapter=this.mJSExceptionAdapter;
+      config.classLoaderAdapter = this.classLoaderAdapter;
+      config.apmGenerater = this.apmGenerater;
+      config.jsFileLoaderAdapter = this.jsFileLoaderAdapter;
+      config.jscProcessManager = this.jscProcessManager;
+      config.nativeLibraryList = this.nativeLibraryList;
+      return config;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/RenderContainer.java b/android/sdk/src/main/java/org/apache/weex/RenderContainer.java
new file mode 100644
index 0000000..29af1b6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/RenderContainer.java
@@ -0,0 +1,96 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex;
+
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.os.Build;
+import android.util.AttributeSet;
+import android.view.View;
+
+
+import org.apache.weex.render.WXAbstractRenderContainer;
+
+/**
+ * Created by sospartan on 08/10/2016.
+ */
+
+public class RenderContainer extends WXAbstractRenderContainer implements WeexFrameRateControl.VSyncListener{
+  private WeexFrameRateControl mFrameRateControl;
+
+  public RenderContainer(Context context) {
+    super(context);
+    mFrameRateControl = new WeexFrameRateControl(this);
+  }
+
+  public RenderContainer(Context context, AttributeSet attrs) {
+    super(context, attrs);
+    mFrameRateControl = new WeexFrameRateControl(this);
+  }
+
+  public RenderContainer(Context context, AttributeSet attrs, int defStyleAttr) {
+    super(context, attrs, defStyleAttr);
+    mFrameRateControl = new WeexFrameRateControl(this);
+  }
+
+  @TargetApi(Build.VERSION_CODES.LOLLIPOP)
+  public RenderContainer(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
+    super(context, attrs, defStyleAttr, defStyleRes);
+    mFrameRateControl = new WeexFrameRateControl(this);
+  }
+
+
+
+  @Override
+  public void onAttachedToWindow() {
+    super.onAttachedToWindow();
+    if (mFrameRateControl != null) {
+      mFrameRateControl.start();
+    }
+  }
+
+  @Override
+  protected void onDetachedFromWindow() {
+    super.onDetachedFromWindow();
+    if (mFrameRateControl != null) {
+      mFrameRateControl.stop();
+    }
+  }
+  @Override
+  public void dispatchWindowVisibilityChanged(int visibility) {
+    super.dispatchWindowVisibilityChanged(visibility);
+    if (visibility == View.GONE) {
+      if (mFrameRateControl != null) {
+        mFrameRateControl.stop();
+      }
+    } else if (visibility == View.VISIBLE) {
+      if (mFrameRateControl != null) {
+        mFrameRateControl.start();
+      }
+    }
+  }
+
+  @Override
+  public void OnVSync() {
+    if (mSDKInstance != null && mSDKInstance.get() != null) {
+      mSDKInstance.get().OnVSync();
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/Script.java b/android/sdk/src/main/java/org/apache/weex/Script.java
new file mode 100644
index 0000000..6688fc3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/Script.java
@@ -0,0 +1,55 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex;
+
+import android.text.TextUtils;
+
+public class Script {
+    private String mContent;
+    private byte[] mBinary;
+
+    public Script(String content) {
+        mContent = content;
+    }
+
+    public Script(byte[] binary) {
+        mBinary = binary;
+    }
+
+    public String getContent() {
+        return mContent;
+    }
+
+    public byte[] getBinary() {
+        return mBinary;
+    }
+
+    public int length() {
+        if (mContent != null) {
+            return mContent.length();
+        } else if (mBinary != null){
+            return mBinary.length;
+        }
+        return 0;
+    }
+
+    public boolean isEmpty() {
+        return TextUtils.isEmpty(mContent) && (mBinary == null || mBinary.length == 0);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/WXEnvironment.java b/android/sdk/src/main/java/org/apache/weex/WXEnvironment.java
new file mode 100644
index 0000000..7fc01e6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/WXEnvironment.java
@@ -0,0 +1,692 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex;
+
+import static android.content.Context.MODE_PRIVATE;
+
+import android.annotation.SuppressLint;
+import android.app.Application;
+import android.content.Context;
+import android.content.SharedPreferences;
+import android.content.pm.ApplicationInfo;
+import android.content.pm.PackageInfo;
+import android.content.pm.PackageManager;
+import android.graphics.Typeface;
+import android.os.Environment;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.telephony.TelephonyManager;
+import android.text.TextUtils;
+import dalvik.system.PathClassLoader;
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.util.HashMap;
+import java.util.Locale;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import org.apache.weex.R;
+import org.apache.weex.common.WXConfig;
+import org.apache.weex.utils.FontDO;
+import org.apache.weex.utils.LogLevel;
+import org.apache.weex.utils.TypefaceUtil;
+import org.apache.weex.utils.WXFileUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXSoInstallMgrSdk;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+public class WXEnvironment {
+
+  public static final String OS = "android";
+  public static String SYS_VERSION = android.os.Build.VERSION.RELEASE;
+  static{
+    if(SYS_VERSION != null && SYS_VERSION.toUpperCase(Locale.ROOT).equals("P")){
+        SYS_VERSION = "9.0.0";
+    }
+    if(SYS_VERSION != null && SYS_VERSION.toUpperCase(Locale.ROOT).equals("Q")){
+       SYS_VERSION = "10.0.0";
+    }
+  }
+  public static final String SYS_MODEL = android.os.Build.MODEL;
+  public static final String EAGLE = "eagle";
+  public static final String ENVIRONMENT = "environment";
+  public static final String WEEX_CURRENT_KEY = "wx_current_url";
+  /*********************
+   * Global config
+   ***************************/
+
+  public static String JS_LIB_SDK_VERSION = BuildConfig.buildJavascriptFrameworkVersion;
+
+  public static String WXSDK_VERSION = BuildConfig.buildVersion;
+  public static Application sApplication;
+  public static final String DEV_Id = getDevId();
+  @Deprecated
+  public static int sDefaultWidth = 750;
+  public volatile static boolean JsFrameworkInit = false;
+
+  public static final String SETTING_EXCLUDE_X86SUPPORT = "env_exclude_x86";
+
+  public static boolean SETTING_FORCE_VERTICAL_SCREEN = false;
+
+  /**
+   * auto adjust device width for when screen size change.
+   * */
+  public static boolean AUTO_ADJUST_ENV_DEVICE_WIDTH = true;
+
+  public static boolean AUTO_UPDATE_APPLICATION_SCREEN_SIZE = true;
+
+  @RestrictTo(Scope.LIBRARY)
+  public static volatile boolean sUseRunTimeApi;
+
+  /**
+   * Debug model
+   */
+  public static boolean sDebugMode = false;
+  public static final boolean sForceEnableDevTool = true;
+  public static String sDebugWsUrl = "";
+  public static boolean sDebugServerConnectable = false;
+  public static boolean sRemoteDebugMode = false;
+  public static String sRemoteDebugProxyUrl = "";
+  public static boolean sDebugNetworkEventReporterEnable = false;//debugtool network switch
+  public static long sJSLibInitTime = 0;
+
+  public static long sSDKInitStart = 0;// init start timestamp
+  public static long sSDKInitInvokeTime = 0;//time cost to invoke init method
+  public static long sSDKInitExecuteTime = 0;//time cost to execute init job
+  /** from init to sdk-ready **/
+  public static long sSDKInitTime =0;
+
+  public static long sJSFMStartListenerTime=0;
+
+  public static volatile boolean isWsFixMode = true;
+
+  /**
+   * component and modules ready
+   * */
+  public static long sComponentsAndModulesReadyTime = 0;
+
+  public static boolean sInAliWeex = false;
+
+  public static LogLevel sLogLevel = LogLevel.DEBUG;
+  private static boolean isApkDebug = true;
+  public static boolean isPerf = false;
+  private static boolean sDebugFlagInit = false;
+
+  private static boolean openDebugLog = true;
+
+  private static String sGlobalFontFamily;
+
+  public static final String CORE_SO_NAME = "weexcore";
+  public static final String CORE_JSS_SO_NAME = "weexjss";
+  public static final String CORE_JSB_SO_NAME = "weexjsb";
+  public static final String CORE_JST_SO_NAME = "weexjst";
+
+  @RestrictTo(Scope.LIBRARY)
+  public static String CORE_JSC_SO_NAME = BuildConfig.JSInterpolatorName;
+  public static  String CORE_JSS_SO_PATH = null;
+
+  private static String CORE_JSS_ICU_PATH = null;
+
+  private static String CORE_JSC_SO_PATH = null;
+
+  public static String CORE_JSB_SO_PATH = null;
+
+  private static String COPY_SO_DES_DIR = null;
+
+  private static String LIB_LD_PATH = null;
+
+  private static Map<String, String> options = new ConcurrentHashMap<>();
+  static {
+    options.put(WXConfig.os, OS);
+    options.put(WXConfig.osName, OS);
+  }
+
+
+  public static synchronized WXDefaultSettings getWXDefaultSettings() {
+    if (mWXDefaultSettings == null && getApplication() != null) {
+      mWXDefaultSettings = new WXDefaultSettings(getApplication());
+    }
+    return mWXDefaultSettings;
+  }
+
+  public static synchronized String getDefaultSettingValue(String key, String defaultValue) {
+    WXDefaultSettings wxDefaultSettings = getWXDefaultSettings();
+    if (wxDefaultSettings == null || TextUtils.isEmpty(key)) {
+      return defaultValue;
+    }
+    return wxDefaultSettings.getValue(key, defaultValue);
+  }
+
+  public static synchronized void writeDefaultSettingsValue(String key, String value) {
+    WXDefaultSettings wxDefaultSettings = getWXDefaultSettings();
+    if (wxDefaultSettings == null
+            || TextUtils.isEmpty(key)
+            || TextUtils.isEmpty(value)) {
+      return;
+    }
+    wxDefaultSettings.saveValue(key, value);
+  }
+
+  private static WXDefaultSettings mWXDefaultSettings;
+
+  /**
+   * dynamic
+   */
+  public static boolean sDynamicMode = false;
+  public static String sDynamicUrl = "";
+
+  /**
+   * Fetch system information.
+   * @return map contains system information.
+   */
+  public static Map<String, String> getConfig() {
+    Map<String, String> configs = new HashMap<>();
+    configs.put(WXConfig.os, OS);
+    configs.put(WXConfig.appVersion, getAppVersionName());
+    configs.put(WXConfig.cacheDir, getAppCacheFile());
+    configs.put(WXConfig.devId, DEV_Id);
+    configs.put(WXConfig.sysVersion, SYS_VERSION);
+    configs.put(WXConfig.sysModel, SYS_MODEL);
+    configs.put(WXConfig.weexVersion, String.valueOf(WXSDK_VERSION));
+
+    try {
+      configs.put(WXConfig.layoutDirection, isLayoutDirectionRTL() ? "rtl" : "ltr");
+    } catch (Exception e) {
+      configs.put(WXConfig.layoutDirection, "ltr");
+    }
+
+    try {
+      if (isApkDebugable()) {
+        addCustomOptions(WXConfig.debugMode, "true");
+      }
+      addCustomOptions(WXConfig.scale, Float.toString(sApplication.getResources().getDisplayMetrics().density));
+      addCustomOptions(WXConfig.androidStatusBarHeight, Float.toString(WXViewUtils.getStatusBarHeight(sApplication)));
+    }catch (NullPointerException e){
+      //There is little chance of NullPointerException as sApplication may be null.
+      WXLogUtils.e("WXEnvironment scale Exception: ", e);
+    }
+    configs.putAll(getCustomOptions());
+    if(configs.get(WXConfig.appName)==null && sApplication!=null){
+      configs.put(WXConfig.appName, sApplication.getPackageName());
+    }
+    return configs;
+  }
+
+  /**
+   * Get the version of the current app.
+   */
+  public static String getAppVersionName() {
+    String versionName = "";
+    PackageManager manager;
+    PackageInfo info = null;
+    try {
+      manager = sApplication.getPackageManager();
+      info = manager.getPackageInfo(sApplication.getPackageName(), 0);
+      versionName = info.versionName;
+    } catch (Exception e) {
+      WXLogUtils.e("WXEnvironment getAppVersionName Exception: ", e);
+    }
+    return versionName;
+  }
+
+  /**
+   *
+   * @return string cache file
+   */
+  private static String getAppCacheFile() {
+    String cache = "";
+    try {
+      cache = sApplication.getApplicationContext().getCacheDir().getPath();
+    } catch (Exception e) {
+      WXLogUtils.e("WXEnvironment getAppCacheFile Exception: ", e);
+    }
+    return cache;
+  }
+
+
+  /**
+   * Use {@link #addCustomOptions(String, String)} to add custom options.
+   * Use {@link #getCustomOptions(String)} to get custom options
+   * @return
+   */
+  @Deprecated
+  public static Map<String, String> getCustomOptions() {
+    return options;
+  }
+
+  public static void addCustomOptions(String key, String value) {
+    options.put(key, value);
+  }
+
+  public static String getCustomOptions(String key){
+    return options.get(key);
+  }
+
+
+  @SuppressLint("SdCardPath")
+  public static String copySoDesDir() {
+    try {
+      if (TextUtils.isEmpty(COPY_SO_DES_DIR)) {
+        if (sApplication == null) {
+          WXLogUtils.e("sApplication is null, so copy path will be null");
+          return null;
+        }
+
+        String dirName = "/cache/weex/libs";
+        File desDir = null;
+        String cachePath = WXEnvironment.getApplication().getApplicationContext().getCacheDir().getPath();
+
+        if (TextUtils.isEmpty(cachePath)) {
+          desDir = new File(cachePath, dirName);
+        } else {
+          String pkgName = sApplication.getPackageName();
+          String toPath = "/data/data/" + pkgName + dirName;
+          desDir = new File(toPath);
+        }
+
+        if (!desDir.exists()) {
+          desDir.mkdirs();
+        }
+        COPY_SO_DES_DIR = desDir.getAbsolutePath();
+      }
+    } catch (Throwable e) {
+      WXLogUtils.e(WXLogUtils.getStackTrace(e));
+    }
+    return COPY_SO_DES_DIR;
+
+  }
+
+  @Deprecated
+  /**
+   * Use {@link #isHardwareSupport()} if you want to see whether current hardware support Weex.
+   */
+  public static boolean isSupport() {
+    boolean isInitialized = WXSDKEngine.isInitialized();
+    if(!isInitialized){
+      WXLogUtils.e("WXSDKEngine.isInitialized():" + isInitialized);
+    }
+    return isHardwareSupport() && isInitialized;
+  }
+
+  public static boolean isLayoutDirectionRTL() {
+    // support RTL
+    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR1) {
+      return sApplication.getApplicationContext().getResources().getBoolean(R.bool.weex_is_right_to_left);
+    }
+    return false;
+  }
+  /**
+   * Tell whether Weex can run on current hardware.
+   * @return true if weex can run on current hardware, otherwise false.
+   * Weex has removed the restrictions on the tablet, please use {@link #isCPUSupport()}
+   */
+  @Deprecated
+  public static boolean isHardwareSupport() {
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("isTableDevice:" + WXUtils.isTabletDevice());
+    }
+    return isCPUSupport();
+  }
+
+  /**
+   * Determine whether Weex supports the current CPU architecture
+   * @return true when support
+   */
+  public static boolean isCPUSupport(){
+    boolean excludeX86 = "true".equals(getCustomOptions().get(SETTING_EXCLUDE_X86SUPPORT));
+    boolean isX86AndExcluded = WXSoInstallMgrSdk.isX86() && excludeX86;
+    boolean isCPUSupport = WXSoInstallMgrSdk.isCPUSupport() && !isX86AndExcluded;
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("WXEnvironment.sSupport:" + isCPUSupport
+              + "isX86AndExclueded: "+ isX86AndExcluded);
+    }
+    return isCPUSupport;
+  }
+
+  public static boolean isApkDebugable() {
+    return isApkDebugable(sApplication);
+  }
+
+  public static boolean isApkDebugable(Application application) {
+    if (application == null) {
+      return false;
+    }
+
+    if (isPerf) {
+      return false;
+    }
+
+    if (sDebugFlagInit){
+      return isApkDebug;
+    }
+    try {
+      String debugModeConfig = getCustomOptions().get(WXConfig.debugMode);
+      if (TextUtils.isEmpty(debugModeConfig)){
+        ApplicationInfo info = application.getApplicationInfo();
+        isApkDebug = (info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0;
+      }else {
+        isApkDebug = Boolean.valueOf(debugModeConfig);
+      }
+    } catch (Exception e) {
+      /**
+       * Don't call WXLogUtils.e here,will cause stackoverflow
+       */
+      e.printStackTrace();
+      isApkDebug = false;
+    }
+    sDebugFlagInit = true;
+    return isApkDebug;
+  }
+
+  public static boolean isPerf() {
+    return isPerf;
+  }
+
+  @SuppressLint("HardwareIds")
+  private static String getDevId() {
+    String ret = "";
+    if(sApplication != null){
+      try{
+        ret = ((TelephonyManager) sApplication
+            .getSystemService(Context.TELEPHONY_SERVICE)).getDeviceId();
+      }catch (SecurityException | NullPointerException e){
+        WXLogUtils.e(WXLogUtils.getStackTrace(e));
+      }
+    }
+    return ret;
+  }
+
+  public static Application getApplication() {
+    return sApplication;
+  }
+
+  public void initMetrics() {
+    if (sApplication == null) {
+      return;
+    }
+  }
+
+  public static String getDiskCacheDir(Context context) {
+    if (context == null) {
+      return null;
+    }
+    String cachePath = null;
+    try {
+      if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState())
+              || !Environment.isExternalStorageRemovable()) {
+        cachePath = context.getExternalCacheDir().getPath();
+      } else {
+        cachePath = context.getCacheDir().getPath();
+      }
+    } catch (Exception e) {
+      e.printStackTrace();
+    }
+    return cachePath;
+  }
+
+  public static String getFilesDir(Context context) {
+    if (context == null) {
+      return "";
+    }
+    File filesDir = context.getFilesDir();
+    String path = "";
+    if (filesDir != null) {
+      path = filesDir.getPath();
+    } else {
+      path = WXEnvironment.getApplication().getApplicationInfo().dataDir;
+      path += File.separator;
+      path += "files";
+    }
+
+    return path;
+  }
+
+  public static String getCrashFilePath(Context context) {
+    if (context == null) {
+        return "";
+    }
+
+    File dir = context.getDir("crash", Context.MODE_PRIVATE);
+    if (dir == null)
+        return "";
+
+    String crashDir = dir.getAbsolutePath();
+
+    return crashDir;
+  }
+
+  public static String getGlobalFontFamilyName() {
+    return sGlobalFontFamily;
+  }
+
+  public static void setGlobalFontFamily(String fontFamilyName, Typeface typeface) {
+    WXLogUtils.d("GlobalFontFamily", "Set global font family: " + fontFamilyName);
+    sGlobalFontFamily = fontFamilyName;
+    if (!TextUtils.isEmpty(fontFamilyName)) {
+      if (typeface == null) {
+        TypefaceUtil.removeFontDO(fontFamilyName);
+      } else {
+        FontDO nativeFontDO = new FontDO(fontFamilyName, typeface);
+        TypefaceUtil.putFontDO(nativeFontDO);
+        WXLogUtils.d("TypefaceUtil", "Add new font: " + fontFamilyName);
+      }
+    }
+  }
+
+  public static boolean isOpenDebugLog() {
+    return openDebugLog;
+  }
+
+  public static void setOpenDebugLog(boolean openDebugLog) {
+    WXEnvironment.openDebugLog = openDebugLog;
+  }
+
+  public static void  setApkDebugable(boolean debugable){
+    isApkDebug  = debugable;
+    if(!isApkDebug){
+      openDebugLog = false;
+    }
+  }
+
+  public static String getCacheDir() {
+    final Application application = getApplication();
+    if (application == null || application.getApplicationContext() == null)
+      return null;
+    return application.getApplicationContext().getCacheDir().getPath();
+  }
+
+  public static String extractSo() {
+    File sourceFile = new File(getApplication().getApplicationContext().getApplicationInfo().sourceDir);
+    final String soDesPath = copySoDesDir();
+    if (sourceFile.exists() && !TextUtils.isEmpty(soDesPath)) {
+      try {
+        WXFileUtils.extractSo(sourceFile.getAbsolutePath(), soDesPath);
+      } catch (IOException e) {
+        WXLogUtils.e("extractSo error " + e.getMessage());
+//        e.printStackTrace();
+        return null;
+      }
+      return soDesPath;
+    }
+    return null;
+  }
+
+  private static String findIcuPath() {
+    File file = new File("/proc/self/maps");
+    BufferedReader reader = null;
+    try {
+      reader = new BufferedReader(new FileReader(file));
+      String tempString = null;
+      while ((tempString = reader.readLine()) != null) {
+        if (tempString.contains("icudt")) {
+
+          int i = tempString.indexOf('/');
+
+          String substring = tempString.substring(i);
+          return substring.trim();
+        }
+      }
+      reader.close();
+    } catch (IOException e) {
+      e.printStackTrace();
+    } finally {
+      if (reader != null) {
+        try {
+          reader.close();
+        } catch (IOException e1) {
+        }
+      }
+    }
+
+    return null;
+  }
+
+
+  public static String findSoPath(String libName) {
+    String soPath = ((PathClassLoader) (WXEnvironment.class.getClassLoader())).findLibrary(libName);
+    if (!TextUtils.isEmpty(soPath)) {
+      File soFile = new File(soPath);
+      if (soFile.exists()) {
+        WXLogUtils.e(libName + "'s Path is" + soPath);
+        return soFile.getAbsolutePath();
+      } else {
+        WXLogUtils.e(libName + "'s Path is " + soPath + " but file does not exist");
+      }
+    }
+
+    String realName = "lib" + libName + ".so";
+    String cacheDir = getCacheDir();
+    if (TextUtils.isEmpty(cacheDir)) {
+      WXLogUtils.e("cache dir is null");
+      return "";
+    }
+
+
+    if (cacheDir.indexOf("/cache") > 0) {
+      soPath = new File(cacheDir.replace("/cache", "/lib"), realName).getAbsolutePath();
+    }
+
+
+    final File soFile = new File(soPath);
+    if (soFile.exists()) {
+      WXLogUtils.e(libName + "use lib so");
+      return soPath;
+    } else {
+      //unzip from apk file
+      final String extractSoPath = extractSo();
+      if (!TextUtils.isEmpty(extractSoPath)) {
+        return new File(extractSoPath, realName).getAbsolutePath();
+      }
+    }
+    return soPath;
+  }
+
+  public static String getLibJScRealPath() {
+    if(TextUtils.isEmpty(CORE_JSC_SO_PATH)) {
+      CORE_JSC_SO_PATH = findSoPath(CORE_JSC_SO_NAME);
+      WXLogUtils.e("findLibJscRealPath " + CORE_JSC_SO_PATH);
+    }
+    return CORE_JSC_SO_PATH;
+  }
+
+  public static String getLibJssRealPath() {
+    if(TextUtils.isEmpty(CORE_JSS_SO_PATH)) {
+      CORE_JSS_SO_PATH = findSoPath(CORE_JSS_SO_NAME);
+      WXLogUtils.d("test-> findLibJssRealPath " + CORE_JSS_SO_PATH);
+    }
+
+    return CORE_JSS_SO_PATH;
+  }
+
+  public static String getLibJssIcuPath() {
+    if(TextUtils.isEmpty(CORE_JSS_ICU_PATH)){
+      CORE_JSS_ICU_PATH = findIcuPath();
+    }
+
+    return CORE_JSS_ICU_PATH;
+  }
+
+  public static String getLibLdPath() {
+    if (TextUtils.isEmpty(LIB_LD_PATH)) {
+      ClassLoader classLoader = WXEnvironment.class.getClassLoader();
+      try {
+        Method getLdLibraryPath = classLoader.getClass().getMethod("getLdLibraryPath", new Class[0]);
+        LIB_LD_PATH = (String) getLdLibraryPath.invoke(classLoader, new Object[0]);
+      } catch (IllegalAccessException e) {
+        e.printStackTrace();
+      } catch (InvocationTargetException e) {
+        e.printStackTrace();
+      } catch (NoSuchMethodException e) {
+        e.printStackTrace();
+      }
+    }
+
+    if(TextUtils.isEmpty(LIB_LD_PATH)) {
+      try {
+        String property = System.getProperty("java.library.path");
+        String libJScRealPath = getLibJScRealPath();
+        if(!TextUtils.isEmpty(libJScRealPath)) {
+          LIB_LD_PATH = new File(libJScRealPath).getParent() + ":" + property;
+        }
+      } catch (Exception e) {
+        e.printStackTrace();
+      }
+    }
+
+    WXLogUtils.d("getLibLdPath is " + LIB_LD_PATH);
+    return LIB_LD_PATH;
+  }
+
+  public static class WXDefaultSettings {
+    private String configName = "weex_default_settings";
+    private SharedPreferences sharedPreferences = null;
+    public WXDefaultSettings(Application application) {
+      if(application != null) {
+        sharedPreferences = application.getSharedPreferences(configName, MODE_PRIVATE);
+      }
+    }
+
+    public synchronized String getValue(String key, String defaultValue) {
+      if(sharedPreferences == null || TextUtils.isEmpty(key)) {
+        WXLogUtils.i("get default settings " + key + " return default value :" + defaultValue);
+        return defaultValue;
+      }
+
+      String result = sharedPreferences.getString(key, defaultValue);
+      WXLogUtils.i("get default settings " + key + " : " + result);
+      return result;
+    }
+
+    public synchronized void saveValue(String key, String value) {
+      if (sharedPreferences == null
+              || TextUtils.isEmpty(key)
+              || TextUtils.isEmpty(value)) {
+        return;
+      }
+      WXLogUtils.i("save default settings " + key + ":" + value);
+      SharedPreferences.Editor editor = sharedPreferences.edit();
+      editor.putString(key, value);
+      editor.apply();
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/WXGlobalEventModule.java b/android/sdk/src/main/java/org/apache/weex/WXGlobalEventModule.java
new file mode 100644
index 0000000..9ad32e1
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/WXGlobalEventModule.java
@@ -0,0 +1,52 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex;
+
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.common.WXModule;
+
+import java.util.Map;
+
+/**
+ * Created by lixinke on 16/8/25.
+ */
+public class WXGlobalEventModule extends WXModule {
+
+
+  @JSMethod
+  public void addEventListener(String eventName, String callback) {
+    mWXSDKInstance.addEventListener(eventName,callback);
+  }
+
+  public void removeEventListener(String eventName, String callback) {
+    mWXSDKInstance.removeEventListener(eventName,callback);
+  }
+
+  @JSMethod
+  public void removeEventListener(String eventName){
+    mWXSDKInstance.removeEventListener(eventName);
+  }
+
+
+  @Override
+  public void addEventListener(String eventName, String callback, Map<String, Object> options) {
+    super.addEventListener(eventName, callback, options);
+    addEventListener(eventName,callback);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/WXGlobalEventReceiver.java b/android/sdk/src/main/java/org/apache/weex/WXGlobalEventReceiver.java
new file mode 100644
index 0000000..75c1f85
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/WXGlobalEventReceiver.java
@@ -0,0 +1,57 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex;
+
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.HashMap;
+
+public class WXGlobalEventReceiver extends BroadcastReceiver {
+
+  public static final String EVENT_NAME = "eventName";
+  public static final String EVENT_PARAMS = "eventParams";
+  public static final String EVENT_ACTION = "wx_global_action";
+  public static final String EVENT_WX_INSTANCEID = "wx_instanceid";
+
+  private WXSDKInstance mWXSDKInstance;
+
+  public WXGlobalEventReceiver() {
+  }
+
+  public WXGlobalEventReceiver(WXSDKInstance instance) {
+    mWXSDKInstance = instance;
+  }
+
+  @Override
+  public void onReceive(Context context, Intent intent) {
+    String eventName = intent.getStringExtra(EVENT_NAME);
+    String params = intent.getStringExtra(EVENT_PARAMS);
+    HashMap<String, Object> maps = null;
+    try {
+      maps = com.alibaba.fastjson.JSON.parseObject(params, HashMap.class);
+      mWXSDKInstance.fireGlobalEventCallback(eventName, maps);
+    } catch (Exception e) {
+      WXLogUtils.e("global-receive",e);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/WXHttpListener.java b/android/sdk/src/main/java/org/apache/weex/WXHttpListener.java
new file mode 100644
index 0000000..234c3c4
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/WXHttpListener.java
@@ -0,0 +1,307 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex;
+
+import android.net.Uri;
+import android.text.TextUtils;
+
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXPerformance;
+import org.apache.weex.common.WXRenderStrategy;
+import org.apache.weex.common.WXResponse;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.tracing.WXTracing;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.tools.LogDetail;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import org.apache.weex.adapter.IWXHttpAdapter.OnHttpListener;
+
+/**
+ * load bundle js listener
+ */
+public class WXHttpListener implements OnHttpListener {
+
+    private String pageName;
+    private Map<String, Object> options;
+    private String jsonInitData;
+    private WXRenderStrategy flag;
+    private WXSDKInstance instance;
+    private long startRequestTime;
+    private int traceId;
+    private WXPerformance mWXPerformance;
+    private WXInstanceApm mApmForInstance;
+    private IWXUserTrackAdapter mUserTrackAdapter;
+    public boolean isPreDownLoadMode = false;
+    private boolean isInstanceReady =false;
+    private boolean isResponseHasWait = false;
+    private WXResponse mResponse;
+    private LogDetail mLogDetail;
+
+    private String mBundleUrl;
+
+    public WXHttpListener(WXSDKInstance instance) {
+        if(instance != null) {
+            mLogDetail = instance.mTimeCalculator.createLogDetail("downloadBundleJS");
+        }
+        this.instance = instance;
+        this.traceId = WXTracing.nextId();
+        this.mWXPerformance = instance.getWXPerformance();
+        this.mApmForInstance = instance.getApmForInstance();
+        this.mUserTrackAdapter = WXSDKManager.getInstance().getIWXUserTrackAdapter();
+        if (WXTracing.isAvailable()) {
+            WXTracing.TraceEvent event = WXTracing.newEvent("downloadBundleJS", instance.getInstanceId(), -1);
+            event.iid = instance.getInstanceId();
+            event.tname = "Network";
+            event.ph = "B";
+            event.traceId = traceId;
+            event.submit();
+        }
+    }
+
+    public WXHttpListener(WXSDKInstance instance, String bundleUrl) {
+        this(instance);
+        this.startRequestTime = System.currentTimeMillis();
+        this.mBundleUrl = bundleUrl;
+    }
+
+    public WXHttpListener(WXSDKInstance instance, String pageName, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag, long startRequestTime) {
+        this(instance);
+        this.pageName = pageName;
+        this.options = options;
+        this.jsonInitData = jsonInitData;
+        this.flag = flag;
+        this.startRequestTime = startRequestTime;
+        this.mBundleUrl = instance.getBundleUrl();
+    }
+
+    public void setSDKInstance(WXSDKInstance instance) {
+        this.instance = instance;
+    }
+
+    protected WXSDKInstance getInstance() {
+        return instance;
+    }
+
+    @Override
+    public void onHttpStart() {
+        if (this.instance != null
+                && this.instance.getWXStatisticsListener() != null) {
+            this.instance.getWXStatisticsListener().onHttpStart();
+            if(mLogDetail != null) {
+                mLogDetail.taskStart();
+            }
+        }
+    }
+
+    @Override
+    public void onHeadersReceived(int statusCode, Map<String,List<String>> headers) {
+        if (this.instance != null
+                && this.instance.getWXStatisticsListener() != null) {
+            this.instance.getWXStatisticsListener().onHeadersReceived();
+            this.instance.onHttpStart();
+        }
+        if(this.instance != null
+                && this.instance.responseHeaders != null
+                && headers != null){
+            this.instance.responseHeaders.putAll(headers);
+        }
+    }
+
+    @Override
+    public void onHttpUploadProgress(int uploadProgress) {
+
+    }
+
+    @Override
+    public void onHttpResponseProgress(int loadedLength) {
+        instance.getApmForInstance().extInfo.put(WXInstanceApm.VALUE_BUNDLE_LOAD_LENGTH,loadedLength);
+    }
+
+    @Override
+    public void onHttpFinish(WXResponse response) {
+        if(mLogDetail != null) {
+            mLogDetail.taskEnd();
+        }
+        if (this.instance != null
+                && this.instance.getWXStatisticsListener() != null) {
+            this.instance.getWXStatisticsListener().onHttpFinish();
+        }
+
+        if (WXTracing.isAvailable()) {
+            WXTracing.TraceEvent event = WXTracing.newEvent("downloadBundleJS", instance.getInstanceId(), -1);
+            event.traceId = traceId;
+            event.tname = "Network";
+            event.ph = "E";
+            event.extParams = new HashMap<>();
+            if (response != null && response.originalData != null) {
+                event.extParams.put("BundleSize", response.originalData.length);
+            }
+            event.submit();
+        }
+
+        mWXPerformance.networkTime = System.currentTimeMillis() - startRequestTime;
+        if(null!= response && response.extendParams!=null){
+            mApmForInstance.updateRecordInfo(response.extendParams);
+            Object actualNetworkTime=response.extendParams.get("actualNetworkTime");
+            mWXPerformance.actualNetworkTime=actualNetworkTime instanceof Long?(long)actualNetworkTime:0;
+
+            Object pureNetworkTime=response.extendParams.get("pureNetworkTime");
+            mWXPerformance.pureNetworkTime=pureNetworkTime instanceof Long?(long)pureNetworkTime:0;
+
+            Object connectionType=response.extendParams.get("connectionType");
+            mWXPerformance.connectionType=connectionType instanceof String?(String)connectionType:"";
+
+            Object packageSpendTime=response.extendParams.get("packageSpendTime");
+            mWXPerformance.packageSpendTime=packageSpendTime instanceof Long ?(long)packageSpendTime:0;
+
+            Object syncTaskTime=response.extendParams.get("syncTaskTime");
+            mWXPerformance.syncTaskTime=syncTaskTime instanceof Long ?(long)syncTaskTime:0;
+
+            Object requestType=response.extendParams.get("requestType");
+            mWXPerformance.requestType=requestType instanceof String?(String)requestType:"none";
+
+            Object cacheType = response.extendParams.get(WXPerformance.Dimension.cacheType.toString());
+            if(cacheType instanceof String){
+                mWXPerformance.cacheType = (String) cacheType;
+            }
+
+            Object zCacheInfo = response.extendParams.get("zCacheInfo");
+            mWXPerformance.zCacheInfo = zCacheInfo instanceof String?(String)zCacheInfo:"";
+
+            if(isNet(mWXPerformance.requestType) && mUserTrackAdapter!=null){
+                WXPerformance performance=new WXPerformance(instance.getInstanceId());
+                if(!TextUtils.isEmpty(mBundleUrl)){
+                    try {
+                        performance.args= Uri.parse(mBundleUrl).buildUpon().clearQuery().toString();
+                    } catch (Exception e) {
+                        performance.args=pageName;
+                    }
+                }
+                if(!"200".equals(response.statusCode)){
+                    performance.errCode= WXErrorCode.WX_ERR_JSBUNDLE_DOWNLOAD.getErrorCode();
+                    performance.appendErrMsg(response.errorCode);
+                    performance.appendErrMsg("|");
+                    performance.appendErrMsg(response.errorMsg);
+
+                }else if("200".equals(response.statusCode) && (response.originalData==null || response.originalData.length<=0)){
+                    performance.errCode=WXErrorCode.WX_ERR_JSBUNDLE_DOWNLOAD.getErrorCode();
+                    performance.appendErrMsg(response.statusCode);
+                    performance.appendErrMsg("|template is null!");
+                }else {
+                    performance.errCode=WXErrorCode.WX_SUCCESS.getErrorCode();
+                }
+
+                if (mUserTrackAdapter != null) {
+                    mUserTrackAdapter.commit(instance.getContext(), null, IWXUserTrackAdapter.JS_DOWNLOAD, performance, null);
+                }
+            }
+        }
+
+        if (isPreDownLoadMode){
+            if (isInstanceReady){
+                WXLogUtils.d("test->", "DownLoad didHttpFinish on http" );
+                didHttpFinish(response);
+            }else {
+                WXLogUtils.d("test->", "DownLoad end before activity created" );
+                mResponse = response;
+                isResponseHasWait = true;
+            }
+        }else {
+            didHttpFinish(response);
+        }
+
+    }
+
+    public void onInstanceReady(){
+        if (!isPreDownLoadMode){
+            return;
+        }
+        this.isInstanceReady = true;
+        if (isResponseHasWait){
+            WXLogUtils.d("test->", "preDownLoad didHttpFinish on ready" );
+            this.didHttpFinish(mResponse);
+        }
+
+    }
+
+    private void didHttpFinish(WXResponse response){
+        String wxErrorCode = WXInstanceApm.VALUE_ERROR_CODE_DEFAULT;
+        if (response!=null && response.originalData!=null && TextUtils.equals("200", response.statusCode)) {
+            mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_END);
+            onSuccess(response);
+
+            // check content-type
+        } else if (TextUtils.equals(WXErrorCode.WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR.getErrorCode(),
+                response.statusCode)) {
+            WXLogUtils.e("user intercept: WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR");
+            wxErrorCode = WXErrorCode.WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR.getErrorCode();
+            instance.onRenderError(wxErrorCode,
+                    "|response.errorMsg==" + response.errorMsg +
+                            "|instance bundleUrl = \n" + instance.getBundleUrl() +
+                            "|instance requestUrl = \n" + Uri.decode(WXSDKInstance.requestUrl)
+            );
+            onFail(response);
+
+            // check content-length
+        } else if (response!=null && response.originalData!=null && TextUtils.equals("-206", response.statusCode)) {
+            WXLogUtils.e("user intercept: WX_DEGRAD_ERR_NETWORK_CHECK_CONTENT_LENGTH_FAILED");
+            wxErrorCode =  WXErrorCode.WX_DEGRAD_ERR_NETWORK_CHECK_CONTENT_LENGTH_FAILED.getErrorCode();
+            instance.onRenderError(wxErrorCode ,
+                    WXErrorCode.WX_DEGRAD_ERR_NETWORK_CHECK_CONTENT_LENGTH_FAILED.getErrorCode() +
+                            "|response.errorMsg==" + response.errorMsg
+            );
+            onFail(response);
+        }
+        else {
+            wxErrorCode = WXErrorCode.WX_DEGRAD_ERR_NETWORK_BUNDLE_DOWNLOAD_FAILED.getErrorCode();
+            instance.onRenderError(wxErrorCode,
+                    response.errorMsg);
+            onFail(response);
+        }
+        if (!WXInstanceApm.VALUE_ERROR_CODE_DEFAULT.equals(wxErrorCode)){
+            mApmForInstance.addProperty(WXInstanceApm.KEY_PROPERTIES_ERROR_CODE,wxErrorCode);
+        }
+    }
+
+    private boolean isNet(String requestType){
+
+        return "network".equals(requestType) || "2g".equals(requestType) || "3g".equals(requestType)
+                || "4g".equals(requestType) || "wifi".equals(requestType) || "other".equals(requestType)
+                || "unknown".equals(requestType);
+    }
+
+    public void onSuccess(WXResponse response) {
+        if (flag==WXRenderStrategy.DATA_RENDER_BINARY){
+            instance.render(pageName, response.originalData, options, jsonInitData);
+        }else {
+            String template = new String(response.originalData);
+            instance.render(pageName, template, options, jsonInitData, flag);
+        }
+    }
+
+    public void onFail(WXResponse response) {
+
+    }
+}
+
+
diff --git a/android/sdk/src/main/java/org/apache/weex/WXSDKEngine.java b/android/sdk/src/main/java/org/apache/weex/WXSDKEngine.java
new file mode 100644
index 0000000..ed1cda6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/WXSDKEngine.java
@@ -0,0 +1,601 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex;
+
+import android.app.Application;
+import android.content.Context;
+import android.content.Intent;
+import android.content.res.Resources;
+import android.support.v4.content.LocalBroadcastManager;
+import android.text.TextUtils;
+import org.apache.weex.adapter.IDrawableLoader;
+import org.apache.weex.adapter.IWXHttpAdapter;
+import org.apache.weex.adapter.IWXImgLoaderAdapter;
+import org.apache.weex.adapter.IWXJSExceptionAdapter;
+import org.apache.weex.adapter.IWXJsFileLoaderAdapter;
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.appfram.clipboard.WXClipboardModule;
+import org.apache.weex.appfram.navigator.IActivityNavBarSetter;
+import org.apache.weex.appfram.navigator.INavigator;
+import org.apache.weex.appfram.navigator.WXNavigatorModule;
+import org.apache.weex.appfram.pickers.WXPickersModule;
+import org.apache.weex.appfram.storage.IWXStorageAdapter;
+import org.apache.weex.appfram.storage.WXStorageModule;
+import org.apache.weex.appfram.websocket.WebSocketModule;
+import org.apache.weex.bridge.ModuleFactory;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.bridge.WXModuleManager;
+import org.apache.weex.bridge.WXServiceManager;
+import org.apache.weex.common.Destroyable;
+import org.apache.weex.common.TypeModuleFactory;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXException;
+import org.apache.weex.common.WXInstanceWrap;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.http.WXStreamModule;
+import org.apache.weex.performance.WXStateRecord;
+import org.apache.weex.ui.ExternalLoaderComponentHolder;
+import org.apache.weex.ui.IExternalComponentGetter;
+import org.apache.weex.ui.IExternalModuleGetter;
+import org.apache.weex.ui.IFComponentHolder;
+import org.apache.weex.ui.SimpleComponentHolder;
+import org.apache.weex.ui.WXComponentRegistry;
+import org.apache.weex.ui.animation.WXAnimationModule;
+import org.apache.weex.ui.component.Textarea;
+import org.apache.weex.ui.component.WXA;
+import org.apache.weex.ui.component.WXBasicComponentType;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXDiv;
+import org.apache.weex.ui.component.WXEmbed;
+import org.apache.weex.ui.component.WXHeader;
+import org.apache.weex.ui.component.WXImage;
+import org.apache.weex.ui.component.WXIndicator;
+import org.apache.weex.ui.component.WXInput;
+import org.apache.weex.ui.component.WXLoading;
+import org.apache.weex.ui.component.WXLoadingIndicator;
+import org.apache.weex.ui.component.WXRefresh;
+import org.apache.weex.ui.component.WXScroller;
+import org.apache.weex.ui.component.WXSlider;
+import org.apache.weex.ui.component.WXSliderNeighbor;
+import org.apache.weex.ui.component.WXSwitch;
+import org.apache.weex.ui.component.WXText;
+import org.apache.weex.ui.component.WXVideo;
+import org.apache.weex.ui.component.WXWeb;
+import org.apache.weex.ui.component.list.HorizontalListComponent;
+import org.apache.weex.ui.component.list.SimpleListComponent;
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.ui.component.list.WXListComponent;
+import org.apache.weex.ui.component.list.template.WXRecyclerTemplateList;
+import org.apache.weex.ui.component.richtext.WXRichText;
+import org.apache.weex.ui.config.AutoScanConfigRegister;
+import org.apache.weex.ui.module.WXDeviceInfoModule;
+import org.apache.weex.ui.module.ConsoleLogModule;
+import org.apache.weex.ui.module.WXLocaleModule;
+import org.apache.weex.ui.module.WXMetaModule;
+import org.apache.weex.ui.module.WXModalUIModule;
+import org.apache.weex.ui.module.WXTimerModule;
+import org.apache.weex.ui.module.WXWebViewModule;
+import org.apache.weex.utils.LogLevel;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXSoInstallMgrSdk;
+import org.apache.weex.utils.batch.BatchOperationHelper;
+import org.apache.weex.utils.cache.RegisterCache;
+import java.io.Serializable;
+import java.util.HashMap;
+import java.util.Map;
+
+public class WXSDKEngine implements Serializable {
+
+  public static final String JS_FRAMEWORK_RELOAD="js_framework_reload";
+  private static final String V8_SO_NAME = WXEnvironment.CORE_SO_NAME;
+  private volatile static boolean mIsInit = false;
+  private volatile static boolean mIsSoInit = false;
+  private static final Object mLock = new Object();
+  private static final String TAG = "WXSDKEngine";
+
+  /**
+   * Deprecated. Use {@link #initialize(Application, InitConfig)} instead.
+   */
+  @Deprecated
+  public static void init(Application application) {
+    init(application, null);
+  }
+
+  /**
+   * Deprecated. Use {@link #initialize(Application, InitConfig)} instead.
+   */
+  @Deprecated
+  public static void init(Application application, IWXUserTrackAdapter utAdapter) {
+    init(application, utAdapter, null);
+  }
+
+  /**
+   * Deprecated. Use {@link #initialize(Application, InitConfig)} instead.
+   */
+  @Deprecated
+  public static void init(Application application, IWXUserTrackAdapter utAdapter, String framework) {
+    initialize(application,
+            new InitConfig.Builder()
+                    .setUtAdapter(utAdapter)
+                    .build()
+    );
+  }
+
+
+  public static boolean isInitialized(){
+    synchronized(mLock) {
+
+      return mIsInit && WXEnvironment.JsFrameworkInit;
+    }
+  }
+
+  public static boolean isSoInitialized(){
+    synchronized(mLock) {
+      return mIsSoInit;
+    }
+  }
+
+  /**
+   *
+   * @param application
+   * @param config initial configurations or null
+   */
+  public static void initialize(Application application,InitConfig config){
+    synchronized (mLock) {
+      if (mIsInit) {
+        return;
+      }
+      long start = System.currentTimeMillis();
+      WXEnvironment.sSDKInitStart = start;
+      if(WXEnvironment.isApkDebugable(application)){
+        WXEnvironment.sLogLevel = LogLevel.DEBUG;
+      }else{
+        WXEnvironment.sLogLevel = LogLevel.WARN;
+      }
+      doInitInternal(application,config);
+      registerApplicationOptions(application);
+      WXEnvironment.sSDKInitInvokeTime = System.currentTimeMillis()-start;
+      WXLogUtils.renderPerformanceLog("SDKInitInvokeTime", WXEnvironment.sSDKInitInvokeTime);
+      mIsInit = true;
+    }
+  }
+
+  private static void registerApplicationOptions(final Application application) {
+
+    if (application == null) {
+      WXLogUtils.e(TAG, "RegisterApplicationOptions application is null");
+      return;
+    }
+
+    Resources resources = application.getResources();
+    registerCoreEnv("screen_width_pixels", String.valueOf(resources.getDisplayMetrics().widthPixels));
+    registerCoreEnv("screen_height_pixels", String.valueOf(resources.getDisplayMetrics().heightPixels));
+
+    int resourceId = resources.getIdentifier("status_bar_height", "dimen", "android");
+    if (resourceId > 0) {
+      int statusBarHeight = resources.getDimensionPixelSize(resourceId);
+      registerCoreEnv("status_bar_height", String.valueOf(statusBarHeight));
+    }
+  }
+
+  private static void doInitInternal(final Application application,final InitConfig config){
+    WXEnvironment.sApplication = application;
+    if(application == null){
+      WXLogUtils.e(TAG, " doInitInternal application is null");
+      WXExceptionUtils.commitCriticalExceptionRT(null,
+              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
+              "doInitInternal",
+              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT.getErrorMsg() + "WXEnvironment sApplication is null",
+              null);
+    }
+    WXEnvironment.JsFrameworkInit = false;
+
+    WXBridgeManager.getInstance().postWithName(new Runnable() {
+      @Override
+      public void run() {
+        long start = System.currentTimeMillis();
+        WXSDKManager sm = WXSDKManager.getInstance();
+        sm.onSDKEngineInitialize();
+        if(config != null ) {
+          sm.setInitConfig(config);
+        }
+        WXSoInstallMgrSdk.init(application,
+                sm.getIWXSoLoaderAdapter(),
+                sm.getWXStatisticsListener());
+        final IWXUserTrackAdapter userTrackAdapter= config!=null?config.getUtAdapter():null;
+        final int version = 1;
+        mIsSoInit = WXSoInstallMgrSdk.initSo(V8_SO_NAME, version, userTrackAdapter);
+        WXSoInstallMgrSdk.copyJssRuntimeSo();
+        if(config!=null) {
+          for (String libraryName : config.getNativeLibraryList()) {
+            WXSoInstallMgrSdk.initSo(libraryName, version, userTrackAdapter);
+          }
+        }
+        if (!mIsSoInit) {
+          WXExceptionUtils.commitCriticalExceptionRT(null,
+                  WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
+                  "doInitInternal",
+                  WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT.getErrorMsg() + "isSoInit false",
+                  null);
+          return;
+        }
+        sm.initScriptsFramework(config!=null?config.getFramework():null);
+
+        WXEnvironment.sSDKInitExecuteTime = System.currentTimeMillis() - start;
+        WXLogUtils.renderPerformanceLog("SDKInitExecuteTime", WXEnvironment.sSDKInitExecuteTime);
+      }
+    },null,"doInitWeexSdkInternal");
+    WXStateRecord.getInstance().startJSThreadWatchDog();
+    register();
+  }
+
+  @Deprecated
+  public static void init(Application application, String framework, IWXUserTrackAdapter utAdapter, IWXImgLoaderAdapter imgLoaderAdapter, IWXHttpAdapter httpAdapter) {
+    initialize(application,
+            new InitConfig.Builder()
+                    .setUtAdapter(utAdapter)
+                    .setHttpAdapter(httpAdapter)
+                    .setImgAdapter(imgLoaderAdapter)
+                    .build()
+    );
+  }
+
+  public static void setJSExcetptionAdapter(IWXJSExceptionAdapter excetptionAdapter){
+    WXSDKManager.getInstance().setIWXJSExceptionAdapter(excetptionAdapter);
+  }
+
+  private static void register() {
+    BatchOperationHelper batchHelper = new BatchOperationHelper(WXBridgeManager.getInstance());
+    try {
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXText.class,
+                      new WXText.Creator()
+              ),
+              false,
+              WXBasicComponentType.TEXT
+      );
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXDiv.class,
+                      new WXDiv.Ceator()
+              ),
+              false,
+              WXBasicComponentType.CONTAINER,
+              WXBasicComponentType.DIV,
+              WXBasicComponentType.HEADER,
+              WXBasicComponentType.FOOTER
+      );
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXImage.class,
+                      new WXImage.Creator()
+              ),
+              false,
+              WXBasicComponentType.IMAGE,
+              WXBasicComponentType.IMG
+      );
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXScroller.class,
+                      new WXScroller.Creator()
+              ),
+              false,
+              WXBasicComponentType.SCROLLER
+      );
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXSlider.class,
+                      new WXSlider.Creator()
+              ),
+              true,
+              WXBasicComponentType.SLIDER,
+              WXBasicComponentType.CYCLE_SLIDER
+      );
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXSliderNeighbor.class,
+                      new WXSliderNeighbor.Creator()
+              ),
+              true,
+              WXBasicComponentType.SLIDER_NEIGHBOR
+      );
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXCell.class,
+                      new WXCell.Creator()
+              ),
+              true,
+              WXBasicComponentType.CELL);
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXListComponent.class,
+                      new WXListComponent.Creator()
+              ),
+              true,
+              WXBasicComponentType.LIST,
+              WXBasicComponentType.VLIST,
+              WXBasicComponentType.RECYCLER,
+              WXBasicComponentType.WATERFALL);
+
+      registerComponent(
+              new SimpleComponentHolder(
+                      WXRichText.class,
+                      new WXRichText.Creator()
+              ),
+              false,
+              WXBasicComponentType.RICHTEXT
+      );
+
+      String simpleList = "simplelist";
+      registerComponent(SimpleListComponent.class,false,simpleList);
+      registerComponent(WXRecyclerTemplateList.class, false,WXBasicComponentType.RECYCLE_LIST);
+      registerComponent(HorizontalListComponent.class,false,WXBasicComponentType.HLIST);
+      registerComponent(WXBasicComponentType.CELL_SLOT, WXCell.class, true);
+      registerComponent(WXBasicComponentType.INDICATOR, WXIndicator.class, true);
+      registerComponent(WXBasicComponentType.VIDEO, WXVideo.class, false);
+      registerComponent(WXBasicComponentType.INPUT, WXInput.class, false);
+      registerComponent(WXBasicComponentType.TEXTAREA, Textarea.class,false);
+      registerComponent(WXBasicComponentType.SWITCH, WXSwitch.class, false);
+      registerComponent(WXBasicComponentType.A, WXA.class, false);
+      registerComponent(WXBasicComponentType.EMBED, WXEmbed.class, true);
+      registerComponent(WXBasicComponentType.WEB, WXWeb.class);
+      registerComponent(WXBasicComponentType.REFRESH, WXRefresh.class);
+      registerComponent(WXBasicComponentType.LOADING, WXLoading.class);
+      registerComponent(WXBasicComponentType.LOADING_INDICATOR, WXLoadingIndicator.class);
+      registerComponent(WXBasicComponentType.HEADER, WXHeader.class);
+
+      registerModule("modal", WXModalUIModule.class);
+      registerModule("instanceWrap", WXInstanceWrap.class);
+      registerModule("animation", WXAnimationModule.class);
+      registerModule("webview", WXWebViewModule.class);
+      registerModule("navigator", WXNavigatorModule.class);
+      registerModule("stream", WXStreamModule.class);
+      registerModule("timer", WXTimerModule.class);
+      registerModule("storage", WXStorageModule.class);
+      registerModule("clipboard", WXClipboardModule.class);
+      registerModule("globalEvent",WXGlobalEventModule.class);
+      registerModule("picker", WXPickersModule.class);
+      registerModule("meta", WXMetaModule.class);
+      registerModule("webSocket", WebSocketModule.class);
+      registerModule("locale", WXLocaleModule.class);
+      registerModule("deviceInfo", WXDeviceInfoModule.class);
+      registerModule("sdk-console-log", ConsoleLogModule.class);
+    } catch (WXException e) {
+      WXLogUtils.e("[WXSDKEngine] register:", e);
+    }
+
+    if(RegisterCache.getInstance().enableAutoScan()) {
+      AutoScanConfigRegister.doScanConfig();
+    }
+
+    batchHelper.flush();
+  }
+
+  /**
+   *
+   * Register component. The registration is singleton in {@link WXSDKEngine} level
+   * @param type name of component. Same as type field in the JS.
+   * @param clazz the class of the {@link WXComponent} to be registered.
+   * @param appendTree true for appendTree flag
+   * @return true for registration success, false for otherwise.
+   * @throws WXException Throws exception if type conflicts.
+   */
+  public static boolean registerComponent(String type, Class<? extends WXComponent> clazz, boolean appendTree) throws WXException {
+    return registerComponent(clazz, appendTree,type);
+  }
+
+  public static boolean registerComponent(String type, IExternalComponentGetter componentGetter, boolean appendTree) throws WXException {
+    return registerComponent(new ExternalLoaderComponentHolder(type,componentGetter), appendTree,type);
+  }
+
+  /**
+   *
+   * Register component. The registration is singleton in {@link WXSDKEngine} level
+   * @param clazz the class of the {@link WXComponent} to be registered.
+   * @param appendTree true for appendTree flag
+   * @return true for registration success, false for otherwise.
+   * @param names names(alias) of component. Same as type field in the JS.
+   * @throws WXException Throws exception if type conflicts.
+   */
+  public static boolean registerComponent(Class<? extends WXComponent> clazz, boolean appendTree,String ... names) throws WXException {
+    if(clazz == null){
+      return false;
+    }
+    SimpleComponentHolder holder = new SimpleComponentHolder(clazz);
+    return registerComponent(holder,appendTree,names);
+  }
+
+
+  public static boolean registerComponent(IFComponentHolder holder, boolean appendTree, String ... names) throws WXException {
+    boolean result =  true;
+    try {
+      for (String name : names) {
+        Map<String, Object> componentInfo = new HashMap<>();
+        if (appendTree) {
+          componentInfo.put("append", "tree");
+        }
+        result = result && WXComponentRegistry.registerComponent(name, holder, componentInfo);
+      }
+      return result;
+    } catch (Throwable e) {
+      e.printStackTrace();
+      return result;
+    }
+  }
+
+  /**
+   * Register module. This is a wrapper method for
+   * {@link #registerModule(String, Class, boolean)}. The module register here only need to
+   * be singleton in {@link WXSDKInstance} level.
+   * @param moduleName  module name
+   * @param moduleClass module to be registered.
+   * @return true for registration success, false for otherwise.
+   * {@link WXModuleManager#registerModule(String, ModuleFactory, boolean)}
+   */
+  public static <T extends WXModule> boolean registerModule(String moduleName, Class<T> moduleClass,boolean global) throws WXException {
+    return moduleClass != null && registerModule(moduleName, new TypeModuleFactory<>(moduleClass), global);
+  }
+
+  /**
+   * Register module. This is a wrapper method for
+   * {@link #registerModule(String, Class, boolean)}. The module register here only need to
+   * be singleton in {@link WXSDKInstance} level.
+   * @param moduleName  module name
+   * @param factory module factory to be registered. You can override {@link DestroyableModuleFactory#buildInstance()} to customize module creation.
+   * @return true for registration success, false for otherwise.
+   * {@link WXModuleManager#registerModule(String, ModuleFactory, boolean)}
+   */
+  public static <T extends WXModule> boolean registerModuleWithFactory(String moduleName, DestroyableModuleFactory factory, boolean global) throws WXException {
+    return registerModule(moduleName, factory,global);
+  }
+
+
+  public static <T extends WXModule> boolean registerModuleWithFactory(String moduleName, IExternalModuleGetter factory, boolean global) throws WXException {
+    return registerModule(moduleName, factory.getExternalModuleClass(moduleName,WXEnvironment.getApplication()),global);
+  }
+
+  public static <T extends WXModule> boolean registerModule(String moduleName, ModuleFactory factory, boolean global) throws WXException {
+    return WXModuleManager.registerModule(moduleName, factory,global);
+  }
+
+  public static boolean registerModule(String moduleName, Class<? extends WXModule> moduleClass) throws WXException {
+    return registerModule(moduleName, moduleClass,false);
+  }
+
+  public static boolean registerService(String name, String serviceScript, Map<String, Object> options) {
+    return WXServiceManager.registerService(name, serviceScript, options);
+  }
+
+  public static boolean unRegisterService(String name) {
+    return WXServiceManager.unRegisterService(name);
+  }
+
+  /**
+   * module implement {@link Destroyable}
+   */
+  public static abstract class DestroyableModule extends WXModule implements Destroyable {}
+
+  public static  abstract  class DestroyableModuleFactory<T extends DestroyableModule> extends TypeModuleFactory<T> {
+    public DestroyableModuleFactory(Class<T> clz) {
+      super(clz);
+    }
+  }
+
+  public static void callback(String instanceId, String funcId, Map<String, Object> data) {
+    WXSDKManager.getInstance().callback(instanceId, funcId, data);
+  }
+
+  /**
+   * Model switch, only applicable for developer model
+   * @param debug
+   */
+  public static void restartBridge(boolean debug) {
+    WXEnvironment.sDebugMode = debug;
+    WXSDKManager.getInstance().restartBridge();
+  }
+
+  public static boolean registerComponent(String type, Class<? extends WXComponent> clazz) throws WXException {
+    return WXComponentRegistry.registerComponent(type, new SimpleComponentHolder(clazz),new HashMap<String, Object>());
+  }
+
+  public static boolean registerComponent(Map<String, Object> componentInfo, Class<? extends WXComponent> clazz) throws WXException {
+    if(componentInfo == null){
+      return false;
+    }
+    String type = (String)componentInfo.get("type");
+    if(TextUtils.isEmpty(type)){
+      return false;
+    }
+    return WXComponentRegistry.registerComponent(type,new SimpleComponentHolder(clazz), componentInfo);
+  }
+
+  public static void addCustomOptions(String key, String value) {
+    WXEnvironment.addCustomOptions(key, value);
+  }
+
+  public static IWXUserTrackAdapter getIWXUserTrackAdapter() {
+    return WXSDKManager.getInstance().getIWXUserTrackAdapter();
+  }
+
+  public static IWXImgLoaderAdapter getIWXImgLoaderAdapter() {
+    return WXSDKManager.getInstance().getIWXImgLoaderAdapter();
+  }
+
+  public static IDrawableLoader getDrawableLoader() {
+    return WXSDKManager.getInstance().getDrawableLoader();
+  }
+
+  public static IWXHttpAdapter getIWXHttpAdapter() {
+    return WXSDKManager.getInstance().getIWXHttpAdapter();
+  }
+
+  public static IWXStorageAdapter getIWXStorageAdapter() {
+    return WXSDKManager.getInstance().getIWXStorageAdapter();
+  }
+
+
+  public static IWXJsFileLoaderAdapter getIWXJsFileLoaderAdapter() {
+    return WXSDKManager.getInstance().getIWXJsFileLoaderAdapter();
+  }
+
+  public static IActivityNavBarSetter getActivityNavBarSetter() {
+    return WXSDKManager.getInstance().getActivityNavBarSetter();
+  }
+
+  public static INavigator getNavigator() {
+    return WXSDKManager.getInstance().getNavigator();
+  }
+
+  public static  void setNavigator(INavigator navigator) {
+    WXSDKManager.getInstance().setNavigator(navigator);
+  }
+
+  public static void setActivityNavBarSetter(IActivityNavBarSetter activityNavBarSetter) {
+    WXSDKManager.getInstance().setActivityNavBarSetter(activityNavBarSetter);
+  }
+
+  public static void reload(final Context context,String framework, boolean remoteDebug) {
+    WXEnvironment.sRemoteDebugMode = remoteDebug;
+    WXBridgeManager.getInstance().restart();
+    WXBridgeManager.getInstance().initScriptsFramework(framework);
+
+    WXServiceManager.reload();
+    WXModuleManager.reload();
+    WXComponentRegistry.reload();
+    WXSDKManager.getInstance().postOnUiThread(new Runnable() {
+      @Override
+      public void run() {
+        LocalBroadcastManager.getInstance(context).sendBroadcast(new Intent(JS_FRAMEWORK_RELOAD));
+      }
+    }, 0);
+  }
+  public static void reload(final Context context, boolean remoteDebug) {
+    reload(context,null,remoteDebug);
+  }
+
+  public static void reload() {
+    reload(WXEnvironment.getApplication(), WXEnvironment.sRemoteDebugMode);
+  }
+
+  public static void registerCoreEnv(String key, String value) {
+    WXBridgeManager.getInstance().registerCoreEnv(key, value);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/WXSDKInstance.java b/android/sdk/src/main/java/org/apache/weex/WXSDKInstance.java
new file mode 100644
index 0000000..3779727
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/WXSDKInstance.java
@@ -0,0 +1,2503 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex;
+
+import static org.apache.weex.http.WXHttpUtil.KEY_USER_AGENT;
+
+import android.app.Activity;
+import android.app.AlertDialog;
+import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.graphics.Color;
+import android.graphics.Paint;
+import android.net.Uri;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.support.annotation.WorkerThread;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+import android.util.Log;
+import android.view.Menu;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.ScrollView;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.adapter.IDrawableLoader;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.adapter.IWXHttpAdapter;
+import org.apache.weex.adapter.IWXImgLoaderAdapter;
+import org.apache.weex.adapter.IWXJscProcessManager;
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.appfram.websocket.IWebSocketAdapter;
+import org.apache.weex.bridge.EventResult;
+import org.apache.weex.bridge.NativeInvokeHelper;
+import org.apache.weex.bridge.SimpleJSCallback;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.bridge.WXModuleManager;
+import org.apache.weex.bridge.WXParams;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.Destroyable;
+import org.apache.weex.common.OnWXScrollListener;
+import org.apache.weex.common.RenderTypes;
+import org.apache.weex.common.WXConfig;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.common.WXPerformance;
+import org.apache.weex.common.WXRefreshData;
+import org.apache.weex.common.WXRenderStrategy;
+import org.apache.weex.common.WXRequest;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.http.WXHttpUtil;
+import org.apache.weex.instance.InstanceOnFireEventInterceptor;
+import org.apache.weex.jsEngine.JSContext;
+import org.apache.weex.jsEngine.JSEngine;
+import org.apache.weex.layout.ContentBoxMeasurement;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.performance.WXStateRecord;
+import org.apache.weex.performance.WhiteScreenUtils;
+import org.apache.weex.render.WXAbstractRenderContainer;
+import org.apache.weex.tracing.WXTracing;
+import org.apache.weex.ui.action.GraphicActionAddElement;
+import org.apache.weex.ui.component.NestedContainer;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXEmbed;
+import org.apache.weex.ui.flat.FlatGUIContext;
+import org.apache.weex.ui.view.WXScrollView;
+import org.apache.weex.utils.Trace;
+import org.apache.weex.utils.WXDeviceUtils;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXFileUtils;
+import org.apache.weex.utils.WXJsonUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXReflectionUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import org.apache.weex.utils.cache.RegisterCache;
+import org.apache.weex.utils.tools.LogDetail;
+import org.apache.weex.utils.tools.TimeCalculator;
+import java.io.Serializable;
+import java.lang.ref.WeakReference;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.PriorityQueue;
+import java.util.concurrent.ConcurrentHashMap;
+import org.apache.weex.bridge.WXBridgeManager.BundType;
+
+
+/**
+ * Each instance of WXSDKInstance represents an running weex instance.
+ * It can be a pure weex view, or mixed with native view
+ */
+public class WXSDKInstance implements IWXActivityStateListener,View.OnLayoutChangeListener {
+
+  private static  final  String SOURCE_TEMPLATE_BASE64_MD5 = "templateSourceBase64MD5";
+
+  /**
+   * Devtool protocol
+   */
+  public static String ACTION_DEBUG_INSTANCE_REFRESH = "DEBUG_INSTANCE_REFRESH";
+  public static String ACTION_INSTANCE_RELOAD = "INSTANCE_RELOAD";
+
+  //Performance
+  public boolean mEnd = false;
+  public boolean mHasCreateFinish = false;
+  public static final String BUNDLE_URL = "bundleUrl";
+  private IWXUserTrackAdapter mUserTrackAdapter;
+  private IWXRenderListener mRenderListener;
+  private IWXStatisticsListener mStatisticsListener;
+  /** package **/ Context mContext;
+  private final String mInstanceId;
+  private WXAbstractRenderContainer mRenderContainer;
+  private WXComponent mRootComp;
+  private boolean mRendered;
+  private WXRefreshData mLastRefreshData;
+  private NestedInstanceInterceptor mNestedInstanceInterceptor;
+  private String mBundleUrl = "";
+  public static String requestUrl = "requestUrl";
+  private boolean isDestroy=false;
+  private boolean hasException = false;
+  private boolean isRenderSuccess = false;
+  private boolean createInstanceHeartBeat = false;
+  private Map<String,Serializable> mUserTrackParams;
+  private NativeInvokeHelper mNativeInvokeHelper;
+  private boolean isCommit=false;
+  private WXGlobalEventReceiver mGlobalEventReceiver=null;
+  private boolean trackComponent;
+  private boolean enableLayerType = true;
+  private boolean mNeedValidate = false;
+  private boolean mNeedReLoad = false;
+  private boolean mUseScroller = false;
+  private int mInstanceViewPortWidth = 750;
+  private boolean enableFullScreenHeight = false;
+  private WXInstanceApm mApmForInstance;
+  private @NonNull
+  FlatGUIContext mFlatGUIContext =new FlatGUIContext();
+
+  private Map<String,String> mContainerInfo;
+
+  public boolean isNewFsEnd = false;
+  private List<JSONObject> componentsInfoExceedGPULimit  = new LinkedList<>();
+
+  /**
+   * bundle type
+   */
+  public BundType bundleType;
+  public long mRenderStartNanos;
+  public int mExecJSTraceId = WXTracing.nextId();
+
+  private boolean isViewDisAppear = false;
+
+  /**
+   *for network tracker
+   */
+  public String mwxDims[] = new String [5];
+  public long measureTimes[] = new long [5];
+
+  public WeakReference<String> templateRef;
+  public Map<String,List<String>> responseHeaders = new HashMap<>();
+
+  /**
+   * Render strategy.
+   */
+  private WXRenderStrategy mRenderStrategy = WXRenderStrategy.APPEND_ASYNC;
+
+  private boolean mDisableSkipFrameworkInit = false;
+
+  /**
+   * Render start time
+   */
+  public long mRenderStartTime;
+  /**
+   * Refresh start time
+   */
+  private long mRefreshStartTime;
+  private WXPerformance mWXPerformance;
+  private ScrollView mScrollView;
+  private WXScrollView.WXScrollViewListener mWXScrollViewListener;
+
+  private List<OnWXScrollListener> mWXScrollListeners;
+
+  private List<String> mLayerOverFlowListeners;
+
+  private List<ActionBarHandler> mWXActionbarHandlers;
+
+  private List<OnBackPressedHandler> mWXBackPressedHandlers;
+
+  private List<OnActivityResultHandler> mWXOnActivityResultHandlers;
+
+  private WXSDKInstance mParentInstance;
+
+  private String mRenderType = RenderTypes.RENDER_TYPE_NATIVE;
+
+  private boolean mPageDirty = true;
+  private boolean mFixMultiThreadBug = false;
+
+  public TimeCalculator mTimeCalculator;
+  /**
+   * Default Width And Viewport is 750,
+   * when screen width change, we adjust viewport to adapter screen change
+   * */
+  private boolean mAutoAdjustDeviceWidth = WXEnvironment.AUTO_ADJUST_ENV_DEVICE_WIDTH;
+
+  public  List<JSONObject> getComponentsExceedGPULimit(){return componentsInfoExceedGPULimit;}
+  @RestrictTo(Scope.LIBRARY)
+  public void setComponentsInfoExceedGPULimit(JSONObject component){
+    if(component!= null && !component.isEmpty()){
+      componentsInfoExceedGPULimit.add(component);
+    }
+  }
+
+  public List<String> getLayerOverFlowListeners() {
+    return mLayerOverFlowListeners;
+  }
+
+  public void addLayerOverFlowListener(String ref) {
+    if (mLayerOverFlowListeners == null)
+      mLayerOverFlowListeners = new ArrayList<>();
+    mLayerOverFlowListeners.add(ref);
+  }
+
+  public void removeLayerOverFlowListener(String ref) {
+    if (mLayerOverFlowListeners != null)
+      mLayerOverFlowListeners.remove(ref);
+  }
+
+  /**
+   * whether we are in preRender mode
+   * */
+  private volatile boolean isPreRenderMode;
+
+  private boolean mCurrentGround = false;
+  private ComponentObserver mComponentObserver;
+  private Map<String, GraphicActionAddElement> inactiveAddElementAction = new ArrayMap<>();
+
+  private Map<Long, ContentBoxMeasurement> mContentBoxMeasurements = new ArrayMap<>();
+
+  private List<InstanceOnFireEventInterceptor> mInstanceOnFireEventInterceptorList;
+
+
+  /**
+   * network handler
+   */
+  public interface ImageNetworkHandler {
+    public String fetchLocal(String url);
+  }
+
+  public interface StreamNetworkHandler {
+    public String fetchLocal(String url);
+  }
+
+  public interface CustomFontNetworkHandler {
+    public String fetchLocal(String url);
+  }
+
+  private ImageNetworkHandler mImageNetworkHandler;
+
+  private StreamNetworkHandler mStreamNetworkHandler;
+
+  private CustomFontNetworkHandler mCustomFontNetworkHandler;
+
+  public ImageNetworkHandler getImageNetworkHandler() {
+    return mImageNetworkHandler;
+  }
+
+  public void setImageNetworkHandler(ImageNetworkHandler imageNetworkHandler) {
+    this.mImageNetworkHandler = imageNetworkHandler;
+  }
+
+  public StreamNetworkHandler getStreamNetworkHandler() {
+    return mStreamNetworkHandler;
+  }
+
+  public void setStreamNetworkHandler(StreamNetworkHandler streamNetworkHandler) {
+    this.mStreamNetworkHandler = streamNetworkHandler;
+  }
+
+  public CustomFontNetworkHandler getCustomFontNetworkHandler() {
+    return mCustomFontNetworkHandler;
+  }
+
+  public void setCustomFontNetworkHandler(CustomFontNetworkHandler customFontNetworkHandler) {
+    this.mCustomFontNetworkHandler = customFontNetworkHandler;
+  }
+
+
+  /**
+   *  ActionBar Handler
+   */
+
+  public interface ActionBarHandler {
+    boolean onSupportNavigateUp();
+  }
+
+  public interface OnBackPressedHandler {
+    boolean onBackPressed();
+  }
+
+  public static abstract class OnActivityResultHandler {
+    private String id;
+
+    public OnActivityResultHandler(String id) {
+      this.id = id;
+    }
+
+    public abstract boolean onActivityResult(int requestCode, int resultCode, Intent data, String id);
+
+    public boolean onActivityResult(int requestCode, int resultCode, Intent data) {
+      return onActivityResult(requestCode, resultCode, data, id);
+    }
+  }
+
+  /**
+   * set make weexCore run in single process mode
+   * @param flag true means weexCore run in single process mode or multi process mode
+   */
+  public void setUseSingleProcess(boolean flag) {
+    WXBridgeManager.getInstance().setUseSingleProcess(flag);
+  }
+
+  /**
+   * set open SandBox
+   * @param flag
+   */
+  public void setUseSandBox(boolean flag) {
+    WXBridgeManager.getInstance().setSandBoxContext(flag);
+  }
+
+  public PriorityQueue<WXEmbed> hiddenEmbeds;
+
+  private int maxHiddenEmbedsNum = -1; //max hidden embed num, -1 standard for ulimit
+
+  public int getMaxHiddenEmbedsNum() {
+    return maxHiddenEmbedsNum;
+  }
+
+  public void setMaxHiddenEmbedsNum(int maxHiddenEmbedsNum) {
+    this.maxHiddenEmbedsNum = maxHiddenEmbedsNum;
+  }
+
+  @WorkerThread
+  @RestrictTo(Scope.LIBRARY)
+  public void addInActiveAddElementAction(String ref, GraphicActionAddElement action){
+    inactiveAddElementAction.put(ref, action);
+  }
+
+  @WorkerThread
+  @RestrictTo(Scope.LIBRARY)
+  public void removeInActiveAddElmentAction(String ref){
+    inactiveAddElementAction.remove(ref);
+  }
+
+  @WorkerThread
+  @RestrictTo(Scope.LIBRARY)
+  public GraphicActionAddElement getInActiveAddElementAction(String ref){
+    return inactiveAddElementAction.get(ref);
+  }
+
+  /**
+   * If anchor is created manually(etc. define a layout xml resource ),
+   * be aware do not add it to twice when {@link IWXRenderListener#onViewCreated(WXSDKInstance, View)}.
+   * @param a
+   */
+  public void setRenderContainer(RenderContainer a){
+     setWXAbstractRenderContainer(a);
+  }
+
+  public void setWXAbstractRenderContainer(WXAbstractRenderContainer a){
+    if(a != null) {
+      a.setSDKInstance(this);
+      a.addOnLayoutChangeListener(this);
+    }
+
+    mRenderContainer = a;
+    if (mRenderContainer != null && mRenderContainer.getLayoutParams() != null
+            && mRenderContainer.getLayoutParams().width == ViewGroup.LayoutParams.WRAP_CONTENT) {
+      WXBridgeManager.getInstance().post(new Runnable() {
+        @Override
+        public void run() {
+          WXBridgeManager.getInstance().setRenderContentWrapContentToCore(true, getInstanceId());
+        }
+      });
+    } else {
+      WXBridgeManager.getInstance().post(new Runnable() {
+        @Override
+        public void run() {
+          WXBridgeManager.getInstance().setRenderContentWrapContentToCore(false, getInstanceId());
+        }
+      });
+    }
+  }
+
+  private int mMaxDeepLayer;
+
+  public boolean isTrackComponent() {
+    return trackComponent;
+  }
+
+  public void setTrackComponent(boolean trackComponent) {
+    this.trackComponent = trackComponent;
+  }
+
+  /**
+   * Tell whether it is enabled to change the layerType
+   * {@link android.view.View#setLayerType(int, Paint)}
+   * @return True for enable to change the layerType of component, false otherwise. The default
+   * is True
+   */
+  public boolean isLayerTypeEnabled() {
+    return enableLayerType;
+  }
+
+  /**
+   * Enable the ability of changing layerType. e.g. {@link android.view.View#setLayerType(int, Paint)}
+   * Disable the ability of changing layerType will have tremendous <strong>performance
+   * punishment</strong>.
+   *
+   * <strong>Do not</strong> set this to false unless you know exactly what you are doing.
+   * @param enable True for enable to change the layerType of component, false otherwise. The default
+   * is True
+   */
+  public void enableLayerType(boolean enable) {
+    enableLayerType = enable;
+  }
+
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  public @NonNull
+  FlatGUIContext getFlatUIContext(){
+    return mFlatGUIContext;
+  }
+
+  public boolean isNeedValidate() {
+    return mNeedValidate;
+  }
+
+  public boolean isNeedReLoad() {
+    return mNeedReLoad;
+  }
+
+  public void setNeedLoad(boolean load) {
+    mNeedReLoad = load;
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  public void  setEnableFullScreenHeight(boolean fullScreenHeight){enableFullScreenHeight = fullScreenHeight;}
+
+  @RestrictTo(Scope.LIBRARY)
+  public boolean isFullScreenHeightEnabled(){return enableFullScreenHeight;}
+
+  public boolean isUseScroller() {
+    return mUseScroller;
+  }
+
+  public void setUseScroller(boolean use) {
+    mUseScroller = use;
+  }
+
+  public void setInstanceViewPortWidth(int instanceViewPortWidth) {
+    setInstanceViewPortWidth(instanceViewPortWidth,false);
+
+  }
+  public void setInstanceViewPortWidth(int instanceViewPortWidth,boolean fromMetaModule){
+    this.mInstanceViewPortWidth = instanceViewPortWidth;
+    this.mAutoAdjustDeviceWidth = false;
+    if(!fromMetaModule){
+      WXBridgeManager.getInstance().setViewPortWidth(getInstanceId(), mInstanceViewPortWidth);
+    }
+  }
+  public void resetDeviceDisplayOfPage(){
+    WXBridgeManager.getInstance().setDeviceDisplayOfPage(getInstanceId(), WXViewUtils.getScreenWidth(getContext()), WXViewUtils.getScreenHeight(getContext()));
+  }
+  public void setPageKeepRawCssStyles(){
+    WXBridgeManager.getInstance().setPageArgument(getInstanceId(),"reserveCssStyles","true");
+  }
+  public void reloadPageLayout(){
+    WXBridgeManager.getInstance().reloadPageLayout(getInstanceId());
+  }
+
+  public void setAutoAdjustDeviceWidth(boolean autoAdjustViewPort){
+    this.mAutoAdjustDeviceWidth = autoAdjustViewPort;
+  }
+
+  public boolean isAutoAdjustDeviceWidth(){
+    return mAutoAdjustDeviceWidth;
+  }
+
+  private void setDeviceDisplay(float deviceWith, float deviceHeight, float scale){
+    WXBridgeManager.getInstance().setDeviceDisplay(getInstanceId(), deviceWith, deviceHeight, scale);
+  }
+
+
+
+  public int getInstanceViewPortWidth(){
+    return mInstanceViewPortWidth;
+  }
+
+  public interface OnInstanceVisibleListener{
+    void onAppear();
+    void onDisappear();
+  }
+  private List<OnInstanceVisibleListener> mVisibleListeners = new ArrayList<>();
+
+  public WXSDKInstance(Context context) {
+    mInstanceId = WXSDKManager.getInstance().generateInstanceId();
+    init(context);
+  }
+
+  //for preInit
+  public WXSDKInstance(){
+    mInstanceId = WXSDKManager.getInstance().generateInstanceId();
+    mWXPerformance = new WXPerformance(mInstanceId);
+    mApmForInstance = new WXInstanceApm(mInstanceId);
+    WXSDKManager.getInstance().getAllInstanceMap().put(mInstanceId,this);
+    mTimeCalculator = new TimeCalculator(this);
+    initFixMultiThreadFlag();
+  }
+
+
+  private void initFixMultiThreadFlag() {
+    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
+    if (adapter != null) {
+      String config = adapter.getConfig("android_weex_ext_config", "fixMultiThreadBug", "true");
+      mFixMultiThreadBug = Boolean.parseBoolean(config);
+    }
+  }
+
+  /**
+   * For unittest only.
+   */
+  @RestrictTo(Scope.TESTS)
+  WXSDKInstance(Context context,String id) {
+    mInstanceId = id;
+    init(context);
+  }
+
+  public WXComponent getRootComponent() {
+    return mRootComp;
+  }
+
+  public void setNestedInstanceInterceptor(NestedInstanceInterceptor interceptor){
+    mNestedInstanceInterceptor = interceptor;
+  }
+
+  public final WXSDKInstance createNestedInstance(NestedContainer container){
+    WXSDKInstance sdkInstance = newNestedInstance();
+    if(mNestedInstanceInterceptor != null){
+      mNestedInstanceInterceptor.onCreateNestInstance(sdkInstance,container);
+    }
+    if(sdkInstance != null){
+        sdkInstance.setComponentObserver(this.getComponentObserver());
+    }
+    return sdkInstance;
+  }
+
+  protected WXSDKInstance newNestedInstance() {
+    return new WXSDKInstance(mContext);
+  }
+  public boolean isHasException() {
+    return hasException;
+  }
+
+  public void setHasException(boolean hasException) {
+    this.hasException = hasException;
+  }
+
+  public void createInstanceFuncHeartBeat() {
+    WXLogUtils.d("createInstanceFuncHeartBeat: " + mInstanceId);
+    this.createInstanceHeartBeat = true;
+    getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_END_EXCUTE_BUNDLE);
+  }
+
+  public void addOnInstanceVisibleListener(OnInstanceVisibleListener l){
+    mVisibleListeners.add(l);
+  }
+
+  public void removeOnInstanceVisibleListener(OnInstanceVisibleListener l){
+    mVisibleListeners.remove(l);
+  }
+
+  public void init(Context context) {
+    initFixMultiThreadFlag();
+    RegisterCache.getInstance().idle(true);
+    mContext = context;
+    mContainerInfo = new HashMap<>(4);
+    mNativeInvokeHelper = new NativeInvokeHelper(mInstanceId);
+
+    if (null == mWXPerformance){
+      mWXPerformance = new WXPerformance(mInstanceId);
+    }
+    if (null == mApmForInstance){
+      mApmForInstance = new WXInstanceApm(mInstanceId);
+    }
+
+    mWXPerformance.WXSDKVersion = WXEnvironment.WXSDK_VERSION;
+    mWXPerformance.JSLibInitTime = WXEnvironment.sJSLibInitTime;
+
+    mUserTrackAdapter=WXSDKManager.getInstance().getIWXUserTrackAdapter();
+
+    WXSDKManager.getInstance().getAllInstanceMap().put(mInstanceId,this);
+
+    mContainerInfo.put(WXInstanceApm.KEY_PAGE_PROPERTIES_CONTAINER_NAME, context instanceof Activity
+            ? context.getClass().getSimpleName()
+            :"unKnowContainer"
+    );
+    mContainerInfo.put(WXInstanceApm.KEY_PAGE_PROPERTIES_INSTANCE_TYPE,"page");
+
+    // WXBridgeManager.getInstance().checkJsEngineMultiThread();
+    mDisableSkipFrameworkInit = isDisableSkipFrameworkInDataRender();
+
+    if(mTimeCalculator == null) {
+      mTimeCalculator = new TimeCalculator(this);
+    }
+  }
+
+  /**
+   * Set a Observer for component.
+   * This observer will be called in each component, should not doing
+   * anything will impact render performance.
+   *
+   * @param observer
+   */
+  public void setComponentObserver(ComponentObserver observer){
+    mComponentObserver = observer;
+  }
+
+  public ComponentObserver getComponentObserver(){
+    return mComponentObserver;
+  }
+
+  public NativeInvokeHelper getNativeInvokeHelper() {
+    return mNativeInvokeHelper;
+  }
+
+  @Deprecated
+  public void setBizType(String bizType) {
+    if (!TextUtils.isEmpty(bizType)) {
+      mWXPerformance.bizType = bizType;
+    }
+  }
+
+  public ScrollView getScrollView() {
+    return mScrollView;
+  }
+
+  public void setRootScrollView(ScrollView scrollView) {
+    mScrollView = scrollView;
+    if (mWXScrollViewListener != null && mScrollView instanceof WXScrollView) {
+      ((WXScrollView) mScrollView).addScrollViewListener(mWXScrollViewListener);
+    }
+  }
+
+  @Deprecated
+  public void registerScrollViewListener(WXScrollView.WXScrollViewListener scrollViewListener) {
+    mWXScrollViewListener = scrollViewListener;
+  }
+
+  @Deprecated
+  public WXScrollView.WXScrollViewListener getScrollViewListener() {
+    return mWXScrollViewListener;
+  }
+
+  @Deprecated
+  public void setIWXUserTrackAdapter(IWXUserTrackAdapter adapter) {
+  }
+
+  public void setContainerInfo(String key,String val){
+    mContainerInfo.put(key,val);
+  }
+
+  public Map<String, String> getContainerInfo() {
+    return mContainerInfo;
+  }
+
+  /**
+   * Render template asynchronously, use {@link WXRenderStrategy#APPEND_ASYNC} as render strategy
+   * @param template bundle js
+   * @param options  os   iphone/android/ipad
+   *                 weexversion    Weex version(like 1.0.0)
+   *                 appversion     App version(like 1.0.0)
+   *                 devid        Device id(like Aqh9z8dRJNBhmS9drLG5BKCmXhecHUXIZoXOctKwFebH)
+   *                 sysversion    Device system version(like 5.4.4、7.0.4, should be used with os)
+   *                 sysmodel     Device model(like iOS:"MGA82J/A", android:"MI NOTE LTE")
+   *                 Time    UNIX timestamp, UTC+08:00
+   *                 TTID(Optional)
+   *                 MarkertId
+   *                 Appname(Optional)  tm,tb,qa
+   *                 Bundleurl(Optional)  template url
+   * @param jsonInitData Initial data for rendering
+   */
+  public void render(String template, Map<String, Object> options, String jsonInitData) {
+    render(template, options, jsonInitData, WXRenderStrategy.APPEND_ASYNC);
+  }
+
+  /**
+   * Render template asynchronously
+   * @param template bundle js
+   * @param options  os   iphone/android/ipad
+   *                 weexversion    Weex version(like 1.0.0)
+   *                 appversion     App version(like 1.0.0)
+   *                 devid        Device id(like Aqh9z8dRJNBhmS9drLG5BKCmXhecHUXIZoXOctKwFebH)
+   *                 sysversion    Device system version(like 5.4.4、7.0.4, should be used with os)
+   *                 sysmodel     Device model(like iOS:"MGA82J/A", android:"MI NOTE LTE")
+   *                 Time    UNIX timestamp, UTC+08:00
+   *                 TTID(Optional)
+   *                 MarkertId
+   *                 Appname(Optional)  tm,tb,qa
+   *                 Bundleurl(Optional)  template url
+   * @param jsonInitData Initial data for rendering
+   * @param flag     RenderStrategy {@link WXRenderStrategy}
+   */
+  @Deprecated
+  public void render(String template, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag) {
+    render(WXPerformance.DEFAULT, template, options, jsonInitData, flag);
+  }
+
+  /**
+   * Render template asynchronously
+   *
+   * @param pageName, used for performance log.
+   * @param template bundle js
+   * @param options  os   iphone/android/ipad
+   *                 weexversion    Weex version(like 1.0.0)
+   *                 appversion     App version(like 1.0.0)
+   *                 devid        Device id(like Aqh9z8dRJNBhmS9drLG5BKCmXhecHUXIZoXOctKwFebH)
+   *                 sysversion    Device system version(like 5.4.4、7.0.4, should be used with os)
+   *                 sysmodel     Device model(like iOS:"MGA82J/A", android:"MI NOTE LTE")
+   *                 Time    UNIX timestamp, UTC+08:00
+   *                 TTID(Optional)
+   *                 MarkertId
+   *                 Appname(Optional)  tm,tb,qa
+   *                 Bundleurl(Optional)  template url
+   * @param jsonInitData Initial data for rendering
+   * @param flag     RenderStrategy {@link WXRenderStrategy}
+   */
+  public void render(String pageName, String template, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag) {
+    render(pageName, new Script(template), options, jsonInitData, flag);
+  }
+
+  public void render(String pageName, Script template, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag) {
+    mWXPerformance.beforeInstanceRender(mInstanceId);
+
+    if(WXEnvironment.isApkDebugable() && WXPerformance.DEFAULT.equals(pageName)){
+
+      if (getUIContext() != null) {
+        new AlertDialog.Builder(getUIContext())
+                .setTitle("Error: Missing pageName")
+                .setMessage("We highly recommend you to set pageName. Call" +
+                        "\nWXSDKInstance#render(String pageName, String template, Map<String, Object> options, String jsonInitData, WXRenderStrategy flag)\n" +
+                        "to fix it.")
+                .show();
+      }
+
+      return;
+    }
+    renderInternal(pageName,template,options,jsonInitData,flag);
+  }
+
+  /**
+   * Render binary template asynchronously in DATA_RENDER_BINARY strategy.
+   */
+  public void render(String pageName, byte[] template, Map<String, Object> options, String jsonInitData) {
+    render(pageName, new Script(template), options, jsonInitData, WXRenderStrategy.DATA_RENDER_BINARY);
+  }
+
+  private void ensureRenderArchor(){
+    if(mRenderContainer == null){
+      if (getContext() != null) {
+        setRenderContainer(new RenderContainer(getContext()));
+        mRenderContainer.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT));
+        mRenderContainer.setBackgroundColor(Color.TRANSPARENT);
+        mRenderContainer.setSDKInstance(this);
+        mRenderContainer.addOnLayoutChangeListener(this);
+      }
+    }
+  }
+
+  private void renderInternal(String pageName,
+                              String template,
+                              Map<String, Object> options,
+                              String jsonInitData,
+                              WXRenderStrategy flag) {
+    if (mRendered || TextUtils.isEmpty(template)) {
+      return;
+    }
+    renderInternal(pageName, new Script(template), options, jsonInitData, flag);
+  }
+
+  private boolean isPreInit = false;
+  public boolean isPreInitMode(){
+    return isPreInit;
+  }
+
+  private boolean isPreDownLoad =false;
+  public boolean isPreDownLoad(){
+    return isPreDownLoad;
+  }
+
+  public void onInstanceReady(){
+    WXLogUtils.d("test->","onInstanceReady");
+    mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_CONTAINER_READY);
+    if (!isPreInit && !isPreDownLoad){
+      return;
+    }
+    mApmForInstance.onInstanceReady(isPreDownLoad);
+    if (isPreDownLoad){
+        mHttpListener.onInstanceReady();
+    }
+  }
+
+  public void preInit(String pageName,
+                      String script,
+                      Map<String, Object> options,
+                      String jsonInitData,
+                      WXRenderStrategy flag){
+    isPreInit = true;
+    mRenderStrategy = flag;
+    Map<String, Object> renderOptions = options;
+    if (renderOptions == null) {
+      renderOptions = new HashMap<>();
+    }
+    //mApmForInstance.doInit();
+    mApmForInstance.isReady = false;
+    WXSDKManager.getInstance().createInstance(this, new Script(script), renderOptions, jsonInitData);
+  }
+
+  public void preDownLoad(String url,
+                          Map<String, Object> options,
+                          String jsonInitData,
+                          WXRenderStrategy flag){
+    this.isPreDownLoad =true;
+    mRenderStrategy = flag;
+    mApmForInstance.isReady = false;
+    renderByUrl(url,url,options,jsonInitData,flag);
+  }
+
+
+  private void renderInternal(String pageName,
+                              Script template,
+                              Map<String, Object> options,
+                              String jsonInitData,
+                              WXRenderStrategy flag){
+    if (mRendered || template == null || template.isEmpty()) {
+      return;
+    }
+
+    LogDetail logDetail = mTimeCalculator.createLogDetail("renderInternal");
+    mRenderStrategy = flag;
+
+    //some case ,from render(template),but not render (url)
+    if (!mApmForInstance.hasInit()){
+      mApmForInstance.doInit();
+    }
+    mApmForInstance.setPageName(pageName);
+    mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_RENDER_ORGIGIN);
+    mApmForInstance.doDelayCollectData();
+
+    mWXPerformance.pageName = (TextUtils.isEmpty(pageName) ? "defaultBundleUrl":pageName);
+    if (TextUtils.isEmpty(mBundleUrl)) {
+      mBundleUrl = mWXPerformance.pageName;
+    }
+
+    if (WXTracing.isAvailable()) {
+      WXTracing.TraceEvent traceEvent = WXTracing.newEvent("executeBundleJS", mInstanceId, -1);
+      traceEvent.traceId = mExecJSTraceId;
+      traceEvent.iid = mInstanceId;
+      traceEvent.tname = "JSThread";
+      traceEvent.ph = "B";
+      traceEvent.submit();
+      mRenderStartNanos = System.nanoTime();
+    }
+
+    ensureRenderArchor();
+
+    Map<String, Object> renderOptions = options;
+    if (renderOptions == null) {
+      renderOptions = new HashMap<>();
+    }
+
+    if (WXEnvironment.sDynamicMode && !TextUtils.isEmpty(WXEnvironment.sDynamicUrl) && renderOptions.get("dynamicMode") == null) {
+      renderOptions.put("dynamicMode", "true");
+      renderByUrl(pageName, WXEnvironment.sDynamicUrl, renderOptions, jsonInitData, flag);
+      return;
+    }
+
+    TimeCalculator timeCalculator = new TimeCalculator(this);
+
+    mWXPerformance.JSTemplateSize = template.length() / 1024f;
+    mApmForInstance.addStats(WXInstanceApm.KEY_PAGE_STATS_BUNDLE_SIZE,mWXPerformance.JSTemplateSize);
+    mRenderStartTime = System.currentTimeMillis();
+    WXSDKManager.getInstance().setCrashInfo(WXEnvironment.WEEX_CURRENT_KEY,pageName);
+    if(mAutoAdjustDeviceWidth && WXDeviceUtils.isAutoResize(mContext)){
+         if(WXEnvironment.AUTO_UPDATE_APPLICATION_SCREEN_SIZE) {
+             WXViewUtils.updateApplicationScreen(mContext);
+         }
+         WXParams params = WXBridgeManager.getInstance().getInitParams();
+         if(params != null && !TextUtils.equals(params.getDeviceWidth(), String.valueOf(WXViewUtils.getScreenWidth(mContext)))){
+           params.setDeviceWidth(String.valueOf(WXViewUtils.getScreenWidth(mContext)));
+           params.setDeviceHeight(String.valueOf(WXViewUtils.getScreenHeight(mContext)));
+           float density = WXEnvironment.sApplication.getResources().getDisplayMetrics().density;
+           WXEnvironment.addCustomOptions(WXConfig.scale, Float.toString(density));
+           String statusBarHeight =  null;
+           if(WXViewUtils.getStatusBarHeight(mContext) > 0 ){
+             statusBarHeight = String.valueOf(WXViewUtils.getStatusBarHeight(mContext));
+           }
+           WXBridgeManager.getInstance().updateInitDeviceParams(params.getDeviceWidth(),
+                                                                params.getDeviceHeight(),
+                                                                Float.toString(density), statusBarHeight);
+           setDeviceDisplay(WXViewUtils.getScreenWidth(mContext),
+                            WXViewUtils.getScreenHeight(mContext),
+                            WXViewUtils.getScreenDensity(mContext));
+         }
+    }
+    logDetail.taskStart();
+    if (isPreInitMode()){
+      getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_START);
+      WXBridgeManager.getInstance().loadJsBundleInPreInitMode(getInstanceId(),template.getContent());
+    } else {
+      WXSDKManager.getInstance().createInstance(this, template, renderOptions, jsonInitData);
+    }
+    logDetail.taskEnd();
+    mRendered = true;
+
+    final IWXJscProcessManager wxJscProcessManager = WXSDKManager.getInstance().getWXJscProcessManager();
+
+    if(wxJscProcessManager != null && wxJscProcessManager.shouldReboot()) {
+      WXSDKManager.getInstance().postOnUiThread(new Runnable() {
+        @Override
+        public void run() {
+          checkWhiteScreen();
+          if(isDestroy || hasException || isRenderSuccess) {
+            return;
+          }
+
+          // there is no need to reboot js engine if render by eagle
+          if(isDataRender()) {
+            return;
+          }
+
+          View containerView = getContainerView();
+          if(containerView instanceof ViewGroup) {
+            if(0 == ((ViewGroup) containerView).getChildCount()) {
+              if(wxJscProcessManager.withException(WXSDKInstance.this)) {
+                onJSException(String.valueOf(WXErrorCode.WX_ERR_RELOAD_PAGE),"jsc reboot","jsc reboot");
+              }
+              if(!createInstanceHeartBeat) {
+                  WXBridgeManager.getInstance().callReportCrashReloadPage(mInstanceId, null);
+                  WXLogUtils.e("callReportCrashReloadPage with jsc reboot");
+              }
+            }
+          }
+        }
+      }, wxJscProcessManager.rebootTimeout());
+    }
+  }
+
+
+  private void checkWhiteScreen(){
+    if (isDestroy ||!WhiteScreenUtils.doWhiteScreenCheck()){
+      return;
+    }
+
+    boolean isWS = WhiteScreenUtils.isWhiteScreen(this);
+    if (!isWS){
+      return;
+    }
+    WXErrorCode errorCode = createInstanceHeartBeat?WXErrorCode.WX_ERROR_WHITE_SCREEN:WXErrorCode.WHITE_SCREEN_RESPONSE_TIMEOUT;
+    if (WXBridgeManager.getInstance().isRebootExceedLimit()){
+      errorCode = WXErrorCode.WHITE_SCREEN_REBOOT_EXCEED_LIMIT;
+    }
+    Map<String,String> args = new HashMap<>(1);
+    String vieTreeMsg = WhiteScreenUtils.takeViewTreeSnapShot(this);
+    args.put("viewTree",null == vieTreeMsg?"null viewTreeMsg":vieTreeMsg);
+    args.put("weexCoreThreadStackTrace",WXBridgeManager.getInstance().getWeexCoreThreadStackTrace());
+
+    for (Map.Entry<String,String> entry: WXStateRecord.getInstance().getStateInfo().entrySet()){
+      args.put(entry.getKey(),entry.getValue());
+    }
+    WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),errorCode,"checkEmptyScreen",errorCode.getErrorMsg(),args);
+  }
+
+
+  public boolean skipFrameworkInit(){
+    return isDataRender() && !mDisableSkipFrameworkInit;
+  }
+
+  private boolean isDataRender() {
+    return getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY || getRenderStrategy() == WXRenderStrategy.DATA_RENDER;
+  }
+
+  private void renderByUrlInternal(String pageName,
+                                   final String url,
+                                   Map<String, Object> options,
+                                   final String jsonInitData,
+                                   WXRenderStrategy flag) {
+
+
+    LogDetail logDetail = mTimeCalculator.createLogDetail("renderByUrlInternal");
+    logDetail.taskStart();
+    ensureRenderArchor();
+    pageName = wrapPageName(pageName, url);
+    mBundleUrl = url;
+    mRenderStrategy = flag;
+    if(WXSDKManager.getInstance().getValidateProcessor()!=null) {
+      mNeedValidate = WXSDKManager.getInstance().getValidateProcessor().needValidate(mBundleUrl);
+    }
+
+    Map<String, Object> renderOptions = options;
+    if (renderOptions == null) {
+      renderOptions = new HashMap<>();
+    }
+    if (!renderOptions.containsKey(BUNDLE_URL)) {
+      renderOptions.put(BUNDLE_URL, url);
+    }
+
+    getWXPerformance().pageName = pageName;
+
+    mApmForInstance.doInit();
+    mApmForInstance.setPageName(pageName);
+
+    Uri uri = Uri.parse(url);
+    if (uri != null && TextUtils.equals(uri.getScheme(), "file")) {
+      mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_START);
+      String template = WXFileUtils.loadFileOrAsset(assembleFilePath(uri), mContext);
+      mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_END);
+      render(pageName,template , renderOptions, jsonInitData, flag);
+      return;
+    }
+
+    boolean is_wlasm = false;
+    if (uri != null && uri.getPath()!=null) {
+      if(uri.getPath().endsWith(".wlasm")){
+        is_wlasm =  true;
+      }
+    }
+    if (is_wlasm){
+      flag = WXRenderStrategy.DATA_RENDER_BINARY;
+    }
+
+    IWXHttpAdapter adapter = WXSDKManager.getInstance().getIWXHttpAdapter();
+
+    WXRequest wxRequest = new WXRequest();
+    wxRequest.url = rewriteUri(Uri.parse(url), URIAdapter.BUNDLE).toString();
+    if(wxRequest != null && !TextUtils.isEmpty(wxRequest.url)){
+      requestUrl = wxRequest.url;
+    }else {
+      requestUrl = pageName;
+    }
+
+    if (wxRequest.paramMap == null) {
+      wxRequest.paramMap = new HashMap<String, String>();
+    }
+    wxRequest.instanceId = getInstanceId();
+    wxRequest.paramMap.put(KEY_USER_AGENT, WXHttpUtil.assembleUserAgent(mContext,WXEnvironment.getConfig()));
+    wxRequest.paramMap.put("isBundleRequest","true");
+    mHttpListener = new WXHttpListener(this, pageName, renderOptions, jsonInitData, flag, System.currentTimeMillis());
+    mHttpListener.isPreDownLoadMode = isPreDownLoad;
+    mHttpListener.setSDKInstance(this);
+    mApmForInstance.onStage(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_START);
+    adapter.sendRequest(wxRequest, (IWXHttpAdapter.OnHttpListener) mHttpListener);
+    logDetail.taskEnd();
+  }
+
+  private WXHttpListener mHttpListener = null;
+
+  /**
+   * Use {@link #render(String, String, Map, String, WXRenderStrategy)} instead.
+   * @param pageName
+   * @param template
+   * @param options
+   * @param jsonInitData
+   * @param width
+   * @param height
+   * @param flag
+   */
+  @Deprecated
+  public void render(String pageName, String template, Map<String, Object> options, String jsonInitData, int width, int height, WXRenderStrategy flag) {
+    render(pageName,template,options,jsonInitData,flag);
+  }
+
+  /**
+   * Render template asynchronously, use {@link WXRenderStrategy#APPEND_ASYNC} as render strategy
+   * @param template bundle js
+   */
+  public void render(String template) {
+    render(WXPerformance.DEFAULT, template, null, null, mRenderStrategy);
+  }
+
+  /**
+   * Use {@link #render(String)} instead.
+   * @param template
+   * @param width
+   * @param height
+   */
+  @Deprecated
+  public void render(String template, int width, int height) {
+    render(template);
+  }
+
+  /**
+   * Use {@link #renderByUrl(String, String, Map, String, WXRenderStrategy)} instead.
+   * @param pageName
+   * @param url
+   * @param options
+   * @param jsonInitData
+   * @param width
+   * @param height
+   * @param flag
+   */
+  @Deprecated
+  public void renderByUrl(String pageName, final String url, Map<String, Object> options, final String jsonInitData, final int width, final int height, final WXRenderStrategy flag){
+    renderByUrl(pageName,url,options,jsonInitData,flag);
+  }
+
+  public void renderByUrl(String pageName, final String url, Map<String, Object> options, final String jsonInitData, final WXRenderStrategy flag) {
+    renderByUrlInternal(pageName,url,options,jsonInitData,flag);
+  }
+
+  private String wrapPageName(String pageName, String url) {
+    if(TextUtils.equals(pageName, WXPerformance.DEFAULT)){
+      pageName = url;
+      WXExceptionUtils.degradeUrl = pageName;
+      try {
+        Uri uri=Uri.parse(url);
+        if(uri!=null){
+          Uri.Builder builder=new Uri.Builder();
+          builder.scheme(uri.getScheme());
+          builder.authority(uri.getAuthority());
+          builder.path(uri.getPath());
+          pageName=builder.toString();
+        }
+      } catch (Exception e) {
+      }
+    }
+    return pageName;
+  }
+
+  private String assembleFilePath(Uri uri) {
+    if(uri!=null && uri.getPath()!=null){
+      return uri.getPath().replaceFirst("/","");
+    }
+    return "";
+  }
+
+  public void reloadPage(boolean reloadThis) {
+
+    WXSDKEngine.reload();
+
+    if (reloadThis) {
+      if (mContext != null)  {
+        Intent intent = new Intent();
+        intent.setAction(ACTION_INSTANCE_RELOAD);
+        intent.putExtra("url", mBundleUrl);
+        mContext.sendBroadcast(intent);
+      }
+      // mRendered = false;
+      //    destroy();
+      // renderInternal(mPackage, mTemplate, mOptions, mJsonInitData, mFlag);
+      // refreshInstance("{}");
+    } else {
+      IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
+      if (adapter != null) {
+        boolean degrade = Boolean.parseBoolean(adapter
+                .getConfig("android_weex_ext_config",
+                        "degrade_to_h5_if_not_reload",
+                        "true"));
+        WXLogUtils.e("degrade : " + degrade);
+        if(degrade) {
+          onJSException(String.valueOf(WXErrorCode.WX_ERR_RELOAD_PAGE.getErrorCode()),"Do not reloadPage", "Do not reloadPage degradeToH5");
+          WXLogUtils.e("Do not reloadPage degradeToH5");
+        }
+      }
+    }
+  }
+
+  /**
+   * Refresh instance asynchronously.
+   * @param data the new data
+   */
+  public void refreshInstance(Map<String, Object> data) {
+    if (data == null) {
+      return;
+    }
+    refreshInstance(WXJsonUtils.fromObjectToJSONString(data));
+  }
+
+  /**
+   * Refresh instance asynchronously.
+   * @param jsonData the new data
+   */
+  public void refreshInstance(String jsonData) {
+    if (jsonData == null) {
+      return;
+    }
+    mRefreshStartTime = System.currentTimeMillis();
+    //cancel last refresh message
+    if (mLastRefreshData != null) {
+      mLastRefreshData.isDirty = true;
+    }
+
+    mLastRefreshData = new WXRefreshData(jsonData, false);
+
+    WXSDKManager.getInstance().refreshInstance(mInstanceId, mLastRefreshData);
+  }
+
+  public WXRenderStrategy getRenderStrategy() {
+    return mRenderStrategy;
+  }
+
+  public Context getUIContext() {
+    return mContext;
+  }
+
+  public String getInstanceId() {
+    return mInstanceId;
+  }
+
+  public Context getContext() {
+    return mContext;
+  }
+
+  public int getWeexHeight() {
+    return mRenderContainer == null ? 0: mRenderContainer.getHeight();
+  }
+
+  public int getWeexWidth() {
+    return mRenderContainer == null ? 0: mRenderContainer.getWidth();
+  }
+
+
+  public IWXImgLoaderAdapter getImgLoaderAdapter() {
+    return WXSDKManager.getInstance().getIWXImgLoaderAdapter();
+  }
+
+  public IDrawableLoader getDrawableLoader() {
+    return WXSDKManager.getInstance().getDrawableLoader();
+  }
+
+  public URIAdapter getURIAdapter(){
+    return WXSDKManager.getInstance().getURIAdapter();
+  }
+
+  public Uri rewriteUri(Uri uri,String type){
+    return getURIAdapter().rewrite(this,type,uri);
+  }
+
+  public IWXHttpAdapter getWXHttpAdapter() {
+    return WXSDKManager.getInstance().getIWXHttpAdapter();
+  }
+
+  public IWXStatisticsListener getWXStatisticsListener() {
+    return mStatisticsListener;
+  }
+
+  public @Nullable
+  IWebSocketAdapter getWXWebSocketAdapter() {
+    return WXSDKManager.getInstance().getIWXWebSocketAdapter();
+  }
+
+  @Deprecated
+  public void reloadImages() {
+    if (mScrollView == null) {
+      return;
+    }
+  }
+
+
+  public boolean isPreRenderMode() {
+    return this.isPreRenderMode;
+  }
+
+  public void setPreRenderMode(final boolean isPreRenderMode) {
+    WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(new Runnable() {
+      @Override
+      public void run() {
+        WXSDKInstance.this.isPreRenderMode = isPreRenderMode;
+      }
+    },0);
+  }
+
+  public void setContext(@NonNull Context context) {
+    this.mContext = context;
+  }
+
+  /********************************
+   * begin register listener
+   ********************************************************/
+  public void registerRenderListener(IWXRenderListener listener) {
+    mRenderListener = listener;
+  }
+
+  @Deprecated
+  public void registerActivityStateListener(IWXActivityStateListener listener) {
+
+  }
+
+  public void registerStatisticsListener(IWXStatisticsListener listener) {
+    mStatisticsListener = listener;
+  }
+
+  /**set render start time*/
+  public void setRenderStartTime(long renderStartTime) {
+    this.mRenderStartTime = renderStartTime;
+  }
+
+  /********************************
+   * end register listener
+   ********************************************************/
+
+
+  /********************************
+   *  begin hook Activity life cycle callback
+   ********************************************************/
+
+  @Override
+  public void onActivityCreate() {
+
+    // module listen Activity onActivityCreate
+    WXModuleManager.onActivityCreate(getInstanceId());
+
+    if(mRootComp != null) {
+      mRootComp.onActivityCreate();
+    }else{
+        if (WXEnvironment.isApkDebugable()){
+            WXLogUtils.w("Warning :Component tree has not build completely,onActivityCreate can not be call!");
+        }
+    }
+
+    mGlobalEventReceiver=new WXGlobalEventReceiver(this);
+    try {
+      getContext().registerReceiver(mGlobalEventReceiver, new IntentFilter(WXGlobalEventReceiver.EVENT_ACTION));
+    } catch (Throwable e) {
+      // Huawei may throw a exception if register more than 500 BroadcastReceivers
+      WXLogUtils.e(e.getMessage());
+      mGlobalEventReceiver = null;
+    }
+
+  }
+
+  @Override
+  public void onActivityStart() {
+
+    // module listen Activity onActivityCreate
+    WXModuleManager.onActivityStart(getInstanceId());
+    if(mRootComp != null) {
+      mRootComp.onActivityStart();
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("Warning :Component tree has not build completely,onActivityStart can not be call!");
+
+        }
+    }
+
+  }
+
+  public boolean onCreateOptionsMenu(Menu menu) {
+
+    WXModuleManager.onCreateOptionsMenu(getInstanceId(),menu);
+    if(mRootComp != null) {
+      mRootComp.onCreateOptionsMenu(menu);
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("Warning :Component tree has not build completely,onActivityStart can not be call!");
+
+        }
+    }
+    return true;
+  }
+
+  @Override
+  public void onActivityPause() {
+    onViewDisappear();
+    if(!isCommit){
+      if(mUseScroller){
+        mWXPerformance.useScroller=1;
+      }
+      mWXPerformance.maxDeepViewLayer=getMaxDeepLayer();
+      mWXPerformance.wxDims = mwxDims;
+      mWXPerformance.measureTimes = measureTimes;
+      if (mUserTrackAdapter != null) {
+        mUserTrackAdapter.commit(mContext, null, IWXUserTrackAdapter.LOAD, mWXPerformance, getUserTrackParams());
+      }
+      isCommit=true;
+    }
+    // module listen Activity onActivityPause
+    WXModuleManager.onActivityPause(getInstanceId());
+    if(mRootComp != null) {
+      mRootComp.onActivityPause();
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("Warning :Component tree has not build completely,onActivityPause can not be call!");
+        }
+    }
+
+    if (!mCurrentGround) {
+      WXLogUtils.i("Application to be in the backround");
+      Intent intent = new Intent(WXGlobalEventReceiver.EVENT_ACTION);
+      intent.putExtra(WXGlobalEventReceiver.EVENT_NAME, Constants.Event.PAUSE_EVENT);
+      intent.putExtra(WXGlobalEventReceiver.EVENT_WX_INSTANCEID, getInstanceId());
+      /**
+       *  Fix NPE just like {@link #onActivityResume()}
+       */
+      if (null != mContext){
+        mContext.sendBroadcast(intent);
+      }else {
+        try {
+          WXEnvironment.getApplication().sendBroadcast(intent);
+        } catch (Exception e){
+          WXLogUtils.e("weex",e);
+        }
+      }
+      this.mCurrentGround = true;
+    }
+
+    //component appear
+    if((WXEnvironment.isApkDebugable() || WXEnvironment.isPerf()) && mApmForInstance != null){
+        WXLogUtils.e("PerformanceData " + mApmForInstance.toPerfString());
+    }
+  }
+
+
+  @Override
+  public void onActivityResume() {
+
+    // notify onActivityResume callback to module
+    WXModuleManager.onActivityResume(getInstanceId());
+
+    if(mRootComp != null) {
+      mRootComp.onActivityResume();
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("Warning :Component tree has not build completely, onActivityResume can not be call!");
+        }
+    }
+
+    if (mCurrentGround) {
+      WXLogUtils.i("Application  to be in the foreground");
+      Intent intent = new Intent(WXGlobalEventReceiver.EVENT_ACTION);
+      intent.putExtra(WXGlobalEventReceiver.EVENT_NAME, Constants.Event.RESUME_EVENT);
+      intent.putExtra(WXGlobalEventReceiver.EVENT_WX_INSTANCEID, getInstanceId());
+      //todo tmp solution for gray version
+      if (null != mContext){
+        mContext.sendBroadcast(intent);
+      }else {
+        WXEnvironment.getApplication().sendBroadcast(intent);
+      }
+      this.mCurrentGround = false;
+    }
+
+    onViewAppear();
+  }
+
+  @Override
+  public void onActivityStop() {
+
+    // notify onActivityResume callback to module
+    WXModuleManager.onActivityStop(getInstanceId());
+
+    if(mRootComp != null) {
+      mRootComp.onActivityStop();
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("Warning :Component tree has not build completely, onActivityStop can not be call!");
+        }
+    }
+
+  }
+
+  @Override
+  public void onActivityDestroy() {
+    WXModuleManager.onActivityDestroy(getInstanceId());
+
+    if(mRootComp != null) {
+      mRootComp.onActivityDestroy();
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("Warning :Component tree has not build completely, onActivityDestroy can not be call!");
+        }
+    }
+    this.mTimeCalculator.println();
+    destroy();
+  }
+
+  @Override
+  public boolean onActivityBack() {
+
+    WXModuleManager.onActivityBack(getInstanceId());
+
+    if(mRootComp != null) {
+      return mRootComp.onActivityBack();
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("Warning :Component tree has not build completely, onActivityBack can not be call!");
+        }
+    }
+
+    return false;
+  }
+
+  public boolean onSupportNavigateUp() {
+    if (mWXActionbarHandlers != null) {
+      for (ActionBarHandler handler : mWXActionbarHandlers) {
+        if (handler.onSupportNavigateUp()) {
+          return true;
+        }
+      }
+    }
+    return false;
+  }
+
+  public boolean onBackPressed() {
+    if(mWXBackPressedHandlers != null) {
+      for (OnBackPressedHandler handler : mWXBackPressedHandlers) {
+        if(handler.onBackPressed()) {
+          return true;
+        }
+      }
+    }
+
+    WXComponent comp = getRootComponent();
+    if(comp != null) {
+      WXEvent events= comp.getEvents();
+      boolean hasNativeBackHook = events.contains(Constants.Event.NATIVE_BACK);
+      if (hasNativeBackHook) {
+        EventResult result = comp.fireEventWait(Constants.Event.NATIVE_BACK, null);
+        if (WXUtils.getBoolean(result.getResult(), false)) {
+          return true;
+        }
+      }
+
+      boolean hasBackPressed = events.contains(Constants.Event.CLICKBACKITEM);
+      if (hasBackPressed) {
+        fireEvent(comp.getRef(), Constants.Event.CLICKBACKITEM,null, null);
+      }
+      return hasBackPressed;
+    }
+    return false;
+  }
+
+  public void onActivityResult(int requestCode, int resultCode, Intent data){
+    WXModuleManager.onActivityResult(getInstanceId(),requestCode,resultCode,data);
+
+    if(mRootComp != null) {
+      mRootComp.onActivityResult(requestCode,resultCode,data);
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("Warning :Component tree has not build completely, onActivityResult can not be call!");
+        }
+    }
+
+
+    if (mWXOnActivityResultHandlers != null && !mWXOnActivityResultHandlers.isEmpty()) {
+      for (OnActivityResultHandler onActivityResultHandler : mWXOnActivityResultHandlers) {
+        if (onActivityResultHandler.onActivityResult(requestCode, resultCode, data)) {
+          break;
+        }
+      }
+    }
+
+  }
+
+
+  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
+
+    WXModuleManager.onRequestPermissionsResult(getInstanceId(),requestCode,permissions,grantResults);
+
+    if(mRootComp != null) {
+       mRootComp.onRequestPermissionsResult(requestCode,permissions,grantResults);
+    }else{
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w(
+                "Warning :Component tree has not build completely, onRequestPermissionsResult can not be call!");
+        }
+    }
+  }
+
+  /********************************
+   *  end hook Activity life cycle callback
+   ********************************************************/
+
+  public void onViewDisappear(){
+    isViewDisAppear = false;
+    mApmForInstance.onDisAppear();
+    WXComponent comp = getRootComponent();
+    if(comp != null) {
+      fireEvent(comp.getRef(), Constants.Event.VIEWDISAPPEAR, null, null);
+      //call disappear of nested instances
+      for(OnInstanceVisibleListener instance:mVisibleListeners){
+        instance.onDisappear();
+      }
+    }
+  }
+
+  public boolean isViewDisAppear(){
+    return isViewDisAppear;
+  }
+
+  public void onViewAppear(){
+    isViewDisAppear = true;
+    mApmForInstance.onAppear();
+    WXComponent comp = getRootComponent();
+    if(comp != null) {
+      fireEvent( comp.getRef(), Constants.Event.VIEWAPPEAR,null, null);
+      for(OnInstanceVisibleListener instance:mVisibleListeners){
+        instance.onAppear();
+      }
+    }
+  }
+
+
+  public void onCreateFinish() {
+    if(mHasCreateFinish){
+      return;
+    }
+    if (mContext != null) {
+      onViewAppear();
+      View wxView= mRenderContainer;
+      if(mRenderListener != null) {
+        mRenderListener.onViewCreated(WXSDKInstance.this, wxView);
+      }
+      if (mStatisticsListener != null) {
+        mStatisticsListener.onFirstView();
+      }
+    }
+  }
+
+  /**
+   * call back when update finish
+   */
+  public void onUpdateFinish() {
+    if (WXEnvironment.isApkDebugable()){
+      WXLogUtils.d("Instance onUpdateSuccess");
+    }
+  }
+
+
+  public void runOnUiThread(Runnable action) {
+    WXSDKManager.getInstance().postOnUiThread(action, 0);
+  }
+
+  public void onRenderSuccess(final int width, final int height) {
+    isRenderSuccess = true;
+    if (!isNewFsEnd){
+      getApmForInstance().arriveNewFsRenderTime();
+    }
+    if (!getApmForInstance().stageMap.containsKey(WXInstanceApm.KEY_PAGE_STAGES_INTERACTION)){
+      getApmForInstance().arriveInteraction(getRootComponent());
+    }
+
+    long time = System.currentTimeMillis() - mRenderStartTime;
+    long[] renderFinishTime = WXBridgeManager.getInstance().getRenderFinishTime(getInstanceId());
+
+    mWXPerformance.callBridgeTime = renderFinishTime[0];
+    mWXPerformance.cssLayoutTime = renderFinishTime[1];
+    mWXPerformance.parseJsonTime = renderFinishTime[2];
+
+    mWXPerformance.totalTime = time;
+    if(mWXPerformance.screenRenderTime<0.001){
+      mWXPerformance.screenRenderTime =  time;
+    }
+
+    if (mRenderListener != null && mContext != null) {
+      mRenderListener.onRenderSuccess(WXSDKInstance.this, width, height);
+      if (mUserTrackAdapter != null) {
+        WXPerformance performance=new WXPerformance(mInstanceId);
+        performance.errCode=WXErrorCode.WX_SUCCESS.getErrorCode();
+        performance.args=getBundleUrl();
+        mUserTrackAdapter.commit(mContext,null,IWXUserTrackAdapter.JS_BRIDGE,performance,getUserTrackParams());
+      }
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d(WXLogUtils.WEEX_PERF_TAG, mWXPerformance.toString());
+      }
+    }
+    if(WXEnvironment.isPerf()){
+      WXLogUtils.e("weex_perf",mWXPerformance.getPerfData());
+    }
+  }
+
+  public void onRefreshSuccess(final int width, final int height) {
+    if (mRenderListener != null && mContext != null) {
+      mRenderListener.onRefreshSuccess(WXSDKInstance.this, width, height);
+    }
+  }
+
+  public void onChangeElement(WXComponent component, boolean isOutOfScreen) {
+
+    if (isDestroy()  || null == mRenderContainer || mWXPerformance == null ){
+      return;
+    }
+    if (null == component || component.isIgnoreInteraction){
+        return;
+    }
+
+    if (mRenderContainer.hasConsumeEvent()) {
+      return;
+    }
+
+    long lastElementChangeTime = System.currentTimeMillis();
+
+    long lazyLoadTime;
+
+    if (mHasCreateFinish){
+      lazyLoadTime = lastElementChangeTime - mWXPerformance.renderTimeOrigin;
+      if (lazyLoadTime > 8000) {
+        //force record detail performance data
+        return;
+      }
+    }
+
+    if (component.mIsAddElementToTree) {
+      getWXPerformance().localInteractionViewAddCount++;
+      if (!isOutOfScreen)
+        getWXPerformance().interactionViewAddLimitCount++;
+      component.mIsAddElementToTree = false;
+    }
+
+    if (!isOutOfScreen) {
+      mApmForInstance.arriveInteraction(component);
+    }
+  }
+
+  public void onRenderError(final String errCode, final String msg) {
+    WXStateRecord.getInstance().recordException(getInstanceId(),"onRenderError,"+errCode+","+msg);
+    if (mRenderListener != null && mContext != null) {
+      WXLogUtils.e("onRenderError "+errCode +","+msg);
+      runOnUiThread(new Runnable() {
+
+        @Override
+        public void run() {
+          if (mRenderListener != null && mContext != null) {
+            mRenderListener.onException(WXSDKInstance.this, errCode, msg);
+          }
+        }
+      });
+    }
+  }
+
+  public void onJSException(final String errCode, final String function, final String exception) {
+    WXStateRecord.getInstance().recordException(getInstanceId(),"onJSException,"+errCode+","+function+"|"+exception);
+    hasException = true;
+    if (mRenderListener != null && mContext != null) {
+      WXLogUtils.e("onJSException "+errCode +","+exception);
+      runOnUiThread(new Runnable() {
+
+        @Override
+        public void run() {
+          if (mRenderListener != null && mContext != null) {
+            StringBuilder builder = new StringBuilder();
+            builder.append(function);
+            builder.append(exception);
+            mRenderListener.onException(WXSDKInstance.this, errCode, builder.toString());
+          }
+        }
+      });
+    }
+  }
+
+
+  @Override
+  public final void onLayoutChange(View v, int left, int top, int right, int bottom, int oldLeft, int
+          oldTop, int oldRight, int oldBottom) {
+    if (left != oldLeft || top != oldTop || right != oldRight || bottom != oldBottom) {
+      onLayoutChange(v);
+    }
+  }
+
+  /**
+   * Subclass should override this method to get notifications of layout change of GodView.
+   * @param godView the godView.
+   */
+  public void onLayoutChange(View godView) {
+
+  }
+
+  private boolean mCreateInstance =true;
+  public void firstScreenCreateInstanceTime(long time) {
+    if(mCreateInstance) {
+      mWXPerformance.firstScreenJSFExecuteTime = time -mRenderStartTime;
+      mCreateInstance =false;
+    }
+  }
+
+  public void callJsTime(final long time){
+    if (!mEnd){
+      mWXPerformance.fsCallJsTotalTime+=time;
+      mWXPerformance.fsCallJsTotalNum++;
+    }
+  }
+
+  public void onComponentCreate(WXComponent component,long createTime) {
+      mWXPerformance.mActionAddElementCount++;
+      mWXPerformance.mActionAddElementSumTime += createTime;
+      if (!mEnd){
+        mWXPerformance.fsComponentCreateTime+=createTime;
+        mWXPerformance.fsComponentCount++;
+      }
+      mWXPerformance.componentCount++;
+      mWXPerformance.componentCreateTime+=createTime;
+  }
+
+  public void callActionAddElementTime(long time) {
+      mWXPerformance.mActionAddElementSumTime += time;
+  }
+
+  public void onOldFsRenderTimeLogic(){
+      if (mEnd){
+        return;
+      }
+      mEnd = true;
+      if (mStatisticsListener != null && mContext != null) {
+        runOnUiThread(new Runnable() {
+        @Override
+        public void run() {
+            if (mStatisticsListener != null && mContext != null) {
+              Trace.beginSection("onFirstScreen");
+              mStatisticsListener.onFirstScreen();
+              Trace.endSection();
+            }
+          }
+        });
+      }
+      mApmForInstance.arriveFSRenderTime();
+      mWXPerformance.fsRenderTime = System.currentTimeMillis();
+      mWXPerformance.screenRenderTime = System.currentTimeMillis() - mRenderStartTime;
+  }
+
+  public WXSDKInstance getParentInstance() {
+    return mParentInstance;
+  }
+
+  public void setParentInstance(WXSDKInstance mParentInstance) {
+    this.mParentInstance = mParentInstance;
+  }
+
+  private void destroyView(View rootView) {
+    try {
+      if (rootView instanceof ViewGroup) {
+        ViewGroup cViewGroup = ((ViewGroup) rootView);
+        for (int index = 0; index < cViewGroup.getChildCount(); index++) {
+          destroyView(cViewGroup.getChildAt(index));
+        }
+
+        cViewGroup.removeViews(0, ((ViewGroup) rootView).getChildCount());
+        // Ensure that the viewgroup's status to be normal
+        WXReflectionUtils.setValue(rootView, "mChildrenCount", 0);
+
+      }
+      if(rootView instanceof Destroyable){
+        ((Destroyable)rootView).destroy();
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("WXSDKInstance destroyView Exception: ", e);
+    }
+  }
+
+  public synchronized void destroy() {
+    if(!isDestroy()) {
+      if(mParentInstance != null){
+         mParentInstance = null;
+      }
+      mApmForInstance.onEnd();
+
+
+      if(mRendered) {
+        WXSDKManager.getInstance().destroyInstance(mInstanceId);
+      }
+
+      try {
+        if (mGlobalEventReceiver != null) {
+          getContext().unregisterReceiver(mGlobalEventReceiver);
+          mGlobalEventReceiver = null;
+        }
+      }catch (IllegalArgumentException e){
+        WXLogUtils.w(WXLogUtils.getStackTrace(e));
+      }
+
+      if (mRootComp != null) {
+        mRootComp.destroy();
+        mRootComp = null;
+      }
+
+      if(mRenderContainer != null){
+        destroyView(mRenderContainer);
+      }
+
+
+      if (mGlobalEvents != null) {
+        mGlobalEvents.clear();
+      }
+
+      if (mComponentObserver != null) {
+        mComponentObserver = null;
+      }
+
+      if (mLayerOverFlowListeners != null) {
+        mLayerOverFlowListeners.clear();
+      }
+
+      if(mWXOnActivityResultHandlers != null && !mWXOnActivityResultHandlers.isEmpty()) {
+        mWXOnActivityResultHandlers.clear();
+      }
+
+      if(mWXBackPressedHandlers != null && !mWXBackPressedHandlers.isEmpty()) {
+        mWXBackPressedHandlers.clear();
+      }
+
+      if(mWXActionbarHandlers != null && !mWXActionbarHandlers.isEmpty()) {
+        mWXActionbarHandlers.clear();
+      }
+
+      getFlatUIContext().destroy();
+      mFlatGUIContext = null;
+      mInstanceOnFireEventInterceptorList = null;
+      mWXScrollListeners = null;
+      mWXActionbarHandlers = null;
+      mWXBackPressedHandlers = null;
+      mRenderContainer = null;
+      mNestedInstanceInterceptor = null;
+      mUserTrackAdapter = null;
+      mScrollView = null;
+      mContext = null;
+      mRenderListener = null;
+      isDestroy = true;
+      mStatisticsListener = null;
+      if(responseHeaders != null){
+        responseHeaders.clear();
+      }
+      if(templateRef != null){
+        templateRef = null;
+      }
+      if (null != mContentBoxMeasurements) {
+        mContentBoxMeasurements.clear();
+      }
+      mWXPerformance.afterInstanceDestroy(mInstanceId);
+
+      WXBridgeManager.getInstance().post(new Runnable() {
+        @Override
+        public void run() {
+          WXBridgeManager.getInstance().onInstanceClose(getInstanceId());
+          inactiveAddElementAction.clear();
+        }
+      });
+
+      //when report error in @WXExceptionUtils
+      // instance may had destroy and remove,
+      // so we delay remove from allInstanceMap
+      WXBridgeManager.getInstance().postDelay(new Runnable() {
+        @Override
+        public void run() {
+          WXSDKManager.getInstance().getAllInstanceMap().remove(mInstanceId);
+        }
+      },1000);
+    }
+  }
+
+  public boolean isDestroy(){
+    return isDestroy;
+  }
+
+  /**
+   * @return If you use render () the return value may be empty
+   */
+  public @Nullable String getBundleUrl() {
+    return mBundleUrl;
+  }
+
+  public View getRootView() {
+    if (mRootComp == null)
+      return null;
+    return mRootComp.getRealView();
+  }
+
+  public View getContainerView() {
+    return mRenderContainer;
+  }
+
+  @Deprecated
+  public void setBundleUrl(String url){
+    mBundleUrl = url;
+    if(WXSDKManager.getInstance().getValidateProcessor()!=null) {
+      mNeedValidate = WXSDKManager.getInstance().getValidateProcessor().needValidate(mBundleUrl);
+    }
+  }
+
+  public void onRootCreated(WXComponent root) {
+    this.mRootComp = root;
+    this.mRootComp.mDeepInComponentTree =1;
+    mRenderContainer.addView(root.getHostView());
+
+
+    setSize(mRenderContainer.getWidth(),mRenderContainer.getHeight());
+  }
+
+  /**
+   * Move fixed view to container ,except it's already moved.
+   * @param fixedChild
+   */
+  public void moveFixedView(View fixedChild){
+    if(mRenderContainer != null) {
+      ViewGroup parent;
+      if((parent = (ViewGroup) fixedChild.getParent()) != null){
+        if (parent != mRenderContainer) {
+          parent.removeView(fixedChild);
+          mRenderContainer.addView(fixedChild);
+        }
+      }else{
+        mRenderContainer.addView(fixedChild);
+      }
+    }
+  }
+
+  public void removeFixedView(View fixedChild){
+    if(mRenderContainer != null) {
+      mRenderContainer.removeView(fixedChild);
+    }
+  }
+
+  public int getRenderContainerPaddingLeft() {
+    if(mRenderContainer != null) {
+      return mRenderContainer.getPaddingLeft();
+    }
+    return 0;
+  }
+
+  public int getRenderContainerPaddingRight() {
+    if(mRenderContainer != null) {
+      return mRenderContainer.getPaddingRight();
+    }
+    return 0;
+  }
+
+  public int getRenderContainerPaddingTop() {
+    if(mRenderContainer != null) {
+      return mRenderContainer.getPaddingTop();
+    }
+    return 0;
+  }
+
+  public synchronized List<OnWXScrollListener> getWXScrollListeners() {
+    return mWXScrollListeners;
+  }
+
+  public synchronized void registerOnWXScrollListener(OnWXScrollListener wxScrollListener) {
+    if(mWXScrollListeners==null){
+      mWXScrollListeners=new ArrayList<>();
+    }
+    mWXScrollListeners.add(wxScrollListener);
+  }
+
+  public synchronized void registerActionbarHandler(ActionBarHandler actionBarHandler) {
+    if(actionBarHandler == null) {
+      return;
+    }
+    if(mWXActionbarHandlers == null) {
+      mWXActionbarHandlers = new ArrayList<>();
+    }
+
+    mWXActionbarHandlers.add(actionBarHandler);
+  }
+
+  public synchronized void unRegisterActionbarHandler(ActionBarHandler actionBarHandler) {
+    if(mWXActionbarHandlers != null && actionBarHandler != null) {
+      mWXActionbarHandlers.remove(actionBarHandler);
+    }
+  }
+
+  public synchronized void unRegisterOnActivityResultHandler(OnActivityResultHandler onActivityResultHandler) {
+    if(mWXOnActivityResultHandlers != null && onActivityResultHandler != null) {
+      mWXOnActivityResultHandlers.remove(onActivityResultHandler);
+    }
+  }
+
+  public synchronized void registerOnActivityResultHandler(OnActivityResultHandler onActivityResultHandler) {
+    if(onActivityResultHandler == null) {
+      return;
+    }
+
+    if(mWXOnActivityResultHandlers == null) {
+      mWXOnActivityResultHandlers = new ArrayList<>();
+    }
+    mWXOnActivityResultHandlers.add(onActivityResultHandler);
+  }
+
+
+  public synchronized void registerBackPressedHandler(OnBackPressedHandler backPressedHandler) {
+    if(backPressedHandler == null) {
+      return;
+    }
+
+    if(mWXBackPressedHandlers == null) {
+      mWXBackPressedHandlers = new ArrayList<>();
+    }
+
+    mWXBackPressedHandlers.add(backPressedHandler);
+  }
+
+  public synchronized void unRegisterBackPressedHandler(OnBackPressedHandler backPressedHandler) {
+    if(mWXBackPressedHandlers != null && backPressedHandler != null) {
+      mWXBackPressedHandlers.remove(backPressedHandler);
+    }
+  }
+
+  static int sScreenHeight = -1;
+  public void setSize(int width, int height) {
+    if (width > 0 && height > 0 & !isDestroy && mRendered && mRenderContainer != null) {
+        if (sScreenHeight < 0){
+            sScreenHeight = WXViewUtils.getScreenHeight(getContext());
+        }
+        if (sScreenHeight>0){
+            double screenRatio = (double)height/(double)sScreenHeight *100;
+            if(screenRatio>100){
+              screenRatio =100;
+            }
+            getApmForInstance().addStats(WXInstanceApm.KEY_PAGE_STATS_BODY_RATIO,screenRatio);
+        }
+      ViewGroup.LayoutParams layoutParams = mRenderContainer.getLayoutParams();
+      if (layoutParams != null) {
+        final float realWidth = width;
+        final float realHeight = height;
+        if (mRenderContainer.getWidth() != width || mRenderContainer.getHeight() != height) {
+          layoutParams.width = width;
+          layoutParams.height = height;
+          mRenderContainer.setLayoutParams(layoutParams);
+        }
+
+        if (mRootComp != null && layoutParams != null) {
+          final boolean isWidthWrapContent = layoutParams.width == ViewGroup.LayoutParams.WRAP_CONTENT;
+          final boolean isHeightWrapContent = layoutParams.height == ViewGroup.LayoutParams.WRAP_CONTENT;
+
+          WXBridgeManager.getInstance().post(new Runnable() {
+            @Override
+            public void run() {
+              WXBridgeManager.getInstance().setDefaultRootSize(getInstanceId(), realWidth, realHeight, isWidthWrapContent,
+                      isHeightWrapContent);
+            }
+          });
+        }
+      }
+    }
+  }
+
+  /*Global Event*/
+  private HashMap<String, List<String>> mGlobalEvents = new HashMap<>();
+
+  public void fireGlobalEventCallback(String eventName, Map<String,Object> params){
+    List<String> callbacks=mGlobalEvents.get(eventName);
+    if(callbacks!=null){
+      for(String callback:callbacks){
+        WXSDKManager.getInstance().callback(mInstanceId,callback,params,true);
+      }
+    }
+  }
+
+  /**
+   * Fire event callback on a element.
+   * @param elementRef
+   * @param type
+   * @param data
+   * @param domChanges
+   */
+  public void fireEvent(String elementRef,final String type, final Map<String, Object> data,final Map<String, Object> domChanges, List<Object> eventArgs){
+    fireEvent(elementRef, type, data, domChanges, eventArgs, null);
+  }
+
+  public void fireEvent(String elementRef,final String type, final Map<String, Object> data,final Map<String, Object> domChanges, List<Object> eventArgs, EventResult callback) {
+    onInterceptInstanceEvent(getInstanceId(), elementRef, type, data, domChanges);
+    if (null != mWXPerformance && mWXPerformance.fsCallEventTotalNum<Integer.MAX_VALUE){
+      mWXPerformance.fsCallEventTotalNum++;
+    }
+    mApmForInstance.updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_CALL_EVENT_NUM,1);
+    WXBridgeManager.getInstance().fireEventOnNode(getInstanceId(),elementRef,type,data,domChanges, eventArgs, callback);
+  }
+
+
+  /**
+   * Fire event callback on a element.
+   * @param elementRef
+   * @param type
+   * @param data
+   * @param domChanges
+   */
+  public void fireEvent(String elementRef,final String type, final Map<String, Object> data,final Map<String, Object> domChanges){
+    fireEvent(elementRef, type, data, domChanges, null);
+  }
+
+  public void fireEvent(String elementRef,final String type, final Map<String, Object> data){
+    fireEvent(elementRef,type,data,null);
+  }
+
+  public void fireEvent(String ref, String type){
+    fireEvent(ref,type,new HashMap<String, Object>());
+  }
+
+  protected void addEventListener(String eventName, String callback) {
+    if (TextUtils.isEmpty(eventName) || TextUtils.isEmpty(callback)) {
+      return;
+    }
+    List<String> callbacks = mGlobalEvents.get(eventName);
+    if (callbacks == null) {
+      callbacks = new ArrayList<>();
+      mGlobalEvents.put(eventName, callbacks);
+    }
+    callbacks.add(callback);
+  }
+  protected void removeEventListener(String eventName, String callback) {
+    if (TextUtils.isEmpty(eventName) || TextUtils.isEmpty(callback)) {
+      return;
+    }
+    List<String> callbacks = mGlobalEvents.get(eventName);
+    if (callbacks != null) {
+      callbacks.remove(callback);
+    }
+  }
+
+  protected void removeEventListener(String eventName) {
+    if (TextUtils.isEmpty(eventName)) {
+      return;
+    }
+    mGlobalEvents.remove(eventName);
+  }
+
+  /**
+   * Notifies WEEX that this event has occurred
+   * @param eventName WEEX register event
+   * @param module Events occur in this Module
+   * @param params The parameters to be notified to WEEX are required
+   */
+  public void fireModuleEvent(String eventName, WXModule module,Map<String, Object> params) {
+    if (TextUtils.isEmpty(eventName) || module == null) {
+      return;
+    }
+
+    Map<String, Object> event = new HashMap<>();
+    event.put("type", eventName);
+    event.put("module", module.getModuleName());
+    event.put("data", params);
+
+    List<String> callbacks = module.getEventCallbacks(eventName);
+    if (callbacks != null) {
+      for (String callback : callbacks) {
+        SimpleJSCallback jsCallback = new SimpleJSCallback(mInstanceId, callback);
+        if (module.isOnce(callback)) {
+          jsCallback.invoke(event);
+        } else {
+          jsCallback.invokeAndKeepAlive(event);
+        }
+      }
+    }
+  }
+
+  /**
+   * Check whether the current module registered the event
+   * @param eventName EventName register in weex
+   * @param module Events occur in this Module
+   * @return  register->true
+   */
+  public boolean checkModuleEventRegistered(String eventName,WXModule module) {
+    if (module != null) {
+      List<String> events = module.getEventCallbacks(eventName);
+      if (events != null && events.size() > 0) {
+        return true;
+      }
+    }
+    return false;
+  }
+
+  public WXPerformance getWXPerformance(){
+    return mWXPerformance;
+  }
+
+  public WXInstanceApm getApmForInstance() {
+    return mApmForInstance;
+  }
+
+  public Map<String, Serializable> getUserTrackParams() {
+    return mUserTrackParams;
+  }
+
+  public void addUserTrackParameter(String key,Serializable value){
+    if(this.mUserTrackParams == null){
+      this.mUserTrackParams = new ConcurrentHashMap<>();
+    }
+    mUserTrackParams.put(key,value);
+  }
+
+  public void clearUserTrackParameters(){
+    if(this.mUserTrackParams != null){
+      this.mUserTrackParams.clear();
+    }
+  }
+
+  public void removeUserTrackParameter(String key){
+    if(this.mUserTrackParams != null){
+      this.mUserTrackParams.remove(key);
+    }
+  }
+
+  public int getMaxDeepLayer() {
+    return mMaxDeepLayer;
+  }
+
+  public void setMaxDeepLayer(int maxDeepLayer) {
+    mMaxDeepLayer = maxDeepLayer;
+    mApmForInstance.updateMaxStats(WXInstanceApm.KEY_PAGE_STATS_MAX_DEEP_VIEW,maxDeepLayer);
+  }
+
+  public void setMaxDomDeep(int maxDomDeep){
+    mApmForInstance.updateMaxStats(WXInstanceApm.KEY_PAGE_STATS_MAX_DEEP_DOM,maxDomDeep);
+    if (null == mWXPerformance){
+      return;
+    }
+    if (mWXPerformance.maxDeepVDomLayer <= maxDomDeep){
+      mWXPerformance.maxDeepVDomLayer = maxDomDeep;
+    }
+  }
+
+  public void onHttpStart(){
+    if (!mEnd){
+      mWXPerformance.fsRequestNum++;
+    }
+  }
+
+  /**
+   * return md5, and bytes length
+   * */
+  public String getTemplateInfo() {
+    String template = getTemplate();
+    if(template == null){
+      return " template md5 null ,httpHeader:" + JSONObject.toJSONString(responseHeaders);
+    }
+    if(TextUtils.isEmpty(template)){
+      return " template md5  length 0 ,httpHeader" + JSONObject.toJSONString(responseHeaders);
+    }
+    try {
+      byte[] bts = template.getBytes("UTF-8");
+      String sourceMD5 = WXFileUtils.md5(bts);
+      String sourceBase64MD5 = WXFileUtils.base64Md5(bts);
+      ArrayList<String> sourceMD5List = new ArrayList<>();
+      ArrayList<String> sourceBase64MD5List = new ArrayList<>();
+      sourceMD5List.add(sourceMD5);
+      sourceBase64MD5List.add(sourceBase64MD5);
+      responseHeaders.put("templateSourceMD5", sourceMD5List);
+      responseHeaders.put(SOURCE_TEMPLATE_BASE64_MD5, sourceBase64MD5List);
+      return " template md5 " + sourceMD5 + " length " +   bts.length
+              + " base64 md5 " + sourceBase64MD5
+              + " response header " + JSONObject.toJSONString(responseHeaders);
+    } catch (Exception e) {
+      return "template md5 getBytes error";
+    }
+
+  }
+
+  /**
+   * check template header md5 match with header  content-md5
+   * */
+  public boolean isContentMd5Match(){
+    if(responseHeaders == null){
+      return true;
+    }
+    List<String> contentMD5s = responseHeaders.get("Content-Md5");
+    if(contentMD5s == null){
+      contentMD5s  = responseHeaders.get("content-md5");
+    }
+    if(contentMD5s == null || contentMD5s.size() <= 0){
+      return true;
+    }
+    String md5 = contentMD5s.get(0);
+
+    List<String> sourceBase64Md5 = responseHeaders.get(SOURCE_TEMPLATE_BASE64_MD5);
+    if(sourceBase64Md5 == null){
+      getTemplateInfo();
+      sourceBase64Md5 = responseHeaders.get(SOURCE_TEMPLATE_BASE64_MD5);
+    }
+    if(sourceBase64Md5 == null || sourceBase64Md5.size() == 0){
+      return  true;
+    }
+    return  md5.equals(sourceBase64Md5.get(0));
+  }
+
+  public String getTemplate() {
+    if(templateRef == null){
+      return  null;
+    }
+    return templateRef.get();
+  }
+
+  public void setTemplate(String template) {
+    this.templateRef = new WeakReference<String>(template);
+  }
+
+  public interface NestedInstanceInterceptor {
+    void onCreateNestInstance(WXSDKInstance instance, NestedContainer container);
+  }
+
+  public void OnVSync() {
+    if(mFixMultiThreadBug) {
+      if(!mPageDirty) {
+        return;
+      }
+      WXBridgeManager.getInstance().post(new Runnable() {
+        @Override
+        public void run() {
+          boolean forceLayout = WXBridgeManager.getInstance().notifyLayout(getInstanceId());
+          if(forceLayout) {
+            WXBridgeManager.getInstance().forceLayout(getInstanceId());
+          }
+        }
+      });
+    } else  {
+      boolean forceLayout = WXBridgeManager.getInstance().notifyLayout(getInstanceId());
+      if(forceLayout) {
+        WXBridgeManager.getInstance().post(new Runnable() {
+          @Override
+          public void run() {
+            WXBridgeManager.getInstance().forceLayout(getInstanceId());
+          }
+        });
+      }
+    }
+
+
+  }
+
+  public void addContentBoxMeasurement(long renderObjectPtr, ContentBoxMeasurement contentBoxMeasurement) {
+    mContentBoxMeasurements.put(renderObjectPtr, contentBoxMeasurement);
+  }
+
+  public ContentBoxMeasurement getContentBoxMeasurement(long renderObjectPtr) {
+    return mContentBoxMeasurements.get(renderObjectPtr);
+  }
+
+
+  private void onInterceptInstanceEvent(String instanceId, String elementRef, String type, Map<String, Object> data, Map<String, Object> domChanges) {
+    if(this.mInstanceOnFireEventInterceptorList == null){
+      return;
+    }
+    for(InstanceOnFireEventInterceptor instanceOnFireEventInterceptor : this.mInstanceOnFireEventInterceptorList){
+      instanceOnFireEventInterceptor.onInterceptFireEvent(instanceId, elementRef, type, data, domChanges);
+    }
+  }
+
+  public List<InstanceOnFireEventInterceptor> getInstanceOnFireEventInterceptorList(){
+    if(this.mInstanceOnFireEventInterceptorList == null){
+      this.mInstanceOnFireEventInterceptorList = new ArrayList<>();
+    }
+    return mInstanceOnFireEventInterceptorList;
+  }
+
+
+  public void addInstanceOnFireEventInterceptor(InstanceOnFireEventInterceptor instanceOnFireEventInterceptor) {
+    if(instanceOnFireEventInterceptor == null){
+      return;
+    }
+    if(!getInstanceOnFireEventInterceptorList().contains(instanceOnFireEventInterceptor)){
+      getInstanceOnFireEventInterceptorList().add(instanceOnFireEventInterceptor);
+    }
+  }
+
+  public String getRenderType() {
+    return mRenderType;
+  }
+
+  public void setRenderType(String renderType) {
+    this.mRenderType = renderType;
+  }
+
+  private static boolean isDisableSkipFrameworkInDataRender() {
+    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
+    if (adapter == null) {
+      return false;
+    }
+    String result = adapter.getConfig("wxeagle", "disable_skip_framework_init", "false");
+    return "true".equals(result);
+  }
+
+  public boolean isPageDirty() {
+    return mPageDirty;
+  }
+
+  public void setPageDirty(boolean mPageDirty) {
+    this.mPageDirty = mPageDirty;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/WXSDKManager.java b/android/sdk/src/main/java/org/apache/weex/WXSDKManager.java
new file mode 100644
index 0000000..628e4cc
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/WXSDKManager.java
@@ -0,0 +1,540 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex;
+
+import android.os.Looper;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+
+import org.apache.weex.adapter.ClassLoaderAdapter;
+import org.apache.weex.adapter.DefaultUriAdapter;
+import org.apache.weex.adapter.DefaultWXHttpAdapter;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.adapter.ICrashInfoReporter;
+import org.apache.weex.adapter.IDrawableLoader;
+import org.apache.weex.adapter.IWXJscProcessManager;
+import org.apache.weex.adapter.ITracingAdapter;
+import org.apache.weex.adapter.IWXAccessibilityRoleAdapter;
+import org.apache.weex.adapter.IWXHttpAdapter;
+import org.apache.weex.adapter.IWXImgLoaderAdapter;
+import org.apache.weex.adapter.IWXJSExceptionAdapter;
+import org.apache.weex.adapter.IWXJsFileLoaderAdapter;
+import org.apache.weex.adapter.IWXSoLoaderAdapter;
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.appfram.navigator.IActivityNavBarSetter;
+import org.apache.weex.appfram.navigator.INavigator;
+import org.apache.weex.appfram.storage.DefaultWXStorage;
+import org.apache.weex.appfram.storage.IWXStorageAdapter;
+import org.apache.weex.appfram.websocket.IWebSocketAdapter;
+import org.apache.weex.appfram.websocket.IWebSocketAdapterFactory;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.bridge.WXModuleManager;
+import org.apache.weex.bridge.WXValidateProcessor;
+import org.apache.weex.common.WXRefreshData;
+import org.apache.weex.common.WXRuntimeException;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.common.WXWorkThreadManager;
+import org.apache.weex.font.FontAdapter;
+import org.apache.weex.performance.IApmGenerator;
+import org.apache.weex.performance.IWXAnalyzer;
+import org.apache.weex.ui.WXRenderManager;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+
+import java.io.File;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.CopyOnWriteArrayList;
+import java.util.concurrent.atomic.AtomicInteger;
+
+/**
+ * Manger class for weex context.
+ */
+public class WXSDKManager {
+
+  private static volatile WXSDKManager sManager;
+  private static AtomicInteger sInstanceId = new AtomicInteger(0);
+  private final WXWorkThreadManager mWXWorkThreadManager;
+  private WXBridgeManager mBridgeManager;
+  /** package **/ WXRenderManager mWXRenderManager;
+
+  private IWXUserTrackAdapter mIWXUserTrackAdapter;
+  private IWXImgLoaderAdapter mIWXImgLoaderAdapter;
+  private IWXSoLoaderAdapter mIWXSoLoaderAdapter;
+  private IDrawableLoader mDrawableLoader;
+  private IWXHttpAdapter mIWXHttpAdapter;
+  private IActivityNavBarSetter mActivityNavBarSetter;
+  private IWXAccessibilityRoleAdapter mRoleAdapter;
+  private List<IWXAnalyzer> mWXAnalyzerList;
+  private IApmGenerator mApmGenerater;
+  private IWXJsFileLoaderAdapter mWXJsFileLoaderAdapter;
+
+  private ICrashInfoReporter mCrashInfo;
+
+  private IWXJSExceptionAdapter mIWXJSExceptionAdapter;
+
+  private IWXConfigAdapter mConfigAdapter;
+  private IWXStorageAdapter mIWXStorageAdapter;
+  private IWXStatisticsListener mStatisticsListener;
+  private URIAdapter mURIAdapter;
+  private ClassLoaderAdapter mClassLoaderAdapter;
+  private IWebSocketAdapterFactory mIWebSocketAdapterFactory;
+  private ITracingAdapter mTracingAdapter;
+  private WXValidateProcessor mWXValidateProcessor;
+  private IWXJscProcessManager mWXJscProcessManager;
+  // Tell weexv8 to initialize v8, default is true.
+  private boolean mNeedInitV8 = true;
+
+  //add when instance create,rm when instance destroy, not like WXRenderManager
+  private Map<String,WXSDKInstance> mAllInstanceMap;
+
+  private List<InstanceLifeCycleCallbacks> mLifeCycleCallbacks;
+
+  private static final int DEFAULT_VIEWPORT_WIDTH = 750;
+
+  private WXSDKManager() {
+    this(new WXRenderManager());
+  }
+
+  private WXSDKManager(WXRenderManager renderManager) {
+    mWXRenderManager = renderManager;
+    mBridgeManager = WXBridgeManager.getInstance();
+    mWXWorkThreadManager = new WXWorkThreadManager();
+    mWXAnalyzerList = new CopyOnWriteArrayList<>();
+    mAllInstanceMap = new HashMap<>();
+  }
+
+  /**
+   * Used in junit test
+   */
+  static void initInstance(WXRenderManager renderManager){
+    sManager = new WXSDKManager(renderManager);
+  }
+
+  public void registerStatisticsListener(IWXStatisticsListener listener) {
+    mStatisticsListener = listener;
+  }
+
+  public IWXStatisticsListener getWXStatisticsListener() {
+    return mStatisticsListener;
+  }
+
+  public void onSDKEngineInitialize() {
+    if (mStatisticsListener != null) {
+      mStatisticsListener.onSDKEngineInitialize();
+    }
+  }
+
+  public void setNeedInitV8(boolean need) {
+    mNeedInitV8 = need;
+  }
+
+  public boolean needInitV8() {
+    return mNeedInitV8;
+  }
+
+  public void takeJSHeapSnapshot(String path) {
+    File file = new File(path);
+    if (!file.exists()) {
+      if (!file.mkdir()) {
+        return;
+      }
+    }
+
+    String name = String.valueOf(sInstanceId.get());
+    String filename = path;
+
+    if (!path.endsWith(File.separator)) {
+      filename += File.separator;
+    }
+    filename += name;
+    filename += ".heapsnapshot";
+
+    mBridgeManager.takeJSHeapSnapshot(filename);
+  }
+
+  public static WXSDKManager getInstance() {
+    if (sManager == null) {
+      synchronized (WXSDKManager.class) {
+        if(sManager == null) {
+          sManager = new WXSDKManager();
+        }
+      }
+    }
+    return sManager;
+  }
+
+  public static int getInstanceViewPortWidth(String instanceId){
+    WXSDKInstance instance = getInstance().getSDKInstance(instanceId);
+    if (instance == null) {
+      return DEFAULT_VIEWPORT_WIDTH;
+    }
+    return instance.getInstanceViewPortWidth();
+  }
+
+  static void setInstance(WXSDKManager manager){
+    sManager = manager;
+  }
+
+  public IActivityNavBarSetter getActivityNavBarSetter() {
+    return mActivityNavBarSetter;
+  }
+
+  public void setActivityNavBarSetter(IActivityNavBarSetter mActivityNavBarSetter) {
+    this.mActivityNavBarSetter = mActivityNavBarSetter;
+  }
+
+  public void restartBridge() {
+    mBridgeManager.restart();
+  }
+
+  public WXBridgeManager getWXBridgeManager() {
+    return mBridgeManager;
+  }
+
+  public WXRenderManager getWXRenderManager() {
+    return mWXRenderManager;
+  }
+  public IWXJscProcessManager getWXJscProcessManager() {
+    return mWXJscProcessManager;
+  }
+  public WXWorkThreadManager getWXWorkThreadManager() {
+    return mWXWorkThreadManager;
+  }
+
+  public void setWxConfigAdapter(IWXConfigAdapter mConfigAdapter) {
+    this.mConfigAdapter = mConfigAdapter;
+  }
+
+  public IWXConfigAdapter getWxConfigAdapter() {
+    return mConfigAdapter;
+  }
+
+  public @Nullable WXSDKInstance getSDKInstance(String instanceId) {
+    return instanceId == null? null : mWXRenderManager.getWXSDKInstance(instanceId);
+  }
+
+  public void postOnUiThread(Runnable runnable, long delayMillis) {
+    mWXRenderManager.postOnUiThread(WXThread.secure(runnable), delayMillis);
+  }
+  public Map<String, WXSDKInstance> getAllInstanceMap() {
+    return mAllInstanceMap;
+  }
+
+  public void destroy() {
+    if (mWXWorkThreadManager != null) {
+      mWXWorkThreadManager.destroy();
+    }
+    mAllInstanceMap.clear();
+  }
+
+  @Deprecated
+  public void callback(String instanceId, String funcId, Map<String, Object> data) {
+    mBridgeManager.callback(instanceId, funcId, data);
+  }
+
+  @Deprecated
+  public void callback(String instanceId, String funcId, Map<String, Object> data,boolean keepAlive) {
+    mBridgeManager.callback(instanceId, funcId, data,keepAlive);
+  }
+
+  public void initScriptsFramework(String framework) {
+    mBridgeManager.initScriptsFramework(framework);
+  }
+
+  public void registerComponents(List<Map<String, Object>> components) {
+    mBridgeManager.registerComponents(components);
+  }
+
+  public void registerModules(Map<String, Object> modules) {
+    mBridgeManager.registerModules(modules);
+  }
+
+  /**
+   * Do not direct invoke this method in Components, use {@link WXSDKInstance#fireEvent(String, String, Map, Map)} instead.
+   */
+  @Deprecated
+  public void fireEvent(final String instanceId, String ref, String type) {
+    fireEvent(instanceId, ref, type, new HashMap<String, Object>());
+  }
+
+  /**
+   * FireEvent back to JS
+   * Do not direct invoke this method in Components, use {@link WXSDKInstance#fireEvent(String, String, Map, Map)} instead.
+   */
+  @Deprecated
+  public void fireEvent(final String instanceId, String ref, String type, Map<String, Object> params){
+    fireEvent(instanceId,ref,type,params,null);
+  }
+
+  /**
+   * Do not direct invoke this method in Components, use {@link WXSDKInstance#fireEvent(String, String, Map, Map)} instead.
+   **/
+  @Deprecated
+  public void fireEvent(final String instanceId, String ref, String type, Map<String, Object> params,Map<String,Object> domChanges) {
+    if (WXEnvironment.isApkDebugable() && Looper.getMainLooper().getThread().getId() != Thread.currentThread().getId()) {
+      throw new WXRuntimeException("[WXSDKManager]  fireEvent error");
+    }
+    mBridgeManager.fireEventOnNode(instanceId, ref, type, params,domChanges);
+  }
+
+  void createInstance(WXSDKInstance instance, Script code, Map<String, Object> options, String jsonInitData) {
+    mWXRenderManager.registerInstance(instance);
+    mBridgeManager.createInstance(instance.getInstanceId(), code, options, jsonInitData);
+    if (mLifeCycleCallbacks != null) {
+      for (InstanceLifeCycleCallbacks callbacks : mLifeCycleCallbacks) {
+        callbacks.onInstanceCreated(instance.getInstanceId());
+      }
+    }
+  }
+
+  void refreshInstance(String instanceId, WXRefreshData jsonData) {
+    mBridgeManager.refreshInstance(instanceId, jsonData);
+  }
+
+  void destroyInstance(String instanceId) {
+    setCrashInfo(WXEnvironment.WEEX_CURRENT_KEY,"");
+    if (TextUtils.isEmpty(instanceId)) {
+      return;
+    }
+    if (!WXUtils.isUiThread()) {
+      throw new WXRuntimeException("[WXSDKManager] destroyInstance error");
+    }
+    if (mLifeCycleCallbacks != null) {
+      for (InstanceLifeCycleCallbacks callbacks : mLifeCycleCallbacks) {
+        callbacks.onInstanceDestroyed(instanceId);
+      }
+    }
+    mWXRenderManager.removeRenderStatement(instanceId);
+    mBridgeManager.destroyInstance(instanceId);
+    WXModuleManager.destroyInstanceModules(instanceId);
+  }
+
+  String generateInstanceId() {
+    return String.valueOf(sInstanceId.incrementAndGet());
+  }
+
+  public IWXUserTrackAdapter getIWXUserTrackAdapter() {
+    return mIWXUserTrackAdapter;
+  }
+
+  public IWXImgLoaderAdapter getIWXImgLoaderAdapter() {
+    return mIWXImgLoaderAdapter;
+  }
+
+  public IWXJsFileLoaderAdapter getIWXJsFileLoaderAdapter() {
+    return mWXJsFileLoaderAdapter;
+  }
+
+  public IDrawableLoader getDrawableLoader() {
+    return mDrawableLoader;
+  }
+
+  public IWXJSExceptionAdapter getIWXJSExceptionAdapter() {
+    return mIWXJSExceptionAdapter;
+  }
+
+  public void setIWXJSExceptionAdapter(IWXJSExceptionAdapter IWXJSExceptionAdapter) {
+    mIWXJSExceptionAdapter = IWXJSExceptionAdapter;
+  }
+
+  public @NonNull IWXHttpAdapter getIWXHttpAdapter() {
+    if (mIWXHttpAdapter == null) {
+      mIWXHttpAdapter = new DefaultWXHttpAdapter();
+    }
+    return mIWXHttpAdapter;
+  }
+
+  public IApmGenerator getApmGenerater() {
+    return mApmGenerater;
+  }
+
+  public @NonNull URIAdapter getURIAdapter() {
+    if(mURIAdapter == null){
+      mURIAdapter = new DefaultUriAdapter();
+    }
+    return mURIAdapter;
+  }
+
+  public ClassLoaderAdapter getClassLoaderAdapter() {
+    if(mClassLoaderAdapter == null){
+      mClassLoaderAdapter = new ClassLoaderAdapter();
+    }
+    return mClassLoaderAdapter;
+  }
+
+  public IWXSoLoaderAdapter getIWXSoLoaderAdapter() {
+    return mIWXSoLoaderAdapter;
+  }
+
+  public List<IWXAnalyzer> getWXAnalyzerList(){
+    return mWXAnalyzerList;
+  }
+
+  public void addWXAnalyzer(IWXAnalyzer analyzer){
+    if (!mWXAnalyzerList.contains(analyzer)) {
+      mWXAnalyzerList.add(analyzer);
+    }
+  }
+
+  public void rmWXAnalyzer(IWXAnalyzer analyzer){
+    mWXAnalyzerList.remove(analyzer);
+  }
+
+  void setInitConfig(InitConfig config){
+    this.mIWXHttpAdapter = config.getHttpAdapter();
+    this.mIWXImgLoaderAdapter = config.getImgAdapter();
+    this.mDrawableLoader = config.getDrawableLoader();
+    this.mIWXStorageAdapter = config.getStorageAdapter();
+    this.mIWXUserTrackAdapter = config.getUtAdapter();
+    this.mURIAdapter = config.getURIAdapter();
+    this.mIWebSocketAdapterFactory = config.getWebSocketAdapterFactory();
+    this.mIWXJSExceptionAdapter = config.getJSExceptionAdapter();
+    this.mIWXSoLoaderAdapter = config.getIWXSoLoaderAdapter();
+    this.mClassLoaderAdapter = config.getClassLoaderAdapter();
+    this.mApmGenerater = config.getApmGenerater();
+    this.mWXJsFileLoaderAdapter = config.getJsFileLoaderAdapter();
+    this.mWXJscProcessManager = config.getJscProcessManager();
+  }
+
+  public IWXStorageAdapter getIWXStorageAdapter(){
+    if(mIWXStorageAdapter == null){
+      if(WXEnvironment.sApplication != null){
+        mIWXStorageAdapter = new DefaultWXStorage(WXEnvironment.sApplication);
+      }else{
+        WXLogUtils.e("WXStorageModule", "No Application context found,you should call WXSDKEngine#initialize() method in your application");
+      }
+    }
+    return mIWXStorageAdapter;
+  }
+
+  /**
+   * Weex embedders can use <code>notifyTrimMemory</code> to reduce
+   * memory at a proper time.
+   *
+   * It's not a good idea to reduce memory at any time, because
+   * memory trimming is a expense operation, and V8 needs to do
+   * a full GC and all the inline caches get to be cleared.
+   *
+   * The embedder needs to make some scheduling strategies to
+   * ensure that the embedded application is just on an idle time.
+   * If the application use the same js bundle to render pages,
+   * it's not a good idea to trim memory every time of exiting
+   * pages.
+   */
+  public void notifyTrimMemory() {
+    mBridgeManager.notifyTrimMemory();
+  }
+
+  /**
+   * Weex embedders can use <code>notifySerializeCodeCache</code> to
+   * serialize code caches if the jsfm has the alility to compile 'new Function'
+   * against js bundles on the weex native side.
+   *
+   * It's a good time to serialize a code cache after exiting a weex page.
+   * Then, the next time of entering the same weex page, V8 would compile
+   * 'new Function' against the code cache deseriazed from the js bundle.
+   */
+  public void notifySerializeCodeCache() {
+    mBridgeManager.notifySerializeCodeCache();
+  }
+
+  public @Nullable
+  IWebSocketAdapter getIWXWebSocketAdapter() {
+    if (mIWebSocketAdapterFactory != null) {
+      return mIWebSocketAdapterFactory.createWebSocketAdapter();
+    }
+    return null;
+  }
+
+  public void registerValidateProcessor(WXValidateProcessor processor){
+    this.mWXValidateProcessor = processor;
+  }
+
+  public WXValidateProcessor getValidateProcessor(){
+    return mWXValidateProcessor;
+  }
+
+
+  public void setCrashInfoReporter(ICrashInfoReporter mCrashInfo) {
+    this.mCrashInfo = mCrashInfo;
+  }
+
+  public void setCrashInfo(String key, String value) {
+    if(mCrashInfo!=null){
+      mCrashInfo.addCrashInfo(key,value);
+    }
+  }
+
+  public void setTracingAdapter(ITracingAdapter adapter) {
+    this.mTracingAdapter = adapter;
+  }
+
+  public ITracingAdapter getTracingAdapter() {
+    return mTracingAdapter;
+  }
+
+  public void registerInstanceLifeCycleCallbacks(InstanceLifeCycleCallbacks callbacks) {
+    if (mLifeCycleCallbacks == null) {
+      mLifeCycleCallbacks = new ArrayList<>();
+    }
+    mLifeCycleCallbacks.add(callbacks);
+  }
+
+  public void setAccessibilityRoleAdapter(IWXAccessibilityRoleAdapter adapter) {
+    this.mRoleAdapter = adapter;
+  }
+
+  public IWXAccessibilityRoleAdapter getAccessibilityRoleAdapter() {
+    return mRoleAdapter;
+  }
+
+  public interface InstanceLifeCycleCallbacks {
+    void onInstanceDestroyed(String instanceId);
+    void onInstanceCreated(String instanceId);
+  }
+
+  private INavigator mNavigator;
+
+  public INavigator getNavigator() {
+    return mNavigator;
+  }
+
+  public void setNavigator(INavigator mNavigator) {
+    this.mNavigator = mNavigator;
+  }
+
+
+  private FontAdapter mFontAdapter;
+
+  public FontAdapter getFontAdapter(){
+      if(mFontAdapter == null){
+        synchronized (this){
+          if(mFontAdapter == null){
+              mFontAdapter = new FontAdapter();
+          }
+        }
+      }
+      return mFontAdapter;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/WeexFrameRateControl.java b/android/sdk/src/main/java/org/apache/weex/WeexFrameRateControl.java
new file mode 100644
index 0000000..2d98862
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/WeexFrameRateControl.java
@@ -0,0 +1,110 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex;
+
+/**
+ * Created by shiwentao on 2017/8/24.
+ */
+
+import android.annotation.SuppressLint;
+import android.os.Build;
+import android.util.Log;
+import android.view.Choreographer;
+import org.apache.weex.common.WXErrorCode;
+import java.lang.ref.WeakReference;
+
+public class WeexFrameRateControl {
+    private static final long VSYNC_FRAME = 1000 / 60;
+    private WeakReference<VSyncListener> mListener;
+    private final Choreographer mChoreographer;
+    private final Choreographer.FrameCallback mVSyncFrameCallback;
+    private final Runnable runnable;
+
+    public interface VSyncListener {
+        void OnVSync();
+    }
+
+    public WeexFrameRateControl(VSyncListener listener) {
+        mListener = new WeakReference<>(listener);
+        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.ICE_CREAM_SANDWICH_MR1) {
+            mChoreographer = Choreographer.getInstance();
+            mVSyncFrameCallback = new Choreographer.FrameCallback() {
+                @SuppressLint("NewApi")
+                @Override
+                public void doFrame(long frameTimeNanos) {
+                    VSyncListener vSyncListener;
+                    if (mListener != null && (vSyncListener=mListener.get()) != null) {
+                        try {
+                            vSyncListener.OnVSync();
+                            mChoreographer.postFrameCallback(mVSyncFrameCallback);
+                        }catch (UnsatisfiedLinkError e){
+                            if(vSyncListener instanceof WXSDKInstance){
+                                ((WXSDKInstance) vSyncListener).onRenderError(
+                                    WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+                                    Log.getStackTraceString(e));
+                            }
+                        }
+                    }
+                }
+            };
+            runnable = null;
+        } else {
+            // For API 15 or lower
+            runnable = new Runnable() {
+                @Override
+                public void run() {
+                    VSyncListener vSyncListener;
+                    if (mListener != null && (vSyncListener = mListener.get()) != null) {
+                        try {
+                            vSyncListener.OnVSync();
+                            WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(runnable, VSYNC_FRAME);
+                        }catch (UnsatisfiedLinkError e){
+                            if(vSyncListener instanceof WXSDKInstance){
+                                ((WXSDKInstance) vSyncListener).onRenderError(
+                                    WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+                                    Log.getStackTraceString(e));
+                            }
+                        }
+                    }
+                }
+            };
+            mChoreographer = null;
+            mVSyncFrameCallback = null;
+        }
+    }
+
+    @SuppressLint("NewApi")
+    public void start() {
+        if (mChoreographer != null) {
+            mChoreographer.postFrameCallback(mVSyncFrameCallback);
+        }
+        else if(runnable!=null){
+            WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(runnable, VSYNC_FRAME);
+        }
+    }
+
+    @SuppressLint("NewApi")
+    public void stop() {
+        if (mChoreographer != null) {
+            mChoreographer.removeFrameCallback(mVSyncFrameCallback);
+        }else if(runnable!=null){
+            WXSDKManager.getInstance().getWXRenderManager().removeTask(runnable);
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/ClassLoaderAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/ClassLoaderAdapter.java
new file mode 100644
index 0000000..e141025
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/ClassLoaderAdapter.java
@@ -0,0 +1,55 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import android.content.Context;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by furture on 2018/2/7.
+ * class loader adapter for load auto config class.
+ */
+public class ClassLoaderAdapter {
+
+    /**
+     * context is module class
+     * */
+    public Class<? extends WXModule> getModuleClass(String name, String className, Context context){
+        try {
+            return (Class<? extends WXModule>) context.getClassLoader().loadClass(className);
+        } catch (ClassNotFoundException e) {
+            throw  new RuntimeException(e);
+        }
+    }
+
+    /**
+     * context is instance context
+     */
+    public Class<? extends WXComponent> getComponentClass(String name, String className, WXSDKInstance instance) {
+        try {
+            return (Class<? extends WXComponent>) instance.getContext().getClassLoader().loadClass(className);
+        } catch (ClassNotFoundException e) {
+            throw  new RuntimeException(e);
+        }
+    }
+
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/DefaultUriAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/DefaultUriAdapter.java
new file mode 100644
index 0000000..70f24a2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/DefaultUriAdapter.java
@@ -0,0 +1,98 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import android.net.Uri;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKInstance;
+
+import java.util.List;
+
+
+/**
+ * Default Uri adapter. Provide basic capability to handle relative path, local file path etc.
+ * Created by sospartan on 21/11/2016.
+ */
+public class DefaultUriAdapter implements URIAdapter {
+
+
+  @NonNull
+  @Override
+  public Uri rewrite(WXSDKInstance instance, String type, Uri uri) {
+    return rewrite(instance.getBundleUrl(), type, uri);
+  }
+
+  @NonNull
+  @Override
+  public Uri rewrite(String bundleURL, String type, Uri uri) {
+    if (TextUtils.isEmpty(bundleURL)) {
+      return uri;
+    }
+
+    Uri base = Uri.parse(bundleURL);
+    Uri.Builder resultBuilder = uri.buildUpon();
+
+    if (uri.isRelative()) {
+      //When uri is empty, means use the base url instead. Web broswer behave this way.
+      if(uri.getEncodedPath().length() == 0){
+        if(IMAGE.equals(type)){
+          if(TextUtils.isEmpty(uri.toString())){
+            return uri;
+          }
+        }
+        return base;
+      } else {
+        resultBuilder = buildRelativeURI(resultBuilder, base, uri);
+        return resultBuilder.build();
+      }
+    }
+    return uri;
+  }
+
+  private Uri.Builder buildRelativeURI(Uri.Builder resultBuilder, Uri base, Uri uri) {
+    if (uri.getAuthority() != null) {
+      return resultBuilder.scheme(base.getScheme());
+    } else {
+      resultBuilder
+          .encodedAuthority(base.getEncodedAuthority())
+          .scheme(base.getScheme())
+          .path(null);
+
+      if (uri.getPath().startsWith("/")) {
+        //relative to root
+        resultBuilder.appendEncodedPath(uri.getEncodedPath().substring(1));
+      } else {
+        List<String> segments = base.getPathSegments();
+        //ignore last segment if not end with /
+        int ignoreLast = 1;
+        if (base.getPath().endsWith("/")) {
+          ignoreLast = 0;
+        }
+        for (int i = 0, len = segments.size() - ignoreLast; i < len; i++) {
+          resultBuilder.appendEncodedPath(segments.get(i));
+        }
+        resultBuilder.appendEncodedPath(uri.getEncodedPath());
+      }
+      return resultBuilder;
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/DefaultWXHttpAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/DefaultWXHttpAdapter.java
new file mode 100644
index 0000000..7f5fe12
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/DefaultWXHttpAdapter.java
@@ -0,0 +1,248 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.WXRequest;
+import org.apache.weex.common.WXResponse;
+
+import java.io.BufferedReader;
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.net.HttpURLConnection;
+import java.net.URL;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+
+public class DefaultWXHttpAdapter implements IWXHttpAdapter {
+
+  private static final IEventReporterDelegate DEFAULT_DELEGATE = new NOPEventReportDelegate();
+  private ExecutorService mExecutorService;
+
+  private void execute(Runnable runnable){
+    if(mExecutorService==null){
+      mExecutorService = Executors.newFixedThreadPool(3);
+    }
+    mExecutorService.execute(runnable);
+  }
+
+  @Override
+  public void sendRequest(final WXRequest request, final OnHttpListener listener) {
+    if (listener != null) {
+      listener.onHttpStart();
+    }
+    execute(new Runnable() {
+      @Override
+      public void run() {
+        WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(request.instanceId);
+        if (null != instance && !instance.isDestroy()){
+          instance.getApmForInstance().actionNetRequest();
+        }
+
+        boolean isNetRequestSucceed = true;
+
+        WXResponse response = new WXResponse();
+        IEventReporterDelegate reporter = getEventReporterDelegate();
+        try {
+          HttpURLConnection connection = openConnection(request, listener);
+          reporter.preConnect(connection, request.body);
+          Map<String,List<String>> headers = connection.getHeaderFields();
+          int responseCode = connection.getResponseCode();
+          if(listener != null){
+            listener.onHeadersReceived(responseCode,headers);
+          }
+          reporter.postConnect();
+
+          response.statusCode = String.valueOf(responseCode);
+          if (responseCode >= 200 && responseCode<=299) {
+            InputStream rawStream = connection.getInputStream();
+            rawStream = reporter.interpretResponseStream(rawStream);
+            response.originalData = readInputStreamAsBytes(rawStream, listener);
+          } else {
+            response.errorMsg = readInputStream(connection.getErrorStream(), listener);
+            isNetRequestSucceed = false;
+          }
+          if (listener != null) {
+            listener.onHttpFinish(response);
+          }
+        } catch (IOException|IllegalArgumentException e) {
+          isNetRequestSucceed = false;
+          e.printStackTrace();
+          response.statusCode = "-1";
+          response.errorCode="-1";
+          response.errorMsg=e.getMessage();
+          if(listener!=null){
+            listener.onHttpFinish(response);
+          }
+          if (e instanceof IOException) {
+            try {
+              reporter.httpExchangeFailed((IOException) e);
+            } catch (Throwable t) {
+              t.printStackTrace();
+            }
+          }
+        }
+        if (null != instance && !instance.isDestroy()){
+          instance.getApmForInstance().actionNetResult(isNetRequestSucceed,null);
+        }
+      }
+    });
+  }
+
+
+  /**
+   * Opens an {@link HttpURLConnection} with parameters.
+   *
+   * @param request
+   * @param listener
+   * @return an open connection
+   * @throws IOException
+   */
+  private HttpURLConnection openConnection(WXRequest request, OnHttpListener listener) throws IOException {
+    URL url = new URL(request.url);
+    HttpURLConnection connection = createConnection(url);
+    connection.setConnectTimeout(request.timeoutMs);
+    connection.setReadTimeout(request.timeoutMs);
+    connection.setUseCaches(false);
+    connection.setDoInput(true);
+
+    if (request.paramMap != null) {
+      Set<String> keySets = request.paramMap.keySet();
+      for (String key : keySets) {
+        connection.addRequestProperty(key, request.paramMap.get(key));
+      }
+    }
+
+    if ("POST".equals(request.method) || "PUT".equals(request.method) || "PATCH".equals(request.method)) {
+      connection.setRequestMethod(request.method);
+      if (request.body != null) {
+        if (listener != null) {
+          listener.onHttpUploadProgress(0);
+        }
+        connection.setDoOutput(true);
+        DataOutputStream out = new DataOutputStream(connection.getOutputStream());
+        //TODO big stream will cause OOM; Progress callback is meaningless
+        out.write(request.body.getBytes());
+        out.close();
+        if (listener != null) {
+          listener.onHttpUploadProgress(100);
+        }
+      }
+    } else if (!TextUtils.isEmpty(request.method)) {
+      connection.setRequestMethod(request.method);
+    } else {
+      connection.setRequestMethod("GET");
+    }
+
+    return connection;
+  }
+
+  private byte[] readInputStreamAsBytes(InputStream inputStream,OnHttpListener listener) throws IOException{
+    if(inputStream == null){
+      return null;
+    }
+    ByteArrayOutputStream buffer = new ByteArrayOutputStream();
+
+    int nRead;
+    int readCount = 0;
+    byte[] data = new byte[2048];
+
+    while ((nRead = inputStream.read(data, 0, data.length)) != -1) {
+      buffer.write(data, 0, nRead);
+      readCount += nRead;
+      if (listener != null) {
+        listener.onHttpResponseProgress(readCount);
+      }
+    }
+
+    buffer.flush();
+
+    return buffer.toByteArray();
+  }
+
+  private String readInputStream(InputStream inputStream, OnHttpListener listener) throws IOException {
+    if(inputStream == null){
+      return null;
+    }
+    StringBuilder builder = new StringBuilder();
+    BufferedReader localBufferedReader = new BufferedReader(new InputStreamReader(inputStream));
+    char[] data = new char[2048];
+    int len;
+    while ((len = localBufferedReader.read(data)) != -1) {
+      builder.append(data, 0, len);
+      if (listener != null) {
+        listener.onHttpResponseProgress(builder.length());
+      }
+    }
+    localBufferedReader.close();
+    return builder.toString();
+  }
+
+  /**
+   * Create an {@link HttpURLConnection} for the specified {@code url}.
+   */
+  protected HttpURLConnection createConnection(URL url) throws IOException {
+    return (HttpURLConnection) url.openConnection();
+  }
+
+  public @NonNull IEventReporterDelegate getEventReporterDelegate() {
+    return DEFAULT_DELEGATE;
+  }
+
+  public interface IEventReporterDelegate {
+    void preConnect(HttpURLConnection connection, @Nullable String body);
+    void postConnect();
+    InputStream interpretResponseStream(@Nullable InputStream inputStream);
+    void httpExchangeFailed(IOException e);
+  }
+
+  private static class NOPEventReportDelegate implements IEventReporterDelegate {
+    @Override
+    public void preConnect(HttpURLConnection connection, @Nullable String body) {
+      //do nothing
+    }
+
+    @Override
+    public void postConnect() {
+      //do nothing
+    }
+
+    @Override
+    public InputStream interpretResponseStream(@Nullable InputStream inputStream) {
+      return inputStream;
+    }
+
+    @Override
+    public void httpExchangeFailed(IOException e) {
+      //do nothing
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/DrawableStrategy.java b/android/sdk/src/main/java/org/apache/weex/adapter/DrawableStrategy.java
new file mode 100644
index 0000000..60fca0d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/DrawableStrategy.java
@@ -0,0 +1,27 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.adapter;
+
+
+public class DrawableStrategy {
+
+  public int width;
+  public int height;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/ICrashInfoReporter.java b/android/sdk/src/main/java/org/apache/weex/adapter/ICrashInfoReporter.java
new file mode 100644
index 0000000..254fa45
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/ICrashInfoReporter.java
@@ -0,0 +1,27 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+/**
+ * Created by zhengshihan on 2017/5/23.
+ */
+
+public interface ICrashInfoReporter {
+  void addCrashInfo(String key ,String value);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IDrawableLoader.java b/android/sdk/src/main/java/org/apache/weex/adapter/IDrawableLoader.java
new file mode 100644
index 0000000..c71351d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IDrawableLoader.java
@@ -0,0 +1,41 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.adapter;
+
+import android.graphics.drawable.Drawable;
+import android.support.annotation.Nullable;
+
+public interface IDrawableLoader {
+
+  interface DrawableTarget {
+    void setDrawable(@Nullable Drawable drawable, boolean resetBounds);
+  }
+
+  interface StaticTarget extends DrawableTarget{
+    void setDrawable(@Nullable Drawable drawable, boolean resetBounds);
+  }
+
+  interface AnimatedTarget extends DrawableTarget{
+    void setAnimatedDrawable(@Nullable Drawable drawable);
+  }
+
+  void setDrawable(String url, DrawableTarget drawableTarget, DrawableStrategy drawableStrategy);
+}
+
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/ITracingAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/ITracingAdapter.java
new file mode 100644
index 0000000..e0ce304
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/ITracingAdapter.java
@@ -0,0 +1,31 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import org.apache.weex.tracing.WXTracing;
+
+/**
+ * Created by moxun on 2017/7/6.
+ */
+
+public interface ITracingAdapter {
+  void enable();
+  void disable();
+  void submitTracingEvent(WXTracing.TraceEvent event);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXAccessibilityRoleAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXAccessibilityRoleAdapter.java
new file mode 100644
index 0000000..7682339
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXAccessibilityRoleAdapter.java
@@ -0,0 +1,27 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+/**
+ * Created by moxun on 2017/11/13.
+ */
+
+public interface IWXAccessibilityRoleAdapter {
+  String getRole(String key);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXConfigAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXConfigAdapter.java
new file mode 100644
index 0000000..17791e3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXConfigAdapter.java
@@ -0,0 +1,29 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+/**
+ * @author zhongcang
+ * @date 2019/3/20
+ */
+public interface IWXConfigAdapter {
+    String getConfig(String nameSpace,String key,String defaultValue);
+    String getConfigWhenInit(String nameSpace,String key,String defaultValue);
+    boolean checkMode(String name);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXHttpAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXHttpAdapter.java
new file mode 100644
index 0000000..0da8e24
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXHttpAdapter.java
@@ -0,0 +1,68 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+
+import org.apache.weex.common.WXRequest;
+import org.apache.weex.common.WXResponse;
+
+import java.util.List;
+import java.util.Map;
+
+public interface IWXHttpAdapter {
+
+  /**
+   * http request method
+   *
+   * @param request weex assemble request
+   * @param listener http response notify
+   */
+  void sendRequest(WXRequest request, OnHttpListener listener);
+
+  interface OnHttpListener {
+
+    /**
+     * start request
+     */
+    void onHttpStart();
+
+    /**
+     * headers received
+     */
+    void onHeadersReceived(int statusCode,Map<String,List<String>> headers);
+
+    /**
+     * post progress
+     * @param uploadProgress
+     */
+    void onHttpUploadProgress(int uploadProgress);
+
+    /**
+     * response loaded length (bytes), full length should read from headers (content-length)
+     * @param loadedLength
+     */
+    void onHttpResponseProgress(int loadedLength);
+
+    /**
+     * http response finish
+     * @param response
+     */
+    void onHttpFinish(WXResponse response);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXImgLoaderAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXImgLoaderAdapter.java
new file mode 100644
index 0000000..ffbad52
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXImgLoaderAdapter.java
@@ -0,0 +1,32 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import android.widget.ImageView;
+
+import org.apache.weex.common.WXImageStrategy;
+import org.apache.weex.dom.WXImageQuality;
+
+/**
+ * Interface for ImageLoader. This interface works as an adapter for various image library.
+ */
+public interface IWXImgLoaderAdapter {
+
+  void setImage(String url, ImageView view, WXImageQuality quality, WXImageStrategy strategy);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXJSExceptionAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXJSExceptionAdapter.java
new file mode 100644
index 0000000..0bedb93
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXJSExceptionAdapter.java
@@ -0,0 +1,32 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import org.apache.weex.common.WXJSExceptionInfo;
+
+public interface IWXJSExceptionAdapter {
+
+  /**
+   * report js exception
+   *
+   * @param exception {@link WXJSExceptionInfo}
+   */
+
+  void onJSException(WXJSExceptionInfo exception);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXJsFileLoaderAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXJsFileLoaderAdapter.java
new file mode 100644
index 0000000..4af0623
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXJsFileLoaderAdapter.java
@@ -0,0 +1,25 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+public interface IWXJsFileLoaderAdapter {
+    String loadRaxApi();
+    String loadJsFramework();
+    String loadJsFrameworkForSandBox();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXJscProcessManager.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXJscProcessManager.java
new file mode 100644
index 0000000..1bce4a8
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXJscProcessManager.java
@@ -0,0 +1,29 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import org.apache.weex.WXSDKInstance;
+
+public interface IWXJscProcessManager {
+    boolean enableBackupThread();
+    boolean enableBackUpThreadCache();
+    boolean shouldReboot();
+    long rebootTimeout();
+    boolean withException(WXSDKInstance instance);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXSoLoaderAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXSoLoaderAdapter.java
new file mode 100644
index 0000000..c652566
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXSoLoaderAdapter.java
@@ -0,0 +1,50 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+/**
+ * Interface for loading library.
+ */
+public interface IWXSoLoaderAdapter {
+  /**
+   * A method <code>doLoadLibrary</code> that
+   * helps embedders to load a shared library with a short name.
+   * <p>
+   *
+   * Embedders would have a chance to take charge of library loading,
+   * they could load libraries with different class loaders,
+   * or load libraries from specified library pathes.
+   *
+   * @param shortName the name of the library
+   */
+  void doLoadLibrary(String shortName);
+
+  /**
+   * A method <code>doLoad</code> that
+   * helps embedders to load a shared library.
+   * <p>
+   *
+   * Embedders would have a chance to take charge of library loading,
+   * they could load libraries with different class loaders,
+   * or load libraries from specified library pathes.
+   *
+   * @param name the file to load.
+   */
+  void doLoad(String name);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/IWXUserTrackAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/IWXUserTrackAdapter.java
new file mode 100644
index 0000000..fcdd711
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/IWXUserTrackAdapter.java
@@ -0,0 +1,56 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import android.content.Context;
+
+import org.apache.weex.common.WXPerformance;
+
+import java.io.Serializable;
+import java.util.Map;
+
+/**
+ * Interface for commit log info. This interface works as an adapter for various log library.
+ */
+public interface IWXUserTrackAdapter {
+
+  String MODULE_NAME = "weex";
+
+  //Performance
+  String LOAD = "load";
+
+  //Alarm
+  String JS_FRAMEWORK = "jsFramework";
+  String JS_DOWNLOAD = "jsDownload";
+  String DOM_MODULE = "domModule";
+  String JS_BRIDGE = "jsBridge";
+  String STREAM_MODULE = "streamModule";
+  String INVOKE_MODULE = "invokeModule";
+  String INIT_FRAMEWORK = "initFramework";
+  String COUNTER = "counter";
+
+  /**
+   * monitor keys
+   */
+  String MONITOR_ERROR_CODE = "errCode";
+  String MONITOR_ARG = "arg";
+  String MONITOR_ERROR_MSG = "errMsg";
+
+  void commit(Context context, String eventId, String type, WXPerformance perf, Map<String, Serializable> params);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/adapter/URIAdapter.java b/android/sdk/src/main/java/org/apache/weex/adapter/URIAdapter.java
new file mode 100644
index 0000000..264dc17
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/adapter/URIAdapter.java
@@ -0,0 +1,80 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.adapter;
+
+import android.net.Uri;
+import android.support.annotation.NonNull;
+
+import org.apache.weex.WXSDKInstance;
+
+/**
+ * Created by sospartan on 15/11/2016.
+ */
+
+public interface URIAdapter {
+
+  /**
+   * Stream request url.
+   */
+  String REQUEST = "request";
+
+  /**
+   * URI for image src.
+   */
+  String IMAGE = "image";
+
+  /**
+   * Font file URI for text @font-face .
+   */
+  String FONT = "font";
+
+  /**
+   * Video URI.
+   */
+  String VIDEO = "video";
+
+  /**
+   * URI for a 'href' attribute.
+   */
+  String LINK = "link";
+
+  /**
+   * Bundle URI for Weex instance.
+   */
+  String BUNDLE = "bundle";
+
+  /**
+   * Web page src
+   */
+  String WEB = "web";
+
+  /**
+   * Unknown URIs.
+   */
+  String OTHERS = "others";
+
+  /**
+   *
+   * @param type URI type, see {@link #IMAGE}/{@link #LINK}/{@link #FONT}/{@link #BUNDLE}/{@link #VIDEO}/{@link #OTHERS}
+   * @param uri
+   * @return
+   */
+  @NonNull Uri rewrite(WXSDKInstance instance, String type, Uri uri);
+  @NonNull Uri rewrite(String bundleURL, String type, Uri uri);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/annotation/Component.java b/android/sdk/src/main/java/org/apache/weex/annotation/Component.java
new file mode 100644
index 0000000..7174925
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/annotation/Component.java
@@ -0,0 +1,33 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.annotation;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * Created by sospartan on 6/12/16.
+ */
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.TYPE)
+public @interface Component {
+  boolean lazyload() default true;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/annotation/JSMethod.java b/android/sdk/src/main/java/org/apache/weex/annotation/JSMethod.java
new file mode 100644
index 0000000..7f8ce5b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/annotation/JSMethod.java
@@ -0,0 +1,39 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.annotation;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Inherited;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * Created by sospartan on 19/10/2016.
+ */
+@Retention(RetentionPolicy.RUNTIME)
+@Inherited
+@Target(ElementType.METHOD)
+public @interface JSMethod {
+  boolean uiThread() default true;
+
+  String alias() default NOT_SET;
+
+  String NOT_SET = "_";
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/clipboard/IWXClipboard.java b/android/sdk/src/main/java/org/apache/weex/appfram/clipboard/IWXClipboard.java
new file mode 100644
index 0000000..1c09643
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/clipboard/IWXClipboard.java
@@ -0,0 +1,31 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.clipboard;
+
+import android.support.annotation.Nullable;
+
+import org.apache.weex.bridge.JSCallback;
+
+/**
+ * Created by yiyuan.zhangyy(xingjiu) <br/>
+ */
+interface IWXClipboard {
+    public void setString(String text);
+    public void getString(@Nullable JSCallback callback);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/clipboard/WXClipboardModule.java b/android/sdk/src/main/java/org/apache/weex/appfram/clipboard/WXClipboardModule.java
new file mode 100644
index 0000000..b38f9f0
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/clipboard/WXClipboardModule.java
@@ -0,0 +1,148 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.clipboard;
+
+import android.content.ClipData;
+import android.content.ClipboardManager;
+import android.content.Context;
+import android.content.Intent;
+import android.content.res.AssetFileDescriptor;
+import android.net.Uri;
+import android.support.annotation.Nullable;
+
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.IOException;
+import java.io.InputStreamReader;
+import java.util.HashMap;
+import java.util.Map;
+
+
+public class WXClipboardModule extends WXModule implements IWXClipboard {
+
+    private final String CLIP_KEY = "WEEX_CLIP_KEY_MAIN";
+
+    private static final String RESULT = "result";
+    private static final String DATA = "data";
+
+    private static final String RESULT_OK = "success";
+    private static final String RESULT_FAILED = "failed";
+
+    @Override
+    @JSMethod
+    public void setString(String text) {
+        if(null == text) {
+            return;
+        }
+
+        Context context = mWXSDKInstance.getContext();
+        ClipboardManager clipboard = (ClipboardManager) context.getSystemService(context.CLIPBOARD_SERVICE);
+        ClipData clip = ClipData.newPlainText(CLIP_KEY, text);
+        clipboard.setPrimaryClip(clip);
+    }
+
+    @Override
+    @JSMethod
+    public void getString(@Nullable JSCallback callback) {
+        Context context = mWXSDKInstance.getContext();
+        ClipboardManager clipboard = (ClipboardManager) context.getSystemService(Context.CLIPBOARD_SERVICE);
+
+        Map<String, Object> map = new HashMap<>(2);
+        ClipData clip = clipboard.getPrimaryClip();
+        if (clip != null && clip.getItemCount() > 0) {
+            ClipData.Item item = clip.getItemAt(0);
+            CharSequence text = coerceToText(context, item);
+
+            map.put(RESULT, text != null ? RESULT_OK : RESULT_FAILED);
+            map.put(DATA, text != null ? text : "");
+        } else {
+            map.put(RESULT, RESULT_FAILED);
+            map.put(DATA, "");
+        }
+
+        if (null != callback) {
+            callback.invoke(map);
+        }
+    }
+
+    @Nullable
+    private CharSequence coerceToText(Context context, ClipData.Item item) {
+        // Condition 1. just a simple text
+        CharSequence text = item.getText();
+        if (text != null) {
+            return text;
+        }
+
+        // Condition 2. a URI value
+        Uri uri = item.getUri();
+        if (uri != null) {
+            InputStreamReader reader = null;
+            FileInputStream stream = null;
+            try {
+                AssetFileDescriptor assetFileDescriptor = context.getContentResolver().openTypedAssetFileDescriptor(uri, "text/*", null);
+                stream = assetFileDescriptor.createInputStream();
+                reader = new InputStreamReader(stream, "UTF-8");
+
+                StringBuilder builder = new StringBuilder(128);
+                char[] buffer = new char[8192];
+                int len;
+                while ((len = reader.read(buffer)) > 0) {
+                    builder.append(buffer, 0, len);
+                }
+                return builder.toString();
+
+            } catch (FileNotFoundException e) {
+                //  ignore.
+            } catch (IOException e) {
+                WXLogUtils.w("ClippedData Failure loading text.", e);
+            } finally {
+                if (reader != null) {
+                    try {
+                        reader.close();
+                    } catch (IOException e) {
+                        // ignore
+                    }
+                }
+                if (stream != null) {
+                    try {
+                        stream.close();
+                    } catch (IOException e) {
+                        // ignore
+                    }
+                }
+            }
+
+            return uri.toString();
+        }
+
+        // Condition 3.  an intent.
+        Intent intent = item.getIntent();
+        if (intent != null) {
+            return intent.toUri(Intent.URI_INTENT_SCHEME);
+        }
+
+        // else case
+        return null;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/navigator/IActivityNavBarSetter.java b/android/sdk/src/main/java/org/apache/weex/appfram/navigator/IActivityNavBarSetter.java
new file mode 100644
index 0000000..6f97e84
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/navigator/IActivityNavBarSetter.java
@@ -0,0 +1,44 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.navigator;
+
+/**
+ *  Define the  NavBarSetter api of the Activity
+ */
+public interface IActivityNavBarSetter {
+
+  boolean push(String param);
+
+  boolean pop(String param);
+
+  boolean setNavBarRightItem(String param);
+
+  boolean clearNavBarRightItem(String param);
+
+  boolean setNavBarLeftItem(String param);
+
+  boolean clearNavBarLeftItem(String param);
+
+  boolean setNavBarMoreItem(String param);
+
+  boolean clearNavBarMoreItem(String param);
+
+  boolean setNavBarTitle(String param);
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/navigator/INavigator.java b/android/sdk/src/main/java/org/apache/weex/appfram/navigator/INavigator.java
new file mode 100644
index 0000000..60ddbb4
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/navigator/INavigator.java
@@ -0,0 +1,31 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.appfram.navigator;
+import android.app.Activity;
+
+/**
+ * Created by zhengshihan on 2018/8/9.
+ */
+
+public interface INavigator {
+
+  boolean push(Activity activity,String param);
+
+  boolean pop(Activity activity,String param);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/navigator/WXNavigatorModule.java b/android/sdk/src/main/java/org/apache/weex/appfram/navigator/WXNavigatorModule.java
new file mode 100644
index 0000000..674c89d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/navigator/WXNavigatorModule.java
@@ -0,0 +1,365 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.navigator;
+
+import android.app.Activity;
+import android.content.Context;
+import android.content.Intent;
+import android.net.Uri;
+import android.support.v7.app.AppCompatActivity;
+import android.text.TextUtils;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONException;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKEngine;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.utils.WXLogUtils;
+
+
+public class WXNavigatorModule extends WXModule {
+
+    public static final String MSG_SUCCESS = "WX_SUCCESS";
+    public static final String MSG_FAILED = "WX_FAILED";
+    public static final String MSG_PARAM_ERR = "WX_PARAM_ERR";
+
+    public static final String CALLBACK_RESULT = "result";
+    public static final String CALLBACK_MESSAGE = "message";
+
+    private final static String INSTANCE_ID = "instanceId";
+    private final static String TAG = "Navigator";
+    private final static String WEEX = "com.taobao.android.intent.category.WEEX";
+    private final static String URL = "url";
+
+    @JSMethod(uiThread = true)
+    public void open(JSONObject options, JSCallback success, JSCallback failure) {
+        if (options != null) {
+            String url = options.getString(Constants.Value.URL);
+            JSCallback callback = success;
+            JSONObject result = new JSONObject();
+            if (!TextUtils.isEmpty(url)) {
+                Uri rawUri = Uri.parse(url);
+                String scheme = rawUri.getScheme();
+                if (TextUtils.isEmpty(scheme) || Constants.Scheme.HTTP.equalsIgnoreCase(scheme) || Constants.Scheme.HTTPS.equalsIgnoreCase(scheme)) {
+                    this.push(options.toJSONString(), success);
+                } else {
+                    try {
+                        Intent intent = new Intent(Intent.ACTION_VIEW, rawUri);
+                        mWXSDKInstance.getContext().startActivity(intent);
+                        result.put(CALLBACK_RESULT, MSG_SUCCESS);
+                    } catch (Throwable e) {
+                        e.printStackTrace();
+                        result.put(CALLBACK_RESULT, MSG_FAILED);
+                        result.put(CALLBACK_MESSAGE, "Open page failed.");
+                        callback = failure;
+                    }
+                }
+            } else {
+                result.put(CALLBACK_RESULT, MSG_PARAM_ERR);
+                result.put(CALLBACK_MESSAGE, "The URL parameter is empty.");
+                callback = failure;
+            }
+
+            if(callback != null){
+                callback.invoke(result);
+            }
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void close(JSONObject options, JSCallback success, JSCallback failure) {
+        JSONObject result = new JSONObject();
+        JSCallback callback = null;
+        if (mWXSDKInstance.getContext() instanceof Activity) {
+            callback = success;
+            ((Activity) mWXSDKInstance.getContext()).finish();
+        } else {
+            result.put(CALLBACK_RESULT, MSG_FAILED);
+            result.put(CALLBACK_MESSAGE, "Close page failed.");
+            callback = failure;
+        }
+        if (callback != null) {
+            callback.invoke(result);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void push(String param, JSCallback callback) {
+
+        if (!TextUtils.isEmpty(param)) {
+            if (WXSDKEngine.getActivityNavBarSetter() != null) {
+                if (WXSDKEngine.getActivityNavBarSetter().push(param)) {
+                    if (callback != null) {
+                        callback.invoke(MSG_SUCCESS);
+                    }
+                    return;
+                }
+            }
+
+            if (mWXSDKInstance.getContext() instanceof Activity){
+                Activity activity = (Activity)mWXSDKInstance.getContext();
+
+                if (WXSDKEngine.getNavigator()!= null
+                    && WXSDKEngine.getNavigator().push(activity,param)) {
+                    if (callback != null) {
+                        callback.invoke(MSG_SUCCESS);
+                    }
+                    return;
+                }
+            }
+
+            try {
+                JSONObject jsonObject = JSON.parseObject(param);
+                String url = jsonObject.getString(URL);
+                if (!TextUtils.isEmpty(url)) {
+                    Uri rawUri = Uri.parse(url);
+                    String scheme = rawUri.getScheme();
+                    Uri.Builder builder = rawUri.buildUpon();
+                    if (TextUtils.isEmpty(scheme)) {
+                        builder.scheme(Constants.Scheme.HTTP);
+                    }
+                    Intent intent = new Intent(Intent.ACTION_VIEW, builder.build());
+                    intent.addCategory(WEEX);
+                    intent.putExtra(INSTANCE_ID, mWXSDKInstance.getInstanceId());
+                    mWXSDKInstance.getContext().startActivity(intent);
+                    if (callback != null) {
+                        callback.invoke(MSG_SUCCESS);
+                    }
+                }
+            } catch (Exception e) {
+                WXLogUtils.eTag(TAG, e);
+                if (callback != null) {
+                    callback.invoke(MSG_FAILED);
+                }
+            }
+        } else if (callback != null) {
+            callback.invoke(MSG_FAILED);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void pop(String param, JSCallback callback) {
+
+        if (WXSDKEngine.getActivityNavBarSetter() != null) {
+            if (WXSDKEngine.getActivityNavBarSetter().pop(param)) {
+                if (callback != null) {
+                    callback.invoke(MSG_SUCCESS);
+                }
+                return;
+            }
+        }
+
+        if (mWXSDKInstance.getContext() instanceof Activity) {
+            Activity activity = (Activity) mWXSDKInstance.getContext();
+            if (WXSDKEngine.getNavigator() != null) {
+                if (WXSDKEngine.getNavigator().pop(activity, param)) {
+                    if (callback != null) {
+                        callback.invoke(MSG_SUCCESS);
+                    }
+                    return;
+                }
+            }
+
+            if (callback != null) {
+                callback.invoke(MSG_SUCCESS);
+            }
+            ((Activity) mWXSDKInstance.getContext()).finish();
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void setNavBarRightItem(String param, JSCallback callback) {
+        if (!TextUtils.isEmpty(param)) {
+            if (WXSDKEngine.getActivityNavBarSetter() != null) {
+                if (WXSDKEngine.getActivityNavBarSetter().setNavBarRightItem(param)) {
+                    if (callback != null) {
+                        callback.invoke(MSG_SUCCESS);
+                    }
+                    return;
+                }
+            }
+        }
+
+        if (callback != null) {
+            callback.invoke(MSG_FAILED);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void clearNavBarRightItem(String param, JSCallback callback) {
+        if (WXSDKEngine.getActivityNavBarSetter() != null) {
+            if (WXSDKEngine.getActivityNavBarSetter().clearNavBarRightItem(param)) {
+                if (callback != null) {
+                    callback.invoke(MSG_SUCCESS);
+                }
+                return;
+            }
+        }
+        if (callback != null) {
+            callback.invoke(MSG_FAILED);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void setNavBarLeftItem(String param, JSCallback callback) {
+        if (!TextUtils.isEmpty(param)) {
+            if (WXSDKEngine.getActivityNavBarSetter() != null) {
+                if (WXSDKEngine.getActivityNavBarSetter().setNavBarLeftItem(param)) {
+                    if (callback != null) {
+                        callback.invoke(MSG_SUCCESS);
+                    }
+                    return;
+                }
+            }
+        }
+
+        if (callback != null) {
+            callback.invoke(MSG_FAILED);
+        }
+
+    }
+
+    @JSMethod(uiThread = true)
+    public void clearNavBarLeftItem(String param, JSCallback callback) {
+        if (WXSDKEngine.getActivityNavBarSetter() != null) {
+            if (WXSDKEngine.getActivityNavBarSetter().clearNavBarLeftItem(param)) {
+                if (callback != null) {
+                    callback.invoke(MSG_SUCCESS);
+                }
+                return;
+            }
+        }
+
+        if (callback != null) {
+            callback.invoke(MSG_FAILED);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void setNavBarMoreItem(String param, JSCallback callback) {
+        if (!TextUtils.isEmpty(param)) {
+            if (WXSDKEngine.getActivityNavBarSetter() != null) {
+                if (WXSDKEngine.getActivityNavBarSetter().setNavBarMoreItem(param)) {
+                    if (callback != null) {
+                        callback.invoke(MSG_SUCCESS);
+                    }
+                    return;
+                }
+            }
+        }
+
+        if (callback != null) {
+            callback.invoke(MSG_FAILED);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void clearNavBarMoreItem(String param, JSCallback callback) {
+        if (WXSDKEngine.getActivityNavBarSetter() != null) {
+            if (WXSDKEngine.getActivityNavBarSetter().clearNavBarMoreItem(param)) {
+                if (callback != null) {
+                    callback.invoke(MSG_SUCCESS);
+                }
+                return;
+            }
+        }
+
+        if (callback != null) {
+            callback.invoke(MSG_FAILED);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void setNavBarTitle(String param, JSCallback callback) {
+        if (!TextUtils.isEmpty(param)) {
+            if (WXSDKEngine.getActivityNavBarSetter() != null) {
+                if (WXSDKEngine.getActivityNavBarSetter().setNavBarTitle(param)) {
+                    if (callback != null) {
+                        callback.invoke(MSG_SUCCESS);
+                    }
+                    return;
+                }
+            }
+        }
+        if (callback != null) {
+            callback.invoke(MSG_FAILED);
+        }
+    }
+
+    @JSMethod
+    public void setNavBarHidden(String param, final String callback) {
+        String message = MSG_FAILED;
+        try {
+            JSONObject jsObj = JSON.parseObject(param);
+            int visibility = jsObj.getInteger(Constants.Name.NAV_BAR_VISIBILITY);
+            boolean success = changeVisibilityOfActionBar(mWXSDKInstance.getContext(), visibility);
+            if (success) {
+                message = MSG_SUCCESS;
+            }
+        } catch (JSONException e) {
+            WXLogUtils.e(TAG, WXLogUtils.getStackTrace(e));
+        }
+        WXBridgeManager.getInstance().callback(mWXSDKInstance.getInstanceId(), callback, message);
+    }
+
+    private boolean changeVisibilityOfActionBar(Context context, int visibility) {
+        boolean result = false;
+        boolean hasAppCompatActivity = false;
+        try {
+            Class.forName("android.support.v7.app.AppCompatActivity");
+            hasAppCompatActivity = true;
+        } catch (ClassNotFoundException e) {
+            e.printStackTrace();
+        }
+        if (hasAppCompatActivity && mWXSDKInstance.getContext() instanceof AppCompatActivity) {
+            android.support.v7.app.ActionBar actionbar = ((AppCompatActivity) mWXSDKInstance.getContext()).getSupportActionBar();
+            if (actionbar != null) {
+                switch (visibility) {
+                    case Constants.Value.NAV_BAR_HIDDEN:
+                        actionbar.hide();
+                        result = true;
+                        break;
+                    case Constants.Value.NAV_BAR_SHOWN:
+                        actionbar.show();
+                        result = true;
+                        break;
+                }
+            }
+        } else if (mWXSDKInstance.getContext() instanceof Activity) {
+            android.app.ActionBar actionbar = ((Activity) mWXSDKInstance.getContext()).getActionBar();
+            if (actionbar != null) {
+                switch (visibility) {
+                    case Constants.Value.NAV_BAR_HIDDEN:
+                        actionbar.hide();
+                        result = true;
+                        break;
+                    case Constants.Value.NAV_BAR_SHOWN:
+                        actionbar.show();
+                        result = true;
+                        break;
+                }
+            }
+        }
+        return result;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/pickers/DatePickerImpl.java b/android/sdk/src/main/java/org/apache/weex/appfram/pickers/DatePickerImpl.java
new file mode 100644
index 0000000..9739bd6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/pickers/DatePickerImpl.java
@@ -0,0 +1,198 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.pickers;
+
+import android.app.AlertDialog;
+import android.app.DatePickerDialog;
+import android.app.TimePickerDialog;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+import android.widget.Button;
+import android.widget.DatePicker;
+import android.widget.TimePicker;
+
+import org.apache.weex.common.WXThread;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.text.ParseException;
+import java.text.SimpleDateFormat;
+import java.util.Calendar;
+import java.util.Date;
+import java.util.Locale;
+import java.util.Map;
+
+/**
+ * Created by moxun on 16/11/23.
+ */
+
+public class DatePickerImpl {
+
+    private static final int DEFAULT_START_YEAR = 1900;
+    private static final int DEFAULT_END_YEAR = 2100;
+
+    private static SimpleDateFormat timeFormatter;
+    private static SimpleDateFormat dateFormatter;
+
+    public static void pickDate(@NonNull Context context, String value, String max, String min, @NonNull final OnPickListener listener, @Nullable Map<String, Object> extras) {
+        Calendar calendar = Calendar.getInstance();
+        calendar.setTime(parseDate(value));
+        final DatePickerDialog dialog = new DatePickerDialog(
+                context,
+                new DatePickerDialog.OnDateSetListener() {
+                    @Override
+                    public void onDateSet(DatePicker view, int year, int monthOfYear, int dayOfMonth) {
+                        int realMonth = monthOfYear + 1;
+                        String realMonthString = realMonth < 10 ? "0" + realMonth : String.valueOf(realMonth);
+                        String realDayString = dayOfMonth < 10 ? "0" + dayOfMonth : String.valueOf(dayOfMonth);
+                        String result = year + "-" + realMonthString + "-" + realDayString;
+                        listener.onPick(true, result);
+                    }
+                },
+                calendar.get(Calendar.YEAR),
+                calendar.get(Calendar.MONTH),
+                calendar.get(Calendar.DAY_OF_MONTH)
+        );
+
+        final DatePicker datePicker = dialog.getDatePicker();
+
+        final Calendar defaultMinDate = Calendar.getInstance(Locale.getDefault());
+        final Calendar defaultMaxDate = Calendar.getInstance(Locale.getDefault());
+
+        defaultMinDate.set(DEFAULT_START_YEAR, Calendar.JANUARY, 1);
+        defaultMaxDate.set(DEFAULT_END_YEAR, Calendar.DECEMBER, 31);
+
+        if (!TextUtils.isEmpty(min)) {
+            long minDate = parseDate(min).getTime();
+            if (datePicker.getMaxDate() >= minDate) {
+                datePicker.setMinDate(parseDate(min).getTime());
+            } else {
+                datePicker.setMinDate(defaultMinDate.getTimeInMillis());
+                datePicker.setMaxDate(defaultMaxDate.getTimeInMillis());
+            }
+        }
+        if (!TextUtils.isEmpty(max)) {
+            long maxDate = parseDate(max).getTime();
+            if (datePicker.getMinDate() <= maxDate) {
+                datePicker.setMaxDate(parseDate(max).getTime());
+            } else {
+                datePicker.setMinDate(defaultMinDate.getTimeInMillis());
+                datePicker.setMaxDate(defaultMaxDate.getTimeInMillis());
+            }
+        }
+
+        dialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
+            @Override
+            public void onCancel(DialogInterface dialog) {
+                listener.onPick(false, null);
+            }
+        });
+
+        setButtonText(dialog, DialogInterface.BUTTON_NEGATIVE, String.valueOf(extras != null ? extras.get("cancelTitle") : null));
+        setButtonText(dialog, DialogInterface.BUTTON_POSITIVE, String.valueOf(extras != null ? extras.get("confirmTitle") : null));
+
+        dialog.show();
+    }
+
+    public static void pickTime(@NonNull Context context, String value, @NonNull final OnPickListener listener, @Nullable Map<String, Object> extras) {
+        Calendar calendar = Calendar.getInstance();
+        calendar.setTime(parseTime(value));
+        TimePickerDialog dialog = new TimePickerDialog(
+                context,
+                new TimePickerDialog.OnTimeSetListener() {
+                    @Override
+                    public void onTimeSet(TimePicker view, int hourOfDay, int minute) {
+                        String h = hourOfDay < 10 ? "0" + hourOfDay : String.valueOf(hourOfDay);
+                        String m = minute < 10 ? "0" + minute : String.valueOf(minute);
+                        String result = h + ":" + m;
+                        listener.onPick(true, result);
+                    }
+                },
+                calendar.get(Calendar.HOUR_OF_DAY),
+                calendar.get(Calendar.MINUTE),
+                false
+        );
+
+        dialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
+            @Override
+            public void onCancel(DialogInterface dialog) {
+                listener.onPick(false, null);
+            }
+        });
+
+        setButtonText(dialog, DialogInterface.BUTTON_NEGATIVE, String.valueOf(extras != null ? extras.get("cancelTitle") : null));
+        setButtonText(dialog, DialogInterface.BUTTON_POSITIVE, String.valueOf(extras != null ? extras.get("confirmTitle") : null));
+
+        dialog.show();
+    }
+
+    public interface OnPickListener {
+        void onPick(boolean set, @Nullable String result);
+    }
+
+    private static Date parseDate(String s) {
+        if (dateFormatter == null) {
+            dateFormatter = new SimpleDateFormat("yyyy-MM-dd", Locale.getDefault());
+        }
+
+        try {
+            return dateFormatter.parse(s);
+        } catch (ParseException e) {
+            //don't worry
+            WXLogUtils.w("[DatePickerImpl] " + e.toString());
+        }
+        return new Date();
+    }
+
+    private static Date parseTime(String s) {
+        if (timeFormatter == null) {
+            timeFormatter = new SimpleDateFormat("HH:mm", Locale.getDefault());
+        }
+
+        try {
+            return timeFormatter.parse(s);
+        } catch (ParseException e) {
+            //don't worry
+            WXLogUtils.w("[DatePickerImpl] " + e.toString());
+        }
+        return new Date();
+    }
+
+    private static void setButtonText(final AlertDialog dialog, final int which, final CharSequence text) {
+        if (TextUtils.isEmpty(text) || "null".equals(text)) {
+            return;
+        }
+        try {
+            dialog.getWindow().getDecorView().post(WXThread.secure(new Runnable() {
+                @Override
+                public void run() {
+                    Button button = dialog.getButton(which);
+                    if (button != null) {
+                        button.setAllCaps(false);
+                        button.setText(text);
+                    }
+                }
+            }));
+        } catch (Throwable t) {
+            t.printStackTrace();
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/pickers/WXPickersModule.java b/android/sdk/src/main/java/org/apache/weex/appfram/pickers/WXPickersModule.java
new file mode 100644
index 0000000..5b312af
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/pickers/WXPickersModule.java
@@ -0,0 +1,310 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.pickers;
+
+import android.content.Context;
+import android.content.DialogInterface;
+import android.graphics.Color;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v7.app.AlertDialog;
+import android.util.TypedValue;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.AdapterView;
+import android.widget.ArrayAdapter;
+import android.widget.Button;
+import android.widget.Checkable;
+import android.widget.ListView;
+import android.widget.TextView;
+
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Created by moxun on 16/10/27.
+ */
+
+public class WXPickersModule extends WXModule {
+
+    private static final String SUCCESS = "success";
+    private static final String CANCEL = "cancel";
+    private static final String ERROR = "error";
+
+    private static final String RESULT = "result";
+    private static final String DATA = "data";
+
+    private static final String KEY_VALUE = "value";
+    private static final String KEY_INDEX = "index";
+    private static final String KEY_TITLE = "title";
+    private static final String KEY_MAX = "max";
+    private static final String KEY_MIN = "min";
+    private static final String KEY_ITEMS = "items";
+
+    private static final String KEY_TITLE_COLOR = "titleColor";
+    private static final String KEY_CANCEL_TITLE_COLOR = "cancelTitleColor";
+    private static final String KEY_CONFIRM_TITLE = "confirmTitle";
+    private static final String KEY_CANCEL_TITLE = "cancelTitle";
+    private static final String KEY_CONFIRM_TITLE_COLOR = "confirmTitleColor";
+    private static final String KEY_TITLE_BACKGROUND_COLOR = "titleBackgroundColor";
+    private static final String KEY_TEXT_COLOR = "textColor";
+    private static final String KEY_SELECTION_COLOR = "selectionColor";
+
+    private int selected;
+
+    @JSMethod
+    public void pick(Map<String, Object> options, JSCallback callback) {
+        List<String> items = safeConvert(getOption(options, KEY_ITEMS, new ArrayList<String>()));
+        try {
+            performSinglePick(items, options, callback);
+        } catch (Throwable throwable) {
+            throwable.printStackTrace();
+        }
+    }
+
+    @JSMethod
+    public void pickDate(Map<String, Object> options, JSCallback callback) {
+        performPickDate(options, callback);
+    }
+
+    @JSMethod
+    public void pickTime(Map<String, Object> options, JSCallback callback) {
+        performPickTime(options, callback);
+    }
+
+    private List<String> safeConvert(List src) {
+        List<String> result = new ArrayList<>(src.size());
+        for (Object obj : src) {
+            result.add(String.valueOf(obj));
+        }
+        return result;
+    }
+
+    private <T> T getOption(Map<String, Object> options, String key, T defValue) {
+        Object value = options.get(key);
+        if (value == null) {
+            return defValue;
+        } else {
+            try {
+                return (T) value;
+            } catch (Exception e) {
+                e.printStackTrace();
+                return defValue;
+            }
+        }
+    }
+
+    private int getColor(Map<String, Object> options, String key, int defValue) {
+        Object value = getOption(options, key, null);
+        if (value == null) {
+            return defValue;
+        }
+        return WXResourceUtils.getColor(value.toString(), defValue);
+    }
+
+    private void performPickTime(Map<String, Object> options, final JSCallback callback) {
+        String value = getOption(options, KEY_VALUE, "");
+        DatePickerImpl.pickTime(
+                mWXSDKInstance.getContext(),
+                value,
+                new DatePickerImpl.OnPickListener() {
+                    @Override
+                    public void onPick(boolean set, @Nullable String result) {
+                        if (set) {
+                            Map<String, Object> ret = new HashMap<>(2);
+                            ret.put(RESULT, SUCCESS);
+                            ret.put(DATA, result);
+                            callback.invoke(ret);
+                        } else {
+                            Map<String, Object> ret = new HashMap<>(2);
+                            ret.put(RESULT, CANCEL);
+                            ret.put(DATA, null);
+                            callback.invoke(ret);
+                        }
+                    }
+                },
+                options);
+    }
+
+    private void performPickDate(Map<String, Object> options, final JSCallback callback) {
+        String value = getOption(options, KEY_VALUE, "");
+        String max = getOption(options, KEY_MAX, "");
+        String min = getOption(options, KEY_MIN, "");
+        DatePickerImpl.pickDate(
+                mWXSDKInstance.getContext(),
+                value,
+                max,
+                min,
+                new DatePickerImpl.OnPickListener() {
+                    @Override
+                    public void onPick(boolean set, @Nullable String result) {
+                        if (set) {
+                            Map<String, Object> ret = new HashMap<>(2);
+                            ret.put(RESULT, SUCCESS);
+                            ret.put(DATA, result);
+                            callback.invoke(ret);
+                        } else {
+                            Map<String, Object> ret = new HashMap<>(2);
+                            ret.put(RESULT, CANCEL);
+                            ret.put(DATA, null);
+                            callback.invoke(ret);
+                        }
+                    }
+                },
+                options);
+
+    }
+
+    private void performSinglePick(final List<String> items, final Map<String, Object> options, final JSCallback callback) {
+        selected = getOption(options, KEY_INDEX, 0);
+        final int textColor = getColor(options, KEY_TEXT_COLOR, Color.TRANSPARENT);
+        final int selectionColor = getColor(options, KEY_SELECTION_COLOR, Color.TRANSPARENT);
+        final ArrayAdapter adapter = new ArrayAdapter<String>(
+            mWXSDKInstance.getContext(),
+            android.R.layout.simple_list_item_single_choice,
+            items) {
+            @NonNull
+            @Override
+            public View getView(int position, View convertView, @Nullable ViewGroup parent) {
+                View itemView =  super.getView(position, convertView, parent);
+
+                if (itemView != null && itemView instanceof Checkable) {
+                    boolean needSelected = position == selected;
+                    ((Checkable) itemView).setChecked(needSelected);
+
+                    if (needSelected) {
+                        itemView.setBackgroundColor(selectionColor);
+                    } else {
+                        itemView.setBackgroundColor(Color.TRANSPARENT);
+                    }
+                }
+
+                if (itemView instanceof TextView && textColor != Color.TRANSPARENT) {
+                    ((TextView) itemView).setTextColor(textColor);
+                }
+
+                return itemView;
+            }
+        };
+        final AlertDialog dialog =  new AlertDialog.Builder(mWXSDKInstance.getContext())
+                .setAdapter(adapter, null)
+                .setPositiveButton(android.R.string.ok, new DialogInterface.OnClickListener() {
+                    @Override
+                    public void onClick(DialogInterface dialog, int which) {
+                        //which == -1
+                        Map<String, Object> ret = new HashMap<>(2);
+                        ret.put(RESULT, SUCCESS);
+                        ret.put(DATA, selected);
+                        callback.invoke(ret);
+                    }
+                })
+                .setNegativeButton(android.R.string.cancel, new DialogInterface.OnClickListener() {
+                    @Override
+                    public void onClick(DialogInterface dialog, int which) {
+                        //which == -2
+                        Map<String, Object> ret = new HashMap<>(2);
+                        ret.put(RESULT, CANCEL);
+                        ret.put(DATA, -1);
+                        callback.invoke(ret);
+                    }
+                })
+                .setCustomTitle(makeTitleView(mWXSDKInstance.getContext(), options))
+                .create();
+
+        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
+            //pre create the content view on dialog.
+            //if not , the content view will not be created until dialog.show() called
+            dialog.create();
+        }
+
+        final ListView listView = dialog.getListView();
+        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
+            @Override
+            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
+                selected = position;
+                adapter.notifyDataSetChanged();
+            }
+        });
+
+        dialog.getWindow().getDecorView().post(WXThread.secure(new Runnable() {
+            @Override
+            public void run() {
+                Button confirm = dialog.getButton(DialogInterface.BUTTON_POSITIVE);
+                Button cancel = dialog.getButton(DialogInterface.BUTTON_NEGATIVE);
+
+                if (confirm != null) {
+                    String confirmTitle = getOption(options, KEY_CONFIRM_TITLE, null);
+                    int confirmColor = getColor(options, KEY_CONFIRM_TITLE_COLOR, Color.TRANSPARENT);
+
+                    if (confirmTitle != null) {
+                        confirm.setText(confirmTitle);
+                        confirm.setAllCaps(false);
+                    }
+
+                    if (confirmColor != Color.TRANSPARENT) {
+                        confirm.setTextColor(confirmColor);
+                        confirm.setAllCaps(false);
+                    }
+                }
+
+                if (cancel != null) {
+                    String cancelTitle = getOption(options, KEY_CANCEL_TITLE, null);
+                    int cancelColor = getColor(options, KEY_CANCEL_TITLE_COLOR, Color.TRANSPARENT);
+
+                    if (cancelTitle != null) {
+                        cancel.setText(cancelTitle);
+                    }
+
+                    if (cancelColor != Color.TRANSPARENT) {
+                        cancel.setTextColor(cancelColor);
+                    }
+                }
+            }
+        }));
+
+        dialog.show();
+    }
+
+    private TextView makeTitleView(Context context, Map<String, Object> options) {
+        String text = getOption(options, KEY_TITLE, null);
+        if (text == null) {
+            return null;
+        }
+        TextView textView = new TextView(context);
+        textView.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT));
+        textView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 20);
+        int padding = WXViewUtils.dip2px(12);
+        textView.setPadding(padding, padding, padding, padding);
+        textView.getPaint().setFakeBoldText(true);
+        textView.setBackgroundColor(getColor(options, KEY_TITLE_BACKGROUND_COLOR, Color.TRANSPARENT));
+        textView.setTextColor(getColor(options, KEY_TITLE_COLOR, Color.BLACK));
+        textView.setText(text);
+        return textView;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/storage/DefaultWXStorage.java b/android/sdk/src/main/java/org/apache/weex/appfram/storage/DefaultWXStorage.java
new file mode 100644
index 0000000..2a0a6bb
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/storage/DefaultWXStorage.java
@@ -0,0 +1,335 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.storage;
+
+import android.content.ContentValues;
+import android.content.Context;
+import android.database.Cursor;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteFullException;
+import android.database.sqlite.SQLiteStatement;
+import android.support.annotation.Nullable;
+
+import org.apache.weex.common.WXThread;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+public class DefaultWXStorage implements IWXStorageAdapter {
+
+    private WXSQLiteOpenHelper mDatabaseSupplier;
+
+    private ExecutorService mExecutorService;
+
+    private void execute(@Nullable final Runnable runnable) {
+        if (mExecutorService == null) {
+            mExecutorService = Executors.newSingleThreadExecutor();
+        }
+
+        if(runnable != null && !mExecutorService.isShutdown() && !mExecutorService.isTerminated()) {
+            mExecutorService.execute(WXThread.secure(runnable));
+        }
+    }
+
+    public DefaultWXStorage(Context context) {
+        this.mDatabaseSupplier = new WXSQLiteOpenHelper(context);
+    }
+
+
+    @Override
+    public void setItem(final String key, final String value, final OnResultReceivedListener listener) {
+        execute(new Runnable() {
+            @Override
+            public void run() {
+                Map<String, Object> data = StorageResultHandler.setItemResult(performSetItem(key, value, false, true));
+                if (listener == null) {
+                    return;
+                }
+                listener.onReceived(data);
+            }
+        });
+    }
+
+    @Override
+    public void getItem(final String key, final OnResultReceivedListener listener) {
+        execute(new Runnable() {
+            @Override
+            public void run() {
+                Map<String, Object> data = StorageResultHandler.getItemResult(performGetItem(key));
+                if (listener == null) {
+                    return;
+                }
+                listener.onReceived(data);
+            }
+        });
+    }
+
+    @Override
+    public void removeItem(final String key, final OnResultReceivedListener listener) {
+        execute(new Runnable() {
+            @Override
+            public void run() {
+                Map<String, Object> data = StorageResultHandler.removeItemResult(performRemoveItem(key));
+                if (listener == null) {
+                    return;
+                }
+                listener.onReceived(data);
+            }
+        });
+    }
+
+    @Override
+    public void length(final OnResultReceivedListener listener) {
+        execute(new Runnable() {
+            @Override
+            public void run() {
+                Map<String, Object> data = StorageResultHandler.getLengthResult(performGetLength());
+                if (listener == null) {
+                    return;
+                }
+                listener.onReceived(data);
+            }
+        });
+    }
+
+    @Override
+    public void getAllKeys(final OnResultReceivedListener listener) {
+        execute(new Runnable() {
+            @Override
+            public void run() {
+                Map<String, Object> data = StorageResultHandler.getAllkeysResult(performGetAllKeys());
+                if (listener == null) {
+                    return;
+                }
+                listener.onReceived(data);
+            }
+        });
+    }
+
+    @Override
+    public void setItemPersistent(final String key, final String value, final OnResultReceivedListener listener) {
+        execute(new Runnable() {
+            @Override
+            public void run() {
+                Map<String, Object> data = StorageResultHandler.setItemResult(performSetItem(key, value, true, true));
+                if (listener == null) {
+                    return;
+                }
+                listener.onReceived(data);
+            }
+        });
+    }
+
+    @Override
+    public void close() {
+        final ExecutorService needCloseService = mExecutorService;
+        execute(new Runnable() {
+            @Override
+            public void run() {
+                try {
+                    mDatabaseSupplier.closeDatabase();
+                    if (needCloseService != null) {
+                        needCloseService.shutdown();
+                    }
+                } catch (Exception e) {
+                    WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, e.getMessage());
+                }
+            }
+        });
+        mExecutorService = null;
+    }
+
+    private boolean performSetItem(String key, String value, boolean isPersistent, boolean allowRetryWhenFull) {
+        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
+        if (database == null) {
+            return false;
+        }
+
+        WXLogUtils.d(WXSQLiteOpenHelper.TAG_STORAGE, "set k-v to storage(key:" + key + ",value:" + value + ",isPersistent:" + isPersistent + ",allowRetry:" + allowRetryWhenFull + ")");
+        String sql = "INSERT OR REPLACE INTO " + WXSQLiteOpenHelper.TABLE_STORAGE + " VALUES (?,?,?,?);";
+        SQLiteStatement statement = null;
+        String timeStamp = WXSQLiteOpenHelper.sDateFormatter.format(new Date());
+        try {
+            statement = database.compileStatement(sql);
+            statement.clearBindings();
+            statement.bindString(1, key);
+            statement.bindString(2, value);
+            statement.bindString(3, timeStamp);
+            statement.bindLong(4, isPersistent ? 1 : 0);
+            statement.execute();
+            return true;
+        } catch (Exception e) {
+            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute setItem :" + e.getMessage());
+            if (e instanceof SQLiteFullException) {
+                if (allowRetryWhenFull && trimToSize()) {
+                    //try again
+                    //setItem/setItemPersistent method only allow try once when occurred a sqliteFullException.
+                    WXLogUtils.d(WXSQLiteOpenHelper.TAG_STORAGE, "retry set k-v to storage(key:" + key + ",value:" + value + ")");
+                    return performSetItem(key, value, isPersistent, false);
+                }
+            }
+
+            return false;
+        } finally {
+            if(statement != null) {
+                statement.close();
+            }
+        }
+    }
+
+    /**
+     * remove 10% of total record(at most) ordered by timestamp.
+     * */
+    private boolean trimToSize() {
+        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
+        if (database == null) {
+            return false;
+        }
+
+        List<String> toEvict = new ArrayList<>();
+        int num = 0;
+
+        Cursor c = database.query(WXSQLiteOpenHelper.TABLE_STORAGE, new String[]{WXSQLiteOpenHelper.COLUMN_KEY, WXSQLiteOpenHelper.COLUMN_PERSISTENT}, null, null, null, null, WXSQLiteOpenHelper.COLUMN_TIMESTAMP + " ASC");
+        try {
+            int evictSize = c.getCount() / 10;
+            while (c.moveToNext()) {
+                String key = c.getString(c.getColumnIndex(WXSQLiteOpenHelper.COLUMN_KEY));
+                boolean persistent = c.getInt(c.getColumnIndex(WXSQLiteOpenHelper.COLUMN_PERSISTENT)) == 1;
+                if (!persistent && key != null) {
+                    num++;
+                    toEvict.add(key);
+                    if (num == evictSize) {
+                        break;
+                    }
+                }
+            }
+        } catch (Exception e) {
+            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute trimToSize:" + e.getMessage());
+        } finally {
+            c.close();
+        }
+
+        if (num <= 0) {
+            return false;
+        }
+
+        for (String key : toEvict) {
+            performRemoveItem(key);
+        }
+        WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "remove " + num + " items by lru");
+        return true;
+    }
+
+    private String performGetItem(String key) {
+        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
+        if (database == null) {
+            return null;
+        }
+
+        Cursor c = database.query(WXSQLiteOpenHelper.TABLE_STORAGE,
+                new String[]{WXSQLiteOpenHelper.COLUMN_VALUE},
+                WXSQLiteOpenHelper.COLUMN_KEY + "=?",
+                new String[]{key},
+                null, null, null);
+        try {
+            if (c.moveToNext()) {
+                ContentValues values = new ContentValues();
+                //update timestamp
+                values.put(WXSQLiteOpenHelper.COLUMN_TIMESTAMP, WXSQLiteOpenHelper.sDateFormatter.format(new Date()));
+                int updateResult = mDatabaseSupplier.getDatabase().update(WXSQLiteOpenHelper.TABLE_STORAGE, values, WXSQLiteOpenHelper.COLUMN_KEY + "= ?", new String[]{key});
+
+                WXLogUtils.d(WXSQLiteOpenHelper.TAG_STORAGE, "update timestamp " + (updateResult == 1 ? "success" : "failed") + " for operation [getItem(key = " + key + ")]");
+                return c.getString(c.getColumnIndex(WXSQLiteOpenHelper.COLUMN_VALUE));
+            } else {
+                return null;
+            }
+        } catch (Exception e) {
+            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute getItem:" + e.getMessage());
+            return null;
+        } finally {
+            c.close();
+        }
+    }
+
+    private boolean performRemoveItem(String key) {
+        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
+        if (database == null) {
+            return false;
+        }
+
+        int count = 0;
+        try {
+            count = database.delete(WXSQLiteOpenHelper.TABLE_STORAGE,
+                    WXSQLiteOpenHelper.COLUMN_KEY + "=?",
+                    new String[]{key});
+        } catch (Exception e) {
+            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute removeItem:" + e.getMessage());
+            return false;
+        }
+        return count == 1;
+    }
+
+    private long performGetLength() {
+        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
+        if (database == null) {
+            return 0;
+        }
+
+        String sql = "SELECT count(" + WXSQLiteOpenHelper.COLUMN_KEY + ") FROM " + WXSQLiteOpenHelper.TABLE_STORAGE;
+        SQLiteStatement statement = null;
+        try {
+            statement = database.compileStatement(sql);
+            return statement.simpleQueryForLong();
+        } catch (Exception e) {
+            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute getLength:" + e.getMessage());
+            return 0;
+        } finally {
+            if(statement != null) {
+                statement.close();
+            }
+        }
+    }
+
+    private List<String> performGetAllKeys() {
+        SQLiteDatabase database = mDatabaseSupplier.getDatabase();
+        if (database == null) {
+            return null;
+        }
+
+        List<String> result = new ArrayList<>();
+        Cursor c = database.query(WXSQLiteOpenHelper.TABLE_STORAGE, new String[]{WXSQLiteOpenHelper.COLUMN_KEY}, null, null, null, null, null);
+        try {
+            while (c.moveToNext()) {
+                result.add(c.getString(c.getColumnIndex(WXSQLiteOpenHelper.COLUMN_KEY)));
+            }
+            return result;
+        } catch (Exception e) {
+            WXLogUtils.e(WXSQLiteOpenHelper.TAG_STORAGE, "DefaultWXStorage occurred an exception when execute getAllKeys:" + e.getMessage());
+            return result;
+        } finally {
+            c.close();
+        }
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/storage/IWXStorage.java b/android/sdk/src/main/java/org/apache/weex/appfram/storage/IWXStorage.java
new file mode 100644
index 0000000..ea6dc06
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/storage/IWXStorage.java
@@ -0,0 +1,32 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.storage;
+
+import android.support.annotation.Nullable;
+
+import org.apache.weex.bridge.JSCallback;
+
+interface IWXStorage {
+    public void setItem(String key, String value,@Nullable JSCallback callback);
+    public void getItem(String key,@Nullable JSCallback callback);
+    public void removeItem(String key,@Nullable JSCallback callback);
+    public void length(@Nullable JSCallback callback);
+    public void getAllKeys(@Nullable JSCallback callback);
+    public void setItemPersistent(String key, String value, @Nullable JSCallback callback);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/storage/IWXStorageAdapter.java b/android/sdk/src/main/java/org/apache/weex/appfram/storage/IWXStorageAdapter.java
new file mode 100644
index 0000000..543e4c3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/storage/IWXStorageAdapter.java
@@ -0,0 +1,53 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.storage;
+
+import java.util.Map;
+import org.apache.weex.InitConfig;
+
+/**
+ * interface for {@link WXStorageModule} class.
+ * this interface works as an adapter for different storage strategy.
+ * the default is use {@link android.database.sqlite.SQLiteDatabase} to store k-v pairs.
+ * You can call {@link InitConfig.Builder#setStorageAdapter(IWXStorageAdapter)} to inject your own
+ * storage implementation.
+ * */
+public interface IWXStorageAdapter {
+    void setItem(String key, String value,OnResultReceivedListener listener);
+
+    void getItem(String key,OnResultReceivedListener listener);
+
+    void removeItem(String key,OnResultReceivedListener listener);
+
+    void length(OnResultReceivedListener listener);
+
+    void getAllKeys(OnResultReceivedListener listener);
+
+    void setItemPersistent(String key, String value, OnResultReceivedListener listener);
+
+    void close();
+
+    /**
+     * the callback of storage operation.
+     * */
+    interface OnResultReceivedListener {
+        void onReceived(Map<String,Object> data);
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/storage/StorageResultHandler.java b/android/sdk/src/main/java/org/apache/weex/appfram/storage/StorageResultHandler.java
new file mode 100644
index 0000000..4225e66
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/storage/StorageResultHandler.java
@@ -0,0 +1,107 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.storage;
+
+import android.support.annotation.Nullable;
+
+import org.apache.weex.bridge.JSCallback;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+public class StorageResultHandler {
+
+    private StorageResultHandler() {
+    }
+
+    private static final String RESULT = "result";
+    private static final String DATA = "data";
+
+
+    private static final String UNDEFINED = "undefined";
+    private static final String RESULT_FAILED_NO_HANDLER = "no_handler";
+    private static final String RESULT_FAILED_INVALID_PARAM = "invalid_param";
+
+
+    private static final String RESULT_OK = "success";
+    private static final String RESULT_FAILED = "failed";
+
+
+    public static Map<String, Object> getItemResult(String result) {
+        Map<String, Object> map = new HashMap<>(4);
+        map.put(RESULT, result != null ? RESULT_OK : RESULT_FAILED);
+        map.put(DATA, result != null ? result : UNDEFINED);
+        return map;
+    }
+
+    public static Map<String, Object> setItemResult(boolean result) {
+        Map<String, Object> map = new HashMap<>(4);
+        map.put(RESULT, result ? RESULT_OK : RESULT_FAILED);
+        map.put(DATA, UNDEFINED);
+        return map;
+    }
+
+
+    public static Map<String, Object> removeItemResult(boolean result) {
+        Map<String, Object> map = new HashMap<>(4);
+        map.put(RESULT, result ? RESULT_OK : RESULT_FAILED);
+        map.put(DATA, UNDEFINED);
+        return map;
+    }
+
+    public static Map<String, Object> getLengthResult(long result) {
+        Map<String, Object> map = new HashMap<>(4);
+        map.put(RESULT, RESULT_OK);
+        map.put(DATA, result);
+        return map;
+    }
+
+    public static Map<String, Object> getAllkeysResult(List<String> result) {
+        if (result == null) {
+            result = new ArrayList<>(1);
+        }
+        Map<String, Object> map = new HashMap<>(4);
+        map.put(RESULT, RESULT_OK);
+        map.put(DATA, result);
+        return map;
+    }
+
+
+    private static void handleResult(@Nullable JSCallback callback, String result, Object data) {
+        if (callback == null) {
+            return;
+        }
+        Map<String, Object> retVal = new HashMap<>(4);
+        retVal.put(RESULT, result);
+        retVal.put(DATA, data);
+        callback.invoke(retVal);
+    }
+
+    public static void handleNoHandlerError(@Nullable JSCallback callback) {
+        handleResult(callback, RESULT_FAILED, RESULT_FAILED_NO_HANDLER);
+    }
+
+    public static void handleInvalidParam(@Nullable JSCallback callback) {
+        handleResult(callback, RESULT_FAILED, RESULT_FAILED_INVALID_PARAM);
+    }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/storage/WXSQLiteOpenHelper.java b/android/sdk/src/main/java/org/apache/weex/appfram/storage/WXSQLiteOpenHelper.java
new file mode 100644
index 0000000..1ae25f2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/storage/WXSQLiteOpenHelper.java
@@ -0,0 +1,226 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.storage;
+
+import android.content.Context;
+import android.database.Cursor;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteException;
+import android.database.sqlite.SQLiteOpenHelper;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+
+import org.apache.weex.utils.WXLogUtils;
+
+import java.text.SimpleDateFormat;
+import java.util.Date;
+import java.util.Locale;
+
+public class WXSQLiteOpenHelper extends SQLiteOpenHelper {
+
+    private static final String DATABASE_NAME = "WXStorage";
+    private static final int DATABASE_VERSION = 2;
+    static final String TAG_STORAGE = "weex_storage";
+
+    private long mMaximumDatabaseSize = 5 * 10 * 1024 * 1024L;//50mb
+    static SimpleDateFormat sDateFormatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss", Locale.getDefault());
+    private Context mContext;
+    private SQLiteDatabase mDb;
+
+
+    static final String TABLE_STORAGE = "default_wx_storage";
+    static final String COLUMN_KEY = "key";
+    static final String COLUMN_VALUE = "value";
+    static final String COLUMN_TIMESTAMP = "timestamp";
+    static final String COLUMN_PERSISTENT = "persistent";
+
+    private static final int SLEEP_TIME_MS = 30;
+
+    private static final String STATEMENT_CREATE_TABLE = "CREATE TABLE IF NOT EXISTS " + TABLE_STORAGE + " ("
+            + COLUMN_KEY
+            + " TEXT PRIMARY KEY,"
+            + COLUMN_VALUE
+            + " TEXT NOT NULL,"
+            + COLUMN_TIMESTAMP
+            + " TEXT NOT NULL,"
+            + COLUMN_PERSISTENT
+            + " INTEGER DEFAULT 0"
+            + ")";
+
+
+    public WXSQLiteOpenHelper(Context context) {
+        super(context, DATABASE_NAME, null, DATABASE_VERSION);
+        this.mContext = context;
+    }
+
+    /**
+     * retrieve sqlite database
+     *
+     * @return a {@link SQLiteDatabase} instance or null if retrieve fails.
+     * */
+    public @Nullable SQLiteDatabase getDatabase() {
+        ensureDatabase();
+        return mDb;
+    }
+
+    @Override
+    public void onCreate(SQLiteDatabase db) {
+        db.execSQL(STATEMENT_CREATE_TABLE);
+    }
+
+
+    /**
+     * version 1:
+     *
+     *   ----------------
+     *   | key | value |
+     *   ---------------
+     *
+     * version 2:
+     *
+     *  ----------------------------------------
+     *  | key | value | timestamp | persistent |
+     *  ----------------------------------------
+     **/
+    @Override
+    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
+        if (oldVersion != newVersion) {
+            if(newVersion == 2 && oldVersion == 1){
+                WXLogUtils.d(TAG_STORAGE,"storage is updating from version "+oldVersion+" to version "+newVersion);
+                boolean updateResult = true;
+                try {
+                    long start = System.currentTimeMillis();
+
+                    db.beginTransaction();
+                    // update table structure
+                    String SQL_ADD_COLUMN_TIMESTAMP = "ALTER TABLE "+TABLE_STORAGE+" ADD COLUMN "+COLUMN_TIMESTAMP+" TEXT;";
+                    WXLogUtils.d(TAG_STORAGE,"exec sql : "+ SQL_ADD_COLUMN_TIMESTAMP);
+                    db.execSQL(SQL_ADD_COLUMN_TIMESTAMP);
+
+                    String SQL_ADD_COLUMN_PERSISTENT = "ALTER TABLE "+TABLE_STORAGE+" ADD COLUMN "+COLUMN_PERSISTENT+" INTEGER;";
+                    WXLogUtils.d(TAG_STORAGE,"exec sql : "+ SQL_ADD_COLUMN_PERSISTENT);
+                    db.execSQL(SQL_ADD_COLUMN_PERSISTENT);
+
+                    // update timestamp & persistent
+                    String SQL_UPDATE_TABLE = "UPDATE "+TABLE_STORAGE+" SET "+ COLUMN_TIMESTAMP+" = '"+sDateFormatter.format(new Date())+"' , "+ COLUMN_PERSISTENT +" = 0";
+                    WXLogUtils.d(TAG_STORAGE,"exec sql : "+ SQL_UPDATE_TABLE);
+                    db.execSQL(SQL_UPDATE_TABLE);
+
+                    db.setTransactionSuccessful();
+                    long time = System.currentTimeMillis() - start;
+                    WXLogUtils.d(TAG_STORAGE,"storage updated success ("+time+"ms)");
+                }catch (Exception e){
+                    WXLogUtils.d(TAG_STORAGE,"storage updated failed from version "+oldVersion+" to version "+newVersion+","+e.getMessage());
+                    updateResult = false;
+                }finally {
+                    db.endTransaction();
+                }
+                //rollback
+                if(!updateResult){
+                    WXLogUtils.d(TAG_STORAGE,"storage is rollback,all data will be removed");
+                    deleteDB();
+                    onCreate(db);
+                }
+            }else{
+                deleteDB();
+                onCreate(db);
+            }
+        }
+    }
+
+
+
+    synchronized void ensureDatabase() {
+        if (mDb != null && mDb.isOpen()) {
+            return;
+        }
+
+        try {
+            // Sometimes retrieving the database fails. We do 2 retries: first without database deletion
+            // and then with deletion.
+            for (int tries = 0; tries < 2; tries++) {
+                try {
+                    if (tries > 0) {
+                        //delete db and recreate
+                        deleteDB();
+                    }
+                    mDb = getWritableDatabase();
+                    break;
+                } catch (SQLiteException e) {
+                    e.printStackTrace();
+                }
+                // Wait before retrying.
+                try {
+                    Thread.sleep(SLEEP_TIME_MS);
+                } catch (InterruptedException ie) {
+                    Thread.currentThread().interrupt();
+                }
+            }
+            if(mDb == null){
+                return;
+            }
+
+            createTableIfNotExists(mDb);
+
+            mDb.setMaximumSize(mMaximumDatabaseSize);
+        } catch (Throwable e) {
+            mDb = null;
+            WXLogUtils.d(TAG_STORAGE,"ensureDatabase failed, throwable = " + e.getMessage());
+        }
+
+    }
+
+    public synchronized void setMaximumSize(long size) {
+        mMaximumDatabaseSize = size;
+        if (mDb != null) {
+            mDb.setMaximumSize(mMaximumDatabaseSize);
+        }
+    }
+
+    private boolean deleteDB() {
+        closeDatabase();
+        return mContext.deleteDatabase(DATABASE_NAME);
+    }
+
+    public synchronized void closeDatabase() {
+        if (mDb != null && mDb.isOpen()) {
+            mDb.close();
+            mDb = null;
+        }
+    }
+
+    private void createTableIfNotExists(@NonNull SQLiteDatabase db) {
+        Cursor cursor = null;
+        try {
+            cursor = db.rawQuery("SELECT DISTINCT tbl_name FROM sqlite_master WHERE tbl_name = '"+TABLE_STORAGE+"'", null);
+            if(cursor != null && cursor.getCount() > 0) {
+                return;
+            }
+            db.execSQL(STATEMENT_CREATE_TABLE);
+        }catch (Exception e){
+            e.printStackTrace();
+        }finally {
+            if(cursor != null){
+                cursor.close();
+            }
+        }
+    }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/storage/WXStorageModule.java b/android/sdk/src/main/java/org/apache/weex/appfram/storage/WXStorageModule.java
new file mode 100644
index 0000000..cb4b6de
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/storage/WXStorageModule.java
@@ -0,0 +1,180 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.storage;
+
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKEngine;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.annotation.JSMethod;
+
+import java.util.Map;
+
+public class WXStorageModule extends WXSDKEngine.DestroyableModule implements IWXStorage {
+
+    IWXStorageAdapter mStorageAdapter;
+
+    private IWXStorageAdapter ability() {
+        if (mStorageAdapter != null) {
+            return mStorageAdapter;
+        }
+        mStorageAdapter = WXSDKEngine.getIWXStorageAdapter();
+        return mStorageAdapter;
+    }
+
+
+    @Override
+    @JSMethod(uiThread = false)
+    public void setItem(String key, String value, @Nullable final JSCallback callback) {
+        if (TextUtils.isEmpty(key) || value == null) {
+            StorageResultHandler.handleInvalidParam(callback);
+            return;
+        }
+
+        IWXStorageAdapter adapter = ability();
+        if (adapter == null) {
+            StorageResultHandler.handleNoHandlerError(callback);
+            return;
+        }
+        adapter.setItem(key, value, new IWXStorageAdapter.OnResultReceivedListener() {
+            @Override
+            public void onReceived(Map<String, Object> data) {
+                if(callback != null){
+                    callback.invoke(data);
+                }
+            }
+        });
+
+
+    }
+
+    @Override
+    @JSMethod(uiThread = false)
+    public void getItem(String key, @Nullable final JSCallback callback) {
+        if (TextUtils.isEmpty(key)) {
+            StorageResultHandler.handleInvalidParam(callback);
+            return;
+        }
+
+        IWXStorageAdapter adapter = ability();
+        if (adapter == null) {
+            StorageResultHandler.handleNoHandlerError(callback);
+            return;
+        }
+        adapter.getItem(key, new IWXStorageAdapter.OnResultReceivedListener() {
+            @Override
+            public void onReceived(Map<String, Object> data) {
+                if(callback != null){
+                    callback.invoke(data);
+                }
+            }
+        });
+    }
+
+    @Override
+    @JSMethod(uiThread = false)
+    public void removeItem(String key, @Nullable final JSCallback callback) {
+        if (TextUtils.isEmpty(key)) {
+            StorageResultHandler.handleInvalidParam(callback);
+            return;
+        }
+
+        IWXStorageAdapter adapter = ability();
+        if (adapter == null) {
+            StorageResultHandler.handleNoHandlerError(callback);
+            return;
+        }
+        adapter.removeItem(key, new IWXStorageAdapter.OnResultReceivedListener() {
+            @Override
+            public void onReceived(Map<String, Object> data) {
+                if(callback != null){
+                    callback.invoke(data);
+                }
+            }
+        });
+    }
+
+    @Override
+    @JSMethod(uiThread = false)
+    public void length(@Nullable final JSCallback callback) {
+        IWXStorageAdapter adapter = ability();
+        if (adapter == null) {
+            StorageResultHandler.handleNoHandlerError(callback);
+            return;
+        }
+        adapter.length(new IWXStorageAdapter.OnResultReceivedListener() {
+            @Override
+            public void onReceived(Map<String, Object> data) {
+                if(callback != null){
+                    callback.invoke(data);
+                }
+            }
+        });
+    }
+
+    @Override
+    @JSMethod(uiThread = false)
+    public void getAllKeys(@Nullable final JSCallback callback) {
+        IWXStorageAdapter adapter = ability();
+        if (adapter == null) {
+            StorageResultHandler.handleNoHandlerError(callback);
+            return;
+        }
+        adapter.getAllKeys(new IWXStorageAdapter.OnResultReceivedListener() {
+            @Override
+            public void onReceived(Map<String, Object> data) {
+                if(callback != null){
+                    callback.invoke(data);
+                }
+            }
+        });
+    }
+
+    @Override
+    @JSMethod(uiThread = false)
+    public void setItemPersistent(String key, String value, @Nullable final JSCallback callback) {
+        if (TextUtils.isEmpty(key) || value == null) {
+            StorageResultHandler.handleInvalidParam(callback);
+            return;
+        }
+
+        IWXStorageAdapter adapter = ability();
+        if (adapter == null) {
+            StorageResultHandler.handleNoHandlerError(callback);
+            return;
+        }
+        adapter.setItemPersistent(key, value, new IWXStorageAdapter.OnResultReceivedListener() {
+            @Override
+            public void onReceived(Map<String, Object> data) {
+                if(callback != null){
+                    callback.invoke(data);
+                }
+            }
+        });
+    }
+
+    @Override
+    public void destroy() {
+        IWXStorageAdapter adapter = ability();
+        if (adapter != null) {
+            adapter.close();
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/websocket/IWebSocketAdapter.java b/android/sdk/src/main/java/org/apache/weex/appfram/websocket/IWebSocketAdapter.java
new file mode 100644
index 0000000..1386620
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/websocket/IWebSocketAdapter.java
@@ -0,0 +1,48 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.websocket;
+
+import android.support.annotation.Nullable;
+
+/**
+ * Created by moxun on 16/12/27.
+ */
+
+public interface IWebSocketAdapter {
+
+    String HEADER_SEC_WEBSOCKET_PROTOCOL = "Sec-WebSocket-Protocol";
+
+    void connect(String url, @Nullable String protocol, EventListener listener);
+
+    void send(String data);
+
+    void close(int code, String reason);
+
+    void destroy();
+
+    interface EventListener {
+        void onOpen();
+
+        void onMessage(String data);
+
+        void onClose(int code, String reason, boolean wasClean);
+
+        void onError(String msg);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/websocket/IWebSocketAdapterFactory.java b/android/sdk/src/main/java/org/apache/weex/appfram/websocket/IWebSocketAdapterFactory.java
new file mode 100644
index 0000000..9ae2e4f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/websocket/IWebSocketAdapterFactory.java
@@ -0,0 +1,27 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.websocket;
+
+/**
+ * Created by moxun on 16/12/28.
+ */
+
+public interface IWebSocketAdapterFactory {
+    IWebSocketAdapter createWebSocketAdapter();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/websocket/WebSocketCloseCodes.java b/android/sdk/src/main/java/org/apache/weex/appfram/websocket/WebSocketCloseCodes.java
new file mode 100644
index 0000000..82c7fa9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/websocket/WebSocketCloseCodes.java
@@ -0,0 +1,51 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.websocket;
+
+/**
+ * Created by moxun on 17/1/3.
+ * @link {https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent}
+ */
+
+public enum WebSocketCloseCodes {
+    CLOSE_NORMAL(1000),
+    CLOSE_GOING_AWAY(1001),
+    CLOSE_PROTOCOL_ERROR(1002),
+    CLOSE_UNSUPPORTED(1003),
+    CLOSE_NO_STATUS(1005),
+    CLOSE_ABNORMAL(1006),
+    UNSUPPORTED_DATA(1007),
+    POLICY_VIOLATION(1008),
+    CLOSE_TOO_LARGE(1009),
+    MISSING_EXTENSION(1010),
+    INTERNAL_ERROR(1011),
+    SERVICE_RESTART(1012),
+    TRY_AGAIN_LATER(1013),
+    TLS_HANDSHAKE(1015);
+
+    private int code;
+
+    WebSocketCloseCodes(int code) {
+        this.code = code;
+    }
+
+    public int getCode() {
+        return code;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/appfram/websocket/WebSocketModule.java b/android/sdk/src/main/java/org/apache/weex/appfram/websocket/WebSocketModule.java
new file mode 100644
index 0000000..7b7ccf1
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/appfram/websocket/WebSocketModule.java
@@ -0,0 +1,188 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.appfram.websocket;
+
+import android.os.Looper;
+
+import org.apache.weex.WXSDKEngine;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Created by moxun on 16/12/27.
+ */
+
+public class WebSocketModule extends WXSDKEngine.DestroyableModule {
+
+    private static final String TAG = "WebSocketModule";
+    private static final String KEY_DATA = "data";
+    private static final String KEY_CODE = "code";
+    private static final String KEY_REASON = "reason";
+    private static final String KEY_WAS_CLEAN = "wasClean";
+
+    private IWebSocketAdapter webSocketAdapter;
+    private WebSocketEventListener eventListener;
+
+    public WebSocketModule() {
+        WXLogUtils.e(TAG, "create new instance");
+    }
+
+    @JSMethod(uiThread = false)
+    public void WebSocket(String url, String protocol) {
+        if (webSocketAdapter != null) {
+            WXLogUtils.w(TAG, "close");
+            webSocketAdapter.close(WebSocketCloseCodes.CLOSE_GOING_AWAY.getCode(), WebSocketCloseCodes.CLOSE_GOING_AWAY.name());
+        }
+        webSocketAdapter = mWXSDKInstance.getWXWebSocketAdapter();
+        if (!reportErrorIfNoAdapter()) {
+            eventListener = new WebSocketEventListener();
+            webSocketAdapter.connect(url, protocol, eventListener);
+        }
+    }
+
+    @JSMethod(uiThread = false)
+    public void send(String data) {
+        if (!reportErrorIfNoAdapter()) {
+            webSocketAdapter.send(data);
+        }
+    }
+
+    @JSMethod(uiThread = false)
+    public void close(String code, String reason) {
+        if (!reportErrorIfNoAdapter()) {
+            int codeNumber = WebSocketCloseCodes.CLOSE_NORMAL.getCode();
+            if (code != null) {
+                try {
+                    codeNumber = Integer.parseInt(code);
+                } catch (NumberFormatException e) {
+                    //ignore
+                }
+            }
+            webSocketAdapter.close(codeNumber, reason);
+        }
+    }
+
+    @JSMethod(uiThread = false)
+    public void onopen(JSCallback callback) {
+        if (eventListener != null) {
+            eventListener.onOpen = callback;
+        }
+    }
+
+    @JSMethod(uiThread = false)
+    public void onmessage(JSCallback callback) {
+        if (eventListener != null) {
+            eventListener.onMessage = callback;
+        }
+    }
+
+    @JSMethod(uiThread = false)
+    public void onclose(JSCallback callback) {
+        if (eventListener != null) {
+            eventListener.onClose = callback;
+        }
+    }
+
+    @JSMethod(uiThread = false)
+    public void onerror(JSCallback callback) {
+        if (eventListener != null) {
+            eventListener.onError = callback;
+        }
+    }
+
+    @Override
+    public void destroy() {
+        Runnable destroyTask = new Runnable() {
+            @Override
+            public void run() {
+                WXLogUtils.w(TAG, "close session with instance id " + mWXSDKInstance.getInstanceId());
+                if (webSocketAdapter != null) {
+                    webSocketAdapter.destroy();
+                }
+                webSocketAdapter = null;
+                eventListener = null;
+            }
+        };
+
+        if (Looper.myLooper() == Looper.getMainLooper()) {
+            WXBridgeManager.getInstance().post(destroyTask);
+        } else {
+            destroyTask.run();
+        }
+    }
+
+    private boolean reportErrorIfNoAdapter() {
+        if (webSocketAdapter == null) {
+            if (eventListener != null) {
+                eventListener.onError("No implementation found for IWebSocketAdapter");
+            }
+            WXLogUtils.e(TAG, "No implementation found for IWebSocketAdapter");
+            return true;
+        }
+        return false;
+    }
+
+    private class WebSocketEventListener implements IWebSocketAdapter.EventListener {
+        private JSCallback onOpen;
+        private JSCallback onClose;
+        private JSCallback onError;
+        private JSCallback onMessage;
+
+        @Override
+        public void onOpen() {
+            if (onOpen != null) {
+                onOpen.invoke(new HashMap<>(0));
+            }
+        }
+
+        @Override
+        public void onMessage(String data) {
+            if (onMessage != null) {
+                Map<String, String> msg = new HashMap<>(1);
+                msg.put(KEY_DATA, data);
+                onMessage.invokeAndKeepAlive(msg);
+            }
+        }
+
+        @Override
+        public void onClose(int code, String reason, boolean wasClean) {
+            if (onClose != null) {
+                Map<String, Object> msg = new HashMap<>(3);
+                msg.put(KEY_CODE, code);
+                msg.put(KEY_REASON, reason);
+                msg.put(KEY_WAS_CLEAN, wasClean);
+                onClose.invoke(msg);
+            }
+        }
+
+        @Override
+        public void onError(String msg) {
+            if (onError != null) {
+                Map<String, String> info = new HashMap<>(1);
+                info.put(KEY_DATA, msg);
+                onError.invokeAndKeepAlive(info);
+            }
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/base/CalledByNative.java b/android/sdk/src/main/java/org/apache/weex/base/CalledByNative.java
new file mode 100644
index 0000000..a9c6fd9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/base/CalledByNative.java
@@ -0,0 +1,22 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.weex.base;
+public @interface CalledByNative {
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/base/FloatUtil.java b/android/sdk/src/main/java/org/apache/weex/base/FloatUtil.java
new file mode 100755
index 0000000..d2ad9c3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/base/FloatUtil.java
@@ -0,0 +1,31 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.base;
+
+public class FloatUtil {
+
+  private static final float EPSILON = .00001f;
+
+  public static boolean floatsEqual(float f1, float f2) {
+    if (Float.isNaN(f1) || Float.isNaN(f2)) {
+      return Float.isNaN(f1) && Float.isNaN(f2);
+    }
+    return Math.abs(f2 - f1) < EPSILON;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/base/SystemMessageHandler.java b/android/sdk/src/main/java/org/apache/weex/base/SystemMessageHandler.java
new file mode 100644
index 0000000..5663b49
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/base/SystemMessageHandler.java
@@ -0,0 +1,105 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.base;
+
+import android.os.Handler;
+import android.os.Message;
+import android.util.Log;
+
+import java.io.Serializable;
+import java.lang.reflect.Method;
+
+
+public class SystemMessageHandler extends Handler implements Serializable {
+
+    private static final String TAG = "SystemMessageHandler";
+
+    private static final int SCHEDULED_WORK = 1;
+
+    private long mMessagePumpDelegateNative = 0;
+
+    private Method mMessageMethodSetAsynchronous;
+
+    private native void nativeRunWork(long delegateNative);
+
+    private SystemMessageHandler(long messagePumpDelegateNative) {
+        this.mMessagePumpDelegateNative = messagePumpDelegateNative;
+        try {
+            Class<?> messageClass = Class.forName("android.os.Message");
+            mMessageMethodSetAsynchronous = messageClass.getMethod(
+                    "setAsynchronous", new Class[]{boolean.class});
+        } catch (ClassNotFoundException e) {
+            Log.e(TAG, "Failed to find android.os.Message class:" + e);
+        } catch (NoSuchMethodException e) {
+            Log.e(TAG, "Failed to load Message.setAsynchronous method:" + e);
+        } catch (RuntimeException e) {
+            Log.e(TAG, "Exception while loading Message.setAsynchronous method: " + e);
+        }
+    }
+
+    @CalledByNative
+    public static SystemMessageHandler create(long messagePumpDelegateNative) {
+        return new SystemMessageHandler(messagePumpDelegateNative);
+    }
+
+    @CalledByNative
+    private void scheduleWork() {
+        sendMessage(obtainAsyncMessage(SCHEDULED_WORK));
+    }
+
+    @CalledByNative
+    private void scheduleDelayedWork(long delayMillis) {
+        sendMessageDelayed(obtainAsyncMessage(SCHEDULED_WORK), delayMillis);
+    }
+
+    @CalledByNative
+    private void stop() {
+        removeMessages(SCHEDULED_WORK);
+    }
+
+    private Message obtainAsyncMessage(int what) {
+        Message msg = Message.obtain();
+        msg.what = what;
+//        if (mMessageMethodSetAsynchronous != null) {
+//            // If invocation fails, assume this is indicative of future
+//            // failures, and avoid log spam by nulling the reflected method.
+//            try {
+//                mMessageMethodSetAsynchronous.invoke(msg, true);
+//            } catch (IllegalAccessException e) {
+//                Log.e(TAG, "Illegal access to asynchronous message creation, disabling.");
+//                mMessageMethodSetAsynchronous = null;
+//            } catch (IllegalArgumentException e) {
+//                Log.e(TAG, "Illegal argument for asynchronous message creation, disabling.");
+//                mMessageMethodSetAsynchronous = null;
+//            } catch (InvocationTargetException e) {
+//                Log.e(TAG, "Invocation exception during asynchronous message creation, disabling.");
+//                mMessageMethodSetAsynchronous = null;
+//            } catch (RuntimeException e) {
+//                Log.e(TAG, "Runtime exception during asynchronous message creation, disabling.");
+//                mMessageMethodSetAsynchronous = null;
+//            }
+//        }
+        return msg;
+    }
+
+    @Override
+    public void handleMessage(Message msg) {
+        nativeRunWork(mMessagePumpDelegateNative);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/EventResult.java b/android/sdk/src/main/java/org/apache/weex/bridge/EventResult.java
new file mode 100644
index 0000000..63b315b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/EventResult.java
@@ -0,0 +1,46 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+/**
+ * Created by furture on 2017/10/17.
+ */
+
+public class EventResult {
+
+    private Object result;
+    private boolean success = false;
+    /**
+     * onCallback javascript event callback method
+     * @param result
+     */
+    public void onCallback(Object result){
+        this.success = true;
+        this.result = result;
+    }
+
+    public boolean isSuccess() {
+        return success;
+    }
+
+    public Object getResult(){
+        return  result;
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/Invoker.java b/android/sdk/src/main/java/org/apache/weex/bridge/Invoker.java
new file mode 100644
index 0000000..0b5232a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/Invoker.java
@@ -0,0 +1,33 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Type;
+
+/**
+ * Created by sospartan on 6/16/16.
+ */
+public interface Invoker {
+  Object invoke(Object receiver,Object...params) throws InvocationTargetException, IllegalAccessException;
+
+  Type[] getParameterTypes();
+
+  boolean isRunOnUIThread();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/JSCallback.java b/android/sdk/src/main/java/org/apache/weex/bridge/JSCallback.java
new file mode 100644
index 0000000..815f19f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/JSCallback.java
@@ -0,0 +1,36 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+/**
+ * Created by sospartan on 5/24/16.
+ */
+public interface JSCallback {
+  /**
+   * invoke javascript callback method, this method will destoryed after invoke.
+   * @param data
+   */
+  void invoke(Object data);
+
+  /**
+   * invoke javascript callback method and keep callback alive for later use.
+   * @param data
+   */
+  void invokeAndKeepAlive(Object data);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/JavascriptInvokable.java b/android/sdk/src/main/java/org/apache/weex/bridge/JavascriptInvokable.java
new file mode 100644
index 0000000..a2f0c30
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/JavascriptInvokable.java
@@ -0,0 +1,28 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+/**
+ * Created by sospartan on 11/11/2016.
+ */
+
+public interface JavascriptInvokable {
+  String[] getMethods();
+  Invoker getMethodInvoker(String name);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/MethodInvoker.java b/android/sdk/src/main/java/org/apache/weex/bridge/MethodInvoker.java
new file mode 100644
index 0000000..812421a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/MethodInvoker.java
@@ -0,0 +1,66 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.lang.reflect.Type;
+
+/**
+ * Created by sospartan on 6/16/16.
+ */
+public class MethodInvoker implements Invoker {
+
+  final Method mMethod;
+  final boolean mRunOnUIThread;
+  Type[] mParam;
+
+  public MethodInvoker(Method method){
+    this(method,false);
+  }
+
+  public MethodInvoker(Method method,boolean runInUIThread){
+    mMethod = method;
+    mParam = mMethod.getGenericParameterTypes();
+    mRunOnUIThread = runInUIThread;
+  }
+
+  @Override
+  public Object invoke(Object receiver, Object... params) throws InvocationTargetException, IllegalAccessException {
+    return mMethod.invoke(receiver,params);
+  }
+
+  @Override
+  public Type[] getParameterTypes() {
+    if(mParam ==null){
+      mParam = mMethod.getGenericParameterTypes();
+    }
+    return mParam;
+  }
+
+  @Override
+  public boolean isRunOnUIThread() {
+    return mRunOnUIThread;
+  }
+
+  @Override
+  public String toString() {
+    return mMethod.getName();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/ModuleFactory.java b/android/sdk/src/main/java/org/apache/weex/bridge/ModuleFactory.java
new file mode 100644
index 0000000..0248766
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/ModuleFactory.java
@@ -0,0 +1,29 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import org.apache.weex.common.WXModule;
+
+/**
+ * Created by sospartan on 6/17/16.
+ */
+public interface ModuleFactory<T extends WXModule> extends JavascriptInvokable {
+
+  T buildInstance() throws IllegalAccessException, InstantiationException;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/ModuleFactoryImpl.java b/android/sdk/src/main/java/org/apache/weex/bridge/ModuleFactoryImpl.java
new file mode 100644
index 0000000..3166e0b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/ModuleFactoryImpl.java
@@ -0,0 +1,37 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+/**
+ * Created by shiwentao on 2018/3/13.
+ */
+
+public class ModuleFactoryImpl {
+  public ModuleFactory mFactory = null;
+  public boolean hasRigster = false;
+
+  public ModuleFactoryImpl(ModuleFactory factory) {
+    mFactory = factory;
+  }
+
+  public ModuleFactoryImpl(ModuleFactory factory, boolean rigister) {
+    mFactory = factory;
+    hasRigster = rigister;
+  }
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/NativeInvokeHelper.java b/android/sdk/src/main/java/org/apache/weex/bridge/NativeInvokeHelper.java
new file mode 100644
index 0000000..ebf17ad
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/NativeInvokeHelper.java
@@ -0,0 +1,124 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import android.util.Log;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.performance.WXAnalyzerDataTransfer;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXReflectionUtils;
+
+import java.lang.reflect.Type;
+
+/**
+ * Created by sospartan on 10/11/2016.
+ */
+
+public class NativeInvokeHelper {
+  private String mInstanceId;
+
+  public NativeInvokeHelper(String instanceId){
+    mInstanceId = instanceId;
+  }
+
+  public Object invoke(final Object target,final Invoker invoker,JSONArray args) throws Exception {
+    final Object[] params = prepareArguments(
+            invoker.getParameterTypes(),
+            args);
+
+    if (WXAnalyzerDataTransfer.isInteractionLogOpen() && invoker instanceof MethodInvoker) {
+      for (int i = 0; i < params.length; i++) {
+        if (params[i] instanceof SimpleJSCallback) {
+          final String callBackId = ((SimpleJSCallback)params[i]).getCallbackId();
+          Log.d(WXAnalyzerDataTransfer.INTERACTION_TAG, "[client][callNativeModuleStart]," + mInstanceId + "," + ((MethodInvoker) invoker).mMethod.getDeclaringClass() + "," + ((MethodInvoker) invoker).mMethod.getName() + "," + callBackId);
+          ((SimpleJSCallback) params[i]).setInvokerCallback(new SimpleJSCallback.InvokerCallback() {
+            @Override
+            public void onInvokeSuccess() {
+              Log.d(WXAnalyzerDataTransfer.INTERACTION_TAG, "[client][callNativeModuleEnd]," + mInstanceId + "," + ((MethodInvoker) invoker).mMethod.getDeclaringClass() + "," + ((MethodInvoker) invoker).mMethod.getName() + "," + callBackId);
+            }
+          });
+          break;
+        }
+      }
+    }
+
+    if (invoker.isRunOnUIThread()) {
+      WXSDKManager.getInstance().postOnUiThread(new Runnable() {
+        @Override
+        public void run() {
+          if (invoker != null) {
+            try {
+              WXSDKInstance targetInstance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
+              if (null == targetInstance || targetInstance.isDestroy()){
+                return;
+              }
+              invoker.invoke(target, params);
+            } catch (Exception e) {
+              WXLogUtils.e("NativeInvokeHelper",target + " Invoker " + invoker.toString()+" exception:"+e);
+            }
+          }
+        }
+      }, 0);
+    } else {
+      return invoker.invoke(target, params);
+    }
+    return null;
+  }
+
+  protected Object[] prepareArguments(Type[] paramClazzs, JSONArray args) throws Exception {
+    Object[] params = new Object[paramClazzs.length];
+    Object value;
+    Type paramClazz;
+    for (int i = 0; i < paramClazzs.length; i++) {
+      paramClazz = paramClazzs[i];
+      if(i>=args.size()){
+        if(!paramClazz.getClass().isPrimitive()) {
+          params[i] = null;
+          continue;
+        }else {
+          throw new Exception("[prepareArguments] method argument list not match.");
+        }
+      }
+      value = args.get(i);
+
+      if (paramClazz == JSONObject.class) {
+        if(value instanceof  JSONObject || value == null) {
+          params[i] = value;
+        }else if (value instanceof String){
+          params[i] = JSON.parseObject(value.toString());
+        }
+      } else if(JSCallback.class == paramClazz){
+        if(value instanceof String){
+          params[i] = new SimpleJSCallback(mInstanceId,(String)value);
+        }else{
+          throw new Exception("Parameter type not match.");
+        }
+      } else {
+        params[i] = WXReflectionUtils.parseArgument(paramClazz,value);
+      }
+    }
+    return params;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/RequestHandler.java b/android/sdk/src/main/java/org/apache/weex/bridge/RequestHandler.java
new file mode 100644
index 0000000..fc87a67
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/RequestHandler.java
@@ -0,0 +1,155 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import static org.apache.weex.http.WXHttpUtil.KEY_USER_AGENT;
+
+import android.net.Uri;
+import android.support.annotation.Keep;
+import android.text.TextUtils;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXHttpListener;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXHttpAdapter;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.base.CalledByNative;
+import org.apache.weex.bridge.WXBridgeManager.BundType;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXRequest;
+import org.apache.weex.common.WXResponse;
+import org.apache.weex.http.WXHttpUtil;
+import org.apache.weex.utils.WXExceptionUtils;
+
+import org.apache.weex.utils.WXLogUtils;
+import java.util.HashMap;
+import java.util.Locale;
+
+public class RequestHandler {
+
+  @Keep
+  native void nativeInvokeOnSuccess(long callback, String script, String bundleType);
+  native void nativeInvokeOnFailed(long callback);
+
+  @CalledByNative
+  public static RequestHandler create() {
+    return new RequestHandler();
+  }
+
+  @CalledByNative
+  public void send(String instanceId, String url, long nativeCallback) {
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(url) ||
+        nativeCallback == 0 ||
+        !WXSDKManager.getInstance().getAllInstanceMap().containsKey(
+            instanceId)) {
+      return;
+    }
+
+    WXSDKManager manager = WXSDKManager.getInstance();
+    WXSDKInstance instance =
+        WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (instance == null)
+      return;
+    IWXHttpAdapter adapter = WXSDKManager.getInstance().getIWXHttpAdapter();
+
+    WXRequest wxRequest = new WXRequest();
+    wxRequest.url = manager.getURIAdapter()
+                        .rewrite(instance, URIAdapter.BUNDLE, Uri.parse(url))
+                        .toString();
+
+    if (wxRequest.paramMap == null) {
+      wxRequest.paramMap = new HashMap<>();
+    }
+    wxRequest.paramMap.put(
+        KEY_USER_AGENT, WXHttpUtil.assembleUserAgent(
+                            instance.getContext(), WXEnvironment.getConfig()));
+    wxRequest.paramMap.put("isBundleRequest", "true");
+    WXLogUtils.i("Eagle", String.format(Locale.ENGLISH, "Weex eagle is going to download script from %s", url));
+    adapter.sendRequest(wxRequest, new OnHttpListenerInner(instance, nativeCallback, url));
+  }
+
+  @Keep
+  @CalledByNative
+  public void getBundleType(String instanceId, final String content, final long nativeCallback){
+    BundType bundleType = WXBridgeManager.getInstance().getBundleType("", content);
+    final String bundleTypeStr = bundleType == null ? "Others" : bundleType.toString();
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if ("Others".equalsIgnoreCase(bundleTypeStr) && null != instance){
+      WXExceptionUtils.commitCriticalExceptionRT(
+          instanceId,
+          WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE,
+          "RequestHandler.onSuccess",
+          "eagle ->" +WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE.getErrorMsg(),
+          null
+      );
+    }
+    WXBridgeManager.getInstance().post(new Runnable() {
+      @Override
+      public void run() {
+        if(WXBridgeManager.getInstance().isJSFrameworkInit()) {
+          nativeInvokeOnSuccess(nativeCallback, content, bundleTypeStr);
+        }
+        else {
+          nativeInvokeOnFailed(nativeCallback);
+        }
+      }
+    });
+  }
+
+  class OnHttpListenerInner extends WXHttpListener {
+    private long sNativeCallback;
+
+    OnHttpListenerInner(WXSDKInstance instance, long nativeCallback, String bundlUrl) {
+      super(instance, bundlUrl);
+      sNativeCallback = nativeCallback;
+    }
+
+    @Override
+    public void onSuccess(WXResponse response) {
+        final String script = new String(response.originalData);
+        BundType bundleType = WXBridgeManager.getInstance().getBundleType("", script);
+        final String bundleTypeStr = bundleType == null ? "Others" : bundleType.toString();
+        if ("Others".equalsIgnoreCase(bundleTypeStr) && null != getInstance()){
+          WXExceptionUtils.commitCriticalExceptionRT(
+              getInstance().getInstanceId(),
+              WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE,
+              "RequestHandler.onSuccess",
+              "eagle ->" +WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE.getErrorMsg(),
+              null
+          );
+        }
+        WXBridgeManager.getInstance().post(new Runnable() {
+          @Override
+          public void run() {
+            if(WXBridgeManager.getInstance().isJSFrameworkInit()) {
+              nativeInvokeOnSuccess(sNativeCallback, script, bundleTypeStr);
+            }
+            else{
+              nativeInvokeOnFailed(sNativeCallback);
+            }
+          }
+        });
+    }
+
+    @Override
+    public void onFail(WXResponse response) {
+      nativeInvokeOnFailed(sNativeCallback);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/ResultCallback.java b/android/sdk/src/main/java/org/apache/weex/bridge/ResultCallback.java
new file mode 100644
index 0000000..203b3d8
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/ResultCallback.java
@@ -0,0 +1,23 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+public interface ResultCallback<T> {
+    void onReceiveResult(T result);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/ResultCallbackManager.java b/android/sdk/src/main/java/org/apache/weex/bridge/ResultCallbackManager.java
new file mode 100644
index 0000000..d945a0f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/ResultCallbackManager.java
@@ -0,0 +1,48 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import android.util.SparseArray;
+
+/**
+ * Manage async callbacks which waiting for the result of executing javascript
+ */
+/* default */ class ResultCallbackManager {
+    // Unique id for callback after executing js
+    private static long sCallbackId = 0;
+    // Map for save callbacks, key is id
+    private static SparseArray<ResultCallback> mResultCallbacks = new SparseArray<>();
+
+    // Generate unique id
+    static long generateCallbackId(ResultCallback callback) {
+        if (sCallbackId >= Integer.MAX_VALUE) {
+            sCallbackId = 0;
+        }
+        int id = (int) sCallbackId++;
+        mResultCallbacks.put(id, callback);
+        return id;
+    }
+
+    // Remove id from callback map
+    static ResultCallback removeCallbackById(long id) {
+        ResultCallback callback = mResultCallbacks.get((int) id);
+        mResultCallbacks.remove((int) id);
+        return callback;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/SimpleJSCallback.java b/android/sdk/src/main/java/org/apache/weex/bridge/SimpleJSCallback.java
new file mode 100644
index 0000000..ef86987
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/SimpleJSCallback.java
@@ -0,0 +1,61 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+/**
+ * Created by sospartan on 27/10/2016.
+ */
+public class SimpleJSCallback implements JSCallback {
+
+  String mInstanceId;
+  String mCallbackId;
+
+  private InvokerCallback mInvokerCallback;
+
+  public void setInvokerCallback(InvokerCallback callback) {
+    this.mInvokerCallback = callback;
+  }
+
+  interface InvokerCallback {
+    void onInvokeSuccess();
+  }
+
+  public String getCallbackId() {
+    return mCallbackId;
+  }
+
+  public SimpleJSCallback(String instanceId, String callbackId) {
+    this.mCallbackId = callbackId;
+    this.mInstanceId = instanceId;
+  }
+
+
+  @Override
+  public void invoke(Object data) {
+    WXBridgeManager.getInstance().callbackJavascript(mInstanceId, mCallbackId, data, false);
+    if (mInvokerCallback != null) {
+      mInvokerCallback.onInvokeSuccess();
+    }
+  }
+
+  @Override
+  public void invokeAndKeepAlive(Object data) {
+    WXBridgeManager.getInstance().callbackJavascript(mInstanceId, mCallbackId, data, true);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXBridge.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXBridge.java
new file mode 100755
index 0000000..05fd44d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXBridge.java
@@ -0,0 +1,946 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import android.text.TextUtils;
+import android.util.Log;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.base.CalledByNative;
+import org.apache.weex.common.IWXBridge;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXRenderStrategy;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.layout.ContentBoxMeasurement;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.performance.WXStateRecord;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXJsonUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXWsonJSONSwitch;
+import org.apache.weex.utils.tools.TimeCalculator;
+
+import java.io.Serializable;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+
+/**
+ * Communication interface for Java code and JavaScript code.
+ */
+
+    public class WXBridge implements IWXBridge {
+
+  private native int nativeInitFrameworkEnv(String framework, WXParams params, String cacheDir, boolean pieSupport);
+
+  private native int nativeInitFramework(String framework, WXParams params);
+
+  private native void nativeRefreshInstance(String instanceId, String namespace, String function, WXJSObject[] args);
+
+  private native int nativeExecJS(String instanceId, String name, String function, WXJSObject[] args);
+
+  private native int nativeExecJSService(String javascript);
+
+  public native byte[] nativeExecJSWithResult(String instanceId, String _namespace, String _function, WXJSObject[] args);
+  public native void nativeExecJSWithCallback(String instanceId, String _namespace, String _function, WXJSObject[] args, long callbackId);
+
+  public native int nativeCreateInstanceContext(String instanceId, String name, String function, WXJSObject[] args);
+
+  public native int nativeDestoryInstance(String instanceId, String name, String function, WXJSObject[] args);
+
+  public native String nativeExecJSOnInstance(String instanceId, String script, int type);
+
+  public native void nativeFireEventOnDataRenderNode(String instanceId, String ref, String type, String data, String domChanges);
+
+  public native void nativeInvokeCallbackOnDataRender(String instanceId, String callbackId, String data, boolean keepAlive);
+
+  public native void nativeRegisterModuleOnDataRenderNode( String data);
+
+  public native void nativeRegisterComponentOnDataRenderNode( String data);
+
+  private native void nativeTakeHeapSnapshot(String filename);
+
+  private native void nativeBindMeasurementToRenderObject(long ptr);
+
+  private native void nativeSetRenderContainerWrapContent(boolean wrap, String instanceId);
+
+  public native long[] nativeGetFirstScreenRenderTime(String instanceId);
+
+  public native long[] nativeGetRenderFinishTime(String instanceId);
+
+  private native void nativeSetDefaultHeightAndWidthIntoRootDom(String instanceId, float defaultWidth, float defaultHeight, boolean isWidthWrapContent, boolean isHeightWrapContent);
+
+  private native void nativeOnInstanceClose(String instanceId);
+
+  private native void nativeForceLayout(String instanceId);
+
+  private native boolean nativeNotifyLayout(String instanceId);
+
+  private native void nativeSetStyleWidth(String instanceId, String ref, float value);
+
+  private native void nativeSetStyleHeight(String instanceId, String ref, float value);
+
+  private native void nativeSetMargin(String instanceId, String ref, int edge, float value);
+
+  private native void nativeSetPadding(String instanceId, String ref, int edge, float value);
+
+  private native void nativeSetPosition(String instanceId, String ref, int edge, float value);
+
+  private native void nativeMarkDirty(String instanceId, String ref, boolean dirty);
+
+  private native void nativeSetDeviceDisplay(String instanceId, float width, float height, float scale);
+
+  private native void nativeRegisterCoreEnv(String key, String value);
+
+  private native void nativeResetWXBridge(Object bridge, String className);
+
+  private native void nativeSetInstanceRenderType(String instanceId, String renderType);
+
+  private native void nativeRemoveInstanceRenderType(String instanceId);
+
+  private native void nativeSetPageArgument(String instanceId, String key, String value);
+
+  public native void nativeOnInteractionTimeUpdate(String instanceId);
+
+  public native String nativeDumpIpcPageQueueInfo();
+
+  /**
+   * Update Init Framework Params
+   * */
+  private native void nativeUpdateInitFrameworkParams(String key, String value, String desc);
+
+  /**
+   * update global config,
+   * @param config params
+   * */
+  public native void nativeUpdateGlobalConfig(String config);
+
+  private native void nativeSetViewPortWidth(String instanceId, float viewPortWidth);
+  private native void nativeSetLogType(float type, float isPerf);
+
+  private native void nativeReloadPageLayout(String instanceId);
+
+  private native void nativeSetDeviceDisplayOfPage(String instanceId,float width,float height);
+
+  public static final boolean MULTIPROCESS = true;
+
+
+  @Override
+  public void updateInitFrameworkParams(String key, String value, String desc){
+    WXStateRecord.getInstance().recordAction("","updateInitFrameworkParams:");
+     nativeUpdateInitFrameworkParams(key, value, desc);
+  }
+
+  @Override
+  public void setLogType(float type, boolean isPerf) {
+    Log.e("WeexCore", "setLog" + WXEnvironment.sLogLevel.getValue() + "isPerf : " + isPerf);
+    nativeSetLogType(type, isPerf ? 1 : 0);
+  }
+
+  @Override
+  public int initFramework(String framework, WXParams params) {
+    return nativeInitFramework(framework, params);
+  }
+
+  @Override
+  public int initFrameworkEnv(String framework, WXParams params, String cacheDir, boolean pieSupport) {
+    if (MULTIPROCESS) {
+      WXStateRecord.getInstance().recordAction("","nativeInitFrameworkEnv:");
+      return nativeInitFrameworkEnv(framework, params, cacheDir, pieSupport);
+    } else {
+      WXStateRecord.getInstance().recordAction("","nativeInitFramework:");
+      return nativeInitFramework(framework, params);
+    }
+  }
+
+  @Override
+  public void refreshInstance(String instanceId, String namespace, String function, WXJSObject[] args) {
+    WXStateRecord.getInstance().recordAction(instanceId,"refreshInstance:"+namespace+","+function);
+    nativeRefreshInstance(instanceId, namespace, function, args);
+  }
+
+  @Override
+  public int execJS(String instanceId, String namespace, String function, WXJSObject[] args) {
+    WXStateRecord.getInstance().recordAction(instanceId,"execJS:"+namespace+","+function);
+    return nativeExecJS(instanceId, namespace, function, args);
+  }
+
+  @Override
+  public void execJSWithCallback(String instanceId, String namespace, String function, WXJSObject[] args, ResultCallback callback) {
+    WXStateRecord.getInstance().recordAction(instanceId,"execJSWithCallback:"+namespace+","+function);
+    if (callback == null) {
+      execJS(instanceId, namespace, function, args);
+    }
+    nativeExecJSWithCallback(instanceId, namespace, function, args,
+            ResultCallbackManager.generateCallbackId(callback));
+  }
+
+  @CalledByNative
+  public void onNativePerformanceDataUpdate(String instanceId,Map<String,String> map){
+    if (TextUtils.isEmpty(instanceId) || null == map || map.size() < 1){
+      return;
+    }
+    WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
+    if (null == instance || null == instance.getApmForInstance()){
+      return;
+    }
+    instance.getApmForInstance().updateNativePerformanceData(map);
+  }
+
+  // Result from js engine
+  @CalledByNative
+  public void onReceivedResult(long callbackId, byte[] result) {
+    WXStateRecord.getInstance().recordAction("onReceivedResult","callbackId"+callbackId);
+    ResultCallback callback = ResultCallbackManager.removeCallbackById(callbackId);
+    if (callback != null) {
+       callback.onReceiveResult(result);
+    }
+  }
+
+  @Override
+  public int execJSService(String javascript) {
+    WXStateRecord.getInstance().recordAction("execJSService","execJSService:");
+    return nativeExecJSService(javascript);
+  }
+
+
+  @Override
+  public void takeHeapSnapshot(String filename) {
+    nativeTakeHeapSnapshot(filename);
+  }
+
+  @Override
+  public int createInstanceContext(String instanceId, String name, String function, WXJSObject[] args) {
+    Log.e(TimeCalculator.TIMELINE_TAG,"createInstance :" + System.currentTimeMillis());
+    WXStateRecord.getInstance().recordAction(instanceId,"createInstanceContext:");
+    return nativeCreateInstanceContext(instanceId, name, function, args);
+  }
+
+  @Override
+  public int destoryInstance(String instanceId, String name, String function, WXJSObject[] args) {
+    WXStateRecord.getInstance().recordAction(instanceId,"destoryInstance:");
+    return nativeDestoryInstance(instanceId, name, function, args);
+  }
+
+  @Override
+  public String execJSOnInstance(String instanceId, String script, int type) {
+    WXStateRecord.getInstance().recordAction(instanceId,"execJSOnInstance:"+type);
+    return nativeExecJSOnInstance(instanceId, script, type);
+  }
+
+  public static final String TAG = "WXBridge";
+
+  /**
+   * JavaScript uses this methods to call Android code
+   *
+   * @param instanceId
+   * @param tasks
+   * @param callback
+   */
+  @CalledByNative
+  public int callNative(String instanceId, byte[] tasks, String callback) {
+    if("HeartBeat".equals(callback)) {
+      Log.e("HeartBeat instanceId", instanceId);
+      WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if(sdkInstance != null) {
+        sdkInstance.createInstanceFuncHeartBeat();
+      }
+      return IWXBridge.INSTANCE_RENDERING;
+    }
+
+    return callNative(instanceId, (JSONArray) JSON.parseArray(new String(tasks)), callback);
+  }
+
+  @Override
+  public int callNative(String instanceId, String tasks, String callback) {
+    try{
+      return callNative(instanceId, JSONArray.parseArray(tasks), callback);
+    }catch (Exception e){
+      WXLogUtils.e(TAG, "callNative throw exception: " + WXLogUtils.getStackTrace(e));
+      return IWXBridge.INSTANCE_RENDERING;
+    }
+  }
+
+  private int callNative(String instanceId, JSONArray tasks, String callback){
+    long start = System.currentTimeMillis();
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (instance != null) {
+      instance.firstScreenCreateInstanceTime(start);
+    }
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callNative(instanceId, tasks, callback);
+    } catch (Throwable e) {
+      WXLogUtils.e(TAG, "callNative throw exception:" + WXLogUtils.getStackTrace(e));
+    }
+
+    if (WXEnvironment.isApkDebugable()) {
+      if (errorCode == IWXBridge.DESTROY_INSTANCE) {
+        WXLogUtils.w("destroyInstance :" + instanceId + " JSF must stop callNative");
+      }
+    }
+    return errorCode;
+  }
+
+  @CalledByNative
+  public void reportJSException(String instanceId, String func, String exception) {
+    WXBridgeManager.getInstance().reportJSException(instanceId, func, exception);
+  }
+
+
+  /**
+   * Bridge module Js Method
+   * support Sync or Async through setting  Annotation as {@link JSMethod }
+   *
+   * @param instanceId Instance ID
+   * @param module     the name of module
+   * @param method     the name of method
+   * @param arguments  the arguments of the method
+   * @param options    option arguments for extending
+   * @return the result
+   */
+  @Override
+  @CalledByNative
+  public Object callNativeModule(String instanceId, String module, String method, byte[] arguments, byte[] options) {
+    try {
+      WXStateRecord.getInstance().recordAction(instanceId,"callNativeModule:"+module+"."+method);
+      long start = WXUtils.getFixUnixTime();
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      JSONArray argArray = null;
+      if (arguments != null){
+        // TODO use a better way
+        if (instance!=null && (instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER
+                || instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER_BINARY)){
+          try {
+            argArray = (JSONArray) JSON.parse(new String(arguments, "UTF-8"));
+          } catch (Exception e) {
+            // For wson use in data render mode
+            argArray = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(arguments);
+          }
+        } else {
+          argArray = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(arguments);
+        }
+      }
+      JSONObject optionsObj = null;
+      if (options != null) {
+        optionsObj = (JSONObject) WXWsonJSONSwitch.parseWsonOrJSON(options);
+      } else if (argArray != null) {
+        final WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+        if (sdkInstance != null) {
+          if (WXBridgeManager.BundType.Rax.equals(sdkInstance.bundleType)) {
+            Object weex_options__ = null;
+            for (Object object: argArray) {
+              if (object instanceof JSONObject && ((JSONObject) object).containsKey("__weex_options__")) {
+                weex_options__ = ((JSONObject) object).get("__weex_options__");
+              }
+            }
+
+            if (weex_options__ instanceof JSONObject)
+              optionsObj = (JSONObject) weex_options__;
+          }
+        }
+
+      }
+
+      Object object = WXBridgeManager.getInstance().callNativeModule(instanceId, module, method, argArray, optionsObj);
+
+      if (null != instance){
+        instance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_CALL_NATIVE_NUM,1);
+        instance.getApmForInstance().updateFSDiffStats(
+            WXInstanceApm.KEY_PAGE_STATS_FS_CALL_NATIVE_TIME,
+            WXUtils.getFixUnixTime()-start
+        );
+      }
+      if (instance!=null && (instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER
+          || instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER_BINARY)){
+        try {
+          if(object == null){
+            return new WXJSObject(null);
+          }
+          if(object.getClass() == WXJSObject.class){
+            return (WXJSObject) object;
+          }
+          return new WXJSObject(WXJSObject.JSON, WXJsonUtils.fromObjectToJSONString(object));
+        } catch (Exception e) {
+          // For wson use in data render mode
+          return WXWsonJSONSwitch.toWsonOrJsonWXJSObject(object);
+        }
+      } else {
+        return WXWsonJSONSwitch.toWsonOrJsonWXJSObject(object);
+      }
+    }catch (Exception e){
+      WXLogUtils.e(TAG,  e);
+      return new WXJSObject(null);
+    }
+  }
+
+  /**
+   * Bridge component Js Method
+   *
+   * @param instanceId   Instance ID
+   * @param ref the ref of component
+   * @param method       the name of method
+   * @param arguments    the arguments of the method
+   * @param options      option arguments for extending
+   */
+  @Override
+  @CalledByNative
+  public void callNativeComponent(String instanceId, String ref, String method, byte[] arguments, byte[] optionsData) {
+    WXStateRecord.getInstance().recordAction(instanceId,"callNativeComponent:"+method);
+    try{
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      JSONArray argArray = null;
+      if (arguments != null){
+        // TODO use a better way
+        if (instance!=null && (instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER
+            || instance.getRenderStrategy()== WXRenderStrategy.DATA_RENDER_BINARY)){
+          try {
+            argArray = (JSONArray) JSON.parse(new String(arguments, "UTF-8"));
+          } catch (Exception e) {
+            // For wson use in data render mode
+            argArray = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(arguments);
+          }
+        } else {
+          argArray = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(arguments);
+        }
+      }
+      Object options = WXWsonJSONSwitch.parseWsonOrJSON(optionsData);
+      WXBridgeManager.getInstance().callNativeComponent(instanceId, ref, method, argArray, options);
+    }catch (Exception e){
+      WXLogUtils.e(TAG,  e);
+    }
+  }
+
+  @Override
+  @CalledByNative
+  public void setTimeoutNative(String callbackId, String time) {
+    WXBridgeManager.getInstance().setTimeout(callbackId, time);
+  }
+
+  @Override
+  @CalledByNative
+  public void setJSFrmVersion(String version) {
+    if (version != null) {
+      WXEnvironment.JS_LIB_SDK_VERSION = version;
+    }
+    WXStateRecord.getInstance().onJSFMInit();
+  }
+
+  @Override
+  public void resetWXBridge(boolean remoteDebug) {
+    final String className = this.getClass().getName().replace('.', '/');
+    nativeResetWXBridge(this, className);
+  }
+
+  @Override
+  @CalledByNative
+  public int callUpdateFinish(String instanceId, byte[] tasks, String callback) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callUpdateFinish(instanceId, callback);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callCreateBody throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callRefreshFinish(String instanceId, byte[] tasks, String callback) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callRefreshFinish(instanceId, callback);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callCreateFinish throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public void reportServerCrash(String instanceId, String crashFile) {
+    WXLogUtils.e(TAG, "reportServerCrash instanceId:" + instanceId + " crashFile: " + crashFile);
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callReportCrashReloadPage(instanceId, crashFile);
+
+      // upload crash log
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "reloadPageNative throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+  }
+
+  @Override
+  @CalledByNative
+  public int callCreateBody(String instanceId, String componentType, String ref,
+                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
+                            float[] margins, float[] paddings, float[] borders) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+
+    try {
+      errorCode = WXBridgeManager.getInstance().callCreateBody(instanceId, componentType, ref,
+              styles, attributes, events, margins, paddings, borders);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callCreateBody throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callAddElement(String instanceId, String componentType, String ref, int index, String parentRef,
+                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
+                            float[] margins, float[] paddings, float[] borders,  boolean willLayout) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+
+    try {
+      errorCode = WXBridgeManager.getInstance().callAddElement(instanceId, componentType, ref, index, parentRef,
+              styles, attributes, events, margins, paddings, borders, willLayout);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        e.printStackTrace();
+        WXLogUtils.e(TAG, "callAddElement throw error:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callRemoveElement(String instanceId, String ref) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callRemoveElement(instanceId, ref);
+    } catch (Throwable e) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callRemoveElement throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callMoveElement(String instanceId, String ref, String parentref, int index) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callMoveElement(instanceId, ref, parentref, index);
+    } catch (Throwable e) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callMoveElement throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callAddEvent(String instanceId, String ref, String event) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callAddEvent(instanceId, ref, event);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      // if(WXEnvironment.isApkDebugable()){
+      WXLogUtils.e(TAG, "callAddEvent throw exception:" + WXLogUtils.getStackTrace(e));
+      // }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callRemoveEvent(String instanceId, String ref, String event) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callRemoveEvent(instanceId, ref, event);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callRemoveEvent throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callUpdateStyle(String instanceId, String ref,
+                             HashMap<String, Object> styles,
+                             HashMap<String, String> paddings,
+                             HashMap<String, String> margins,
+                             HashMap<String, String> borders) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callUpdateStyle(instanceId, ref, styles, paddings, margins, borders);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callUpdateStyle throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callUpdateAttrs(String instanceId, String ref, HashMap<String, String> attrs) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callUpdateAttrs(instanceId, ref, attrs);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callUpdateAttr throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callAddChildToRichtext(String instanceId, String nodeType, String ref, String parentRef, String richTextRef,
+                             HashMap<String, String> styles, HashMap<String, String> attrs){
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callAddChildToRichtext(instanceId, nodeType, ref, parentRef, richTextRef,
+              styles, attrs);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callAddChildToRichtext throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+  @Override
+  @CalledByNative
+  public int callRemoveChildFromRichtext(String instanceId, String ref, String parentRef, String richTextRef){
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callRemoveChildFromRichtext(instanceId, ref, parentRef, richTextRef);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callRemoveChildFromRichtext throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callUpdateRichtextStyle(String instanceId, String ref, HashMap<String, String> styles, String parentRef, String richTextRef){
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callUpdateRichtextStyle(instanceId, ref, styles, parentRef, richTextRef);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callUpdateRichtextStyle throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+  @Override
+  @CalledByNative
+  public int callUpdateRichtextChildAttr(String instanceId, String ref, HashMap<String, String> attrs, String parentRef, String richTextRef){
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callUpdateRichtextChildAttr(instanceId, ref, attrs, parentRef, richTextRef);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callUpdateRichtextChildAttr throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+
+  @Override
+  @CalledByNative
+  public int callLayout(String instanceId, String ref, int top, int bottom, int left, int right, int height, int width, boolean isRTL, int index) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callLayout(instanceId, ref, top, bottom, left, right, height, width, isRTL, index);
+    } catch (Throwable e) {
+      //catch everything during call native.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callLayout throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callCreateFinish(String instanceId) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callCreateFinish(instanceId);
+    } catch (Throwable e) {
+      WXLogUtils.e(TAG, "callCreateFinish throw exception:" + WXLogUtils.getStackTrace(e));
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callRenderSuccess(String instanceId) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callRenderSuccess(instanceId);
+    } catch (Throwable e) {
+      WXLogUtils.e(TAG, "callCreateFinish throw exception:" + WXLogUtils.getStackTrace(e));
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callAppendTreeCreateFinish(String instanceId, String ref) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callAppendTreeCreateFinish(instanceId, ref);
+    } catch (Throwable e) {
+      WXLogUtils.e(TAG, "callAppendTreeCreateFinish throw exception:" + WXLogUtils.getStackTrace(e));
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public int callHasTransitionPros(String instanceId, String ref, HashMap<String, String> styles) {
+    int errorCode = IWXBridge.INSTANCE_RENDERING;
+    try {
+      errorCode = WXBridgeManager.getInstance().callHasTransitionPros(instanceId, ref, styles);
+    } catch (Throwable e) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "callHasTransitionPros throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return errorCode;
+  }
+
+  @Override
+  @CalledByNative
+  public ContentBoxMeasurement getMeasurementFunc(String instanceId, long renderObjectPtr) {
+    ContentBoxMeasurement obj = null;
+    try {
+      obj = WXBridgeManager.getInstance().getMeasurementFunc(instanceId, renderObjectPtr);
+    } catch (Throwable e) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(TAG, "getMeasurementFunc throw exception:" + WXLogUtils.getStackTrace(e));
+      }
+    }
+    return obj;
+  }
+
+  @Override
+  public void bindMeasurementToRenderObject(long ptr){
+    nativeBindMeasurementToRenderObject(ptr);
+  }
+
+  @Override
+  public void setRenderContainerWrapContent(boolean wrap, String instanceId) {
+    nativeSetRenderContainerWrapContent(wrap, instanceId);
+  }
+
+  @Override
+  public long[] getFirstScreenRenderTime(String instanceId) {
+    return nativeGetFirstScreenRenderTime(instanceId);
+  }
+
+  @Override
+  public long[] getRenderFinishTime(String instanceId) {
+    return nativeGetRenderFinishTime(instanceId);
+  }
+
+  @Override
+  public void setDefaultHeightAndWidthIntoRootDom(String instanceId, float defaultWidth, float defaultHeight, boolean isWidthWrapContent, boolean isHeightWrapContent) {
+    nativeSetDefaultHeightAndWidthIntoRootDom(instanceId, defaultWidth, defaultHeight, isWidthWrapContent, isHeightWrapContent);
+  }
+
+  @Override
+  public void onInstanceClose(String instanceId) {
+    nativeOnInstanceClose(instanceId);
+  }
+
+  @Override
+  public void forceLayout(String instanceId) {
+    nativeForceLayout(instanceId);
+  }
+
+  @Override
+  public boolean notifyLayout(String instanceId) {
+    return nativeNotifyLayout(instanceId);
+  }
+
+  @Override
+  public void setStyleWidth(String instanceId, String ref, float value) {
+    nativeSetStyleWidth(instanceId, ref, value);
+  }
+
+  @Override
+  public void setMargin(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
+    nativeSetMargin(instanceId, ref, edge.ordinal(), value);
+  }
+
+  @Override
+  public void setPadding(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
+    nativeSetPadding(instanceId, ref, edge.ordinal(), value);
+  }
+
+  @Override
+  public void setPosition(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
+    nativeSetPosition(instanceId, ref, edge.ordinal(), value);
+  }
+
+  @Override
+  public void markDirty(String instanceId, String ref, boolean dirty) {
+    nativeMarkDirty(instanceId, ref, dirty);
+  }
+
+  @Override
+  public void setDeviceDisplay(String instanceId, float width, float height, float scale) {
+    nativeSetDeviceDisplay(instanceId, width, height, scale);
+  }
+
+  @Override
+  public void setStyleHeight(String instanceId, String ref, float value) {
+    nativeSetStyleHeight(instanceId, ref, value);
+  }
+
+  @Override
+  public void setInstanceRenderType(String instanceId, String renderType){
+    if(TextUtils.isEmpty(renderType)){
+       return;
+    }
+    nativeSetInstanceRenderType(instanceId, renderType);
+  }
+
+  @Override
+  public void setViewPortWidth(String instanceId,float viewPortWidth){
+    nativeSetViewPortWidth(instanceId,viewPortWidth);
+  }
+
+  @Override
+  public void removeInstanceRenderType(String instanceId){
+      nativeRemoveInstanceRenderType(instanceId);
+  }
+
+  @Override
+  public void setPageArgument(String instanceId, String key, String value){
+      nativeSetPageArgument(instanceId, key, value);
+  }
+
+  @Override
+  public void registerCoreEnv(String key, String value) {
+    nativeRegisterCoreEnv(key, value);
+  }
+
+  @CalledByNative
+  public void reportNativeInitStatus(String statusCode, String errorMsg) {
+    if (WXErrorCode.WX_JS_FRAMEWORK_INIT_SINGLE_PROCESS_SUCCESS.getErrorCode().equals(statusCode)
+            || WXErrorCode.WX_JS_FRAMEWORK_INIT_FAILED.getErrorCode().equals(statusCode)) {
+      IWXUserTrackAdapter userTrackAdapter = WXSDKManager.getInstance().getIWXUserTrackAdapter();
+      if (userTrackAdapter != null) {
+        Map<String, Serializable> params = new HashMap<>(3);
+        params.put(IWXUserTrackAdapter.MONITOR_ERROR_CODE, statusCode);
+        params.put(IWXUserTrackAdapter.MONITOR_ARG, "InitFrameworkNativeError");
+        params.put(IWXUserTrackAdapter.MONITOR_ERROR_MSG, errorMsg);
+        WXLogUtils.e("reportNativeInitStatus is running and errorCode is " + statusCode + " And errorMsg is " + errorMsg);
+        userTrackAdapter.commit(null, null, IWXUserTrackAdapter.INIT_FRAMEWORK, null, params);
+      }
+
+      return;
+    }
+
+    if (WXErrorCode.WX_JS_FRAMEWORK_INIT_FAILED_PARAMS_NULL.getErrorCode().equals(statusCode)) {
+      WXExceptionUtils.commitCriticalExceptionRT(null, WXErrorCode.WX_JS_FRAMEWORK_INIT_FAILED_PARAMS_NULL,
+              "WeexProxy::initFromParam()",
+              WXErrorCode.WX_JS_FRAMEWORK_INIT_FAILED_PARAMS_NULL.getErrorMsg() + ": " + errorMsg,
+              null);
+      return;
+    }
+
+    for (WXErrorCode e : WXErrorCode.values()) {
+      if (e.getErrorType().equals(WXErrorCode.ErrorType.NATIVE_ERROR)
+              && e.getErrorCode().equals(statusCode)) {
+        WXExceptionUtils.commitCriticalExceptionRT(null, e, "initFramework", errorMsg, null);
+        break;
+      }
+    }
+  }
+
+  public void fireEventOnDataRenderNode(String instanceId, String ref, String type, String data, String domChanges) {
+    nativeFireEventOnDataRenderNode(instanceId,ref,type,data, domChanges);
+  }
+
+  public void invokeCallbackOnDataRender(String instanceId, String callbackId, String data, boolean keepAlive) {
+    nativeInvokeCallbackOnDataRender(instanceId,callbackId,data, keepAlive);
+  }
+
+  public void registerModuleOnDataRenderNode(String data) {
+    nativeRegisterModuleOnDataRenderNode(data);
+  }
+
+  public void registerComponentOnDataRenderNode(String data) {
+    nativeRegisterComponentOnDataRenderNode(data);
+  }
+  public void reloadPageLayout(String instanceId){
+    nativeReloadPageLayout(instanceId);
+  }
+
+  public void setDeviceDisplayOfPage(String instanceId, float width, float height){
+    nativeSetDeviceDisplayOfPage(instanceId,width,height);
+  }
+
+  @CalledByNative
+  @Override
+  public void setPageDirty(String instanceId, boolean dirty) {
+    WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if(sdkInstance != null) {
+      sdkInstance.setPageDirty(dirty);
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXBridgeManager.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXBridgeManager.java
new file mode 100755
index 0000000..c7873c3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXBridgeManager.java
@@ -0,0 +1,3686 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import static org.apache.weex.bridge.WXModuleManager.createDomModule;
+
+import android.content.Context;
+import android.net.Uri;
+import android.os.Build;
+import android.os.Handler;
+import android.os.Handler.Callback;
+import android.os.Looper;
+import android.os.Message;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.support.annotation.UiThread;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+import android.util.Log;
+import android.util.Pair;
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.Script;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKEngine;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.adapter.IWXJSExceptionAdapter;
+import org.apache.weex.adapter.IWXJsFileLoaderAdapter;
+import org.apache.weex.adapter.IWXJscProcessManager;
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.common.IWXBridge;
+import org.apache.weex.common.IWXDebugConfig;
+import org.apache.weex.common.WXConfig;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXException;
+import org.apache.weex.common.WXJSBridgeMsgType;
+import org.apache.weex.common.WXJSExceptionInfo;
+import org.apache.weex.common.WXRefreshData;
+import org.apache.weex.common.WXRenderStrategy;
+import org.apache.weex.common.WXRuntimeException;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.jsEngine.JSEngine;
+import org.apache.weex.layout.ContentBoxMeasurement;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.performance.WXStateRecord;
+import org.apache.weex.ui.WXComponentRegistry;
+import org.apache.weex.ui.WXRenderManager;
+import org.apache.weex.ui.action.ActionReloadPage;
+import org.apache.weex.ui.action.BasicGraphicAction;
+import org.apache.weex.ui.action.GraphicActionAddChildToRichtext;
+import org.apache.weex.ui.action.GraphicActionAddElement;
+import org.apache.weex.ui.action.GraphicActionAddEvent;
+import org.apache.weex.ui.action.GraphicActionAppendTreeCreateFinish;
+import org.apache.weex.ui.action.GraphicActionCreateBody;
+import org.apache.weex.ui.action.GraphicActionCreateFinish;
+import org.apache.weex.ui.action.GraphicActionLayout;
+import org.apache.weex.ui.action.GraphicActionMoveElement;
+import org.apache.weex.ui.action.GraphicActionRefreshFinish;
+import org.apache.weex.ui.action.GraphicActionRemoveChildFromRichtext;
+import org.apache.weex.ui.action.GraphicActionRemoveElement;
+import org.apache.weex.ui.action.GraphicActionRemoveEvent;
+import org.apache.weex.ui.action.GraphicActionRenderSuccess;
+import org.apache.weex.ui.action.GraphicActionUpdateAttr;
+import org.apache.weex.ui.action.GraphicActionUpdateRichtextAttr;
+import org.apache.weex.ui.action.GraphicActionUpdateRichtextStyle;
+import org.apache.weex.ui.action.GraphicActionUpdateStyle;
+import org.apache.weex.ui.action.GraphicPosition;
+import org.apache.weex.ui.action.GraphicSize;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.module.WXDomModule;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXFileUtils;
+import org.apache.weex.utils.WXJsonUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import org.apache.weex.utils.WXWsonJSONSwitch;
+import org.apache.weex.utils.batch.BactchExecutor;
+import org.apache.weex.utils.batch.Interceptor;
+import org.apache.weex.utils.tools.LogDetail;
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileReader;
+import java.io.InputStreamReader;
+import java.io.Serializable;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Method;
+import java.text.DateFormat;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+import java.util.Stack;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
+import java.util.regex.Pattern;
+
+/**
+ * Manager class for communication between JavaScript and Android.
+ * <ol>
+ * <li>
+ * Handle Android to JavaScript call, can be one of the following
+ * <ul>
+ * <li>{@link #createInstance(String, String, Map, String)}</li>
+ * <li>{@link #destroyInstance(String)}</li>
+ * <li>{@link #refreshInstance(String, WXRefreshData)}</li>
+ * <li>{@link #registerModules(Map)}</li>
+ * <li>{@link #registerComponents(List)}</li>
+ * <li>{@link #invokeCallJSBatch(Message)}</li>
+ * </ul>
+ * </li>
+ * <li>
+ * Handle JavaScript to Android call
+ * </li>
+ * <li>
+ * Handle next tick of message.
+ * </li>
+ * </ol>
+ */
+public class WXBridgeManager implements Callback, BactchExecutor {
+
+  private static Class clazz_debugProxy = null;
+  public static final String METHOD_CREATE_INSTANCE = "createInstance";
+  public static final String METHOD_CREATE_PAGE_WITH_CONTENT = "CreatePageWithContent";
+  public static final String METHOD_UPDATE_COMPONENT_WITH_DATA = "UpdateComponentData";
+  private static final String METHOD_POST_TASK_TO_MSG_LOOP = "PostTaskToMsgLoop";
+  private static final String METHOD_JSFM_NOT_INIT_IN_EAGLE_MODE = "JsfmNotInitInEagleMode";
+  private static final String METHOD_MOVE_RENDER_OBJECT = "RenderPage::MoveRenderObject";
+  public static final String METHOD_DESTROY_INSTANCE = "destroyInstance";
+  public static final String METHOD_CALL_JS = "callJS";
+  public static final String METHOD_SET_TIMEOUT = "setTimeoutCallback";
+  public static final String METHOD_REGISTER_MODULES = "registerModules";
+  public static final String METHOD_REGISTER_COMPONENTS = "registerComponents";
+  public static final String METHOD_FIRE_EVENT = "fireEvent";
+  public static final String METHD_FIRE_EVENT_SYNC = "fireEventSync";
+  public static final String METHD_COMPONENT_HOOK_SYNC = "componentHook";
+  public static final String METHOD_CALLBACK = "callback";
+  public static final String METHOD_REFRESH_INSTANCE = "refreshInstance";
+  public static final String METHOD_FIRE_EVENT_ON_DATA_RENDER_NODE = "fireEventOnDataRenderNode";
+  public static final String METHOD_NOTIFY_TRIM_MEMORY = "notifyTrimMemory";
+  public static final String METHOD_NOTIFY_SERIALIZE_CODE_CACHE =
+          "notifySerializeCodeCache";
+  public static final String METHOD_CREATE_INSTANCE_CONTEXT = "createInstanceContext";
+
+  public static final String KEY_METHOD = "method";
+  public static final String KEY_ARGS = "args";
+
+  // args
+  public static final String COMPONENT = "component";
+  public static final String REF = "ref";
+  public static final String MODULE = "module";
+  public static final String METHOD = "method";
+  public static final String KEY_PARAMS = "params";
+  public static final String ARGS = "args";
+  public static final String OPTIONS = "options";
+  public static final String INITLOGFILE = "/jsserver_start.log";
+  private static final String NON_CALLBACK = "-1";
+  private static final String UNDEFINED = "undefined";
+  private static final String BUNDLE_TYPE = "bundleType";
+  private static final String RENDER_STRATEGY = "renderStrategy";
+  private static final int INIT_FRAMEWORK_OK = 1;
+  private static final int CRASHREINIT = 50;
+  static volatile WXBridgeManager mBridgeManager;
+  private static long LOW_MEM_VALUE = 120;
+  public volatile static int reInitCount = 1;
+  private volatile static int sInitFrameWorkCount = 0;
+  private static String crashUrl = null;
+  private static long lastCrashTime = 0;
+
+  private static String mRaxApi = null;
+//  private static String mRaxExtApi = null;
+
+  // add for clound setting, default value is true
+  // can use it to control weex sandbox
+  // if true will open weex sandbox for multi context
+  private volatile static boolean isSandBoxContext = true;
+
+  // add for cloud setting, default value is false.
+  // weexcore use single process or not
+  private static boolean isUseSingleProcess = false;
+  // add for cloud setting, default value is false.
+  // jsEngine use multiThread or not
+  private volatile static boolean isJsEngineMultiThreadEnable = false;
+
+  public enum BundType {
+    Vue,
+    Rax,
+    Others
+  };
+
+  private static final boolean BRIDGE_LOG_SWITCH = false;
+
+  /**
+   * Whether JS Framework(main.js) has been initialized.
+   */
+  private volatile static boolean mInit = false;
+
+  private static String globalConfig = "none";
+  private static String GLOBAL_CONFIG_KEY = "global_switch_config";
+
+  private static Map<String, String> mWeexCoreEnvOptions = new HashMap<>();
+
+  /**
+   * package
+   **/
+  Handler mJSHandler;
+  /**
+   * next tick tasks, can set priority
+   */
+  private WXHashMap<String, ArrayList<WXHashMap<String, Object>>> mNextTickTasks = new WXHashMap<>();
+  /**
+   * JSThread
+   */
+  private WXThread mJSThread;
+  private IWXBridge mWXBridge;
+  private Object mWxDebugProxy;
+
+  private boolean mMock = false;
+
+  private List<Map<String, Object>> mRegisterComponentFailList = new ArrayList<>(8);
+  private List<Map<String, Object>> mRegisterModuleFailList = new ArrayList<>(8);
+  private List<String> mRegisterServiceFailList = new ArrayList<>(8);
+  private HashSet<String> mDestroyedInstanceId = new HashSet<>();
+  private StringBuilder mLodBuilder = new StringBuilder(50);
+  private Interceptor mInterceptor;
+  private WXParams mInitParams;
+
+  private WXBridgeManager() {
+    initWXBridge(WXEnvironment.sRemoteDebugMode);
+    mJSThread = new WXThread("WeexJSBridgeThread", this);
+    mJSHandler = mJSThread.getHandler();
+  }
+
+  public static WXBridgeManager getInstance() {
+    if (mBridgeManager == null) {
+      synchronized (WXBridgeManager.class) {
+        if (mBridgeManager == null) {
+          mBridgeManager = new WXBridgeManager();
+        }
+      }
+    }
+    return mBridgeManager;
+  }
+
+  public void setUseSingleProcess(final boolean flag) {
+    if (flag != isUseSingleProcess) {
+      isUseSingleProcess = flag;
+//      //we should reinit framework if js framework has been initialized
+//      if (isJSFrameworkInit()) {
+//        if (isJSThread()) {
+//          WXSDKEngine.reload();
+//        } else {
+//          post(new Runnable() {
+//            @Override
+//            public void run() {
+//              WXSDKEngine.reload();
+//            }
+//          });
+//        }
+//      }
+    }
+  }
+
+  public void onInteractionTimeUpdate(final String instanceId){
+    post(new Runnable() {
+      @Override
+      public void run() {
+        if (mWXBridge instanceof WXBridge ){
+          ((WXBridge)mWXBridge).nativeOnInteractionTimeUpdate(instanceId);
+        }
+      }
+    });
+  }
+
+  public boolean jsEngineMultiThreadEnable() {
+    return isJsEngineMultiThreadEnable;
+  }
+
+  public void checkJsEngineMultiThread() {
+    boolean flag = false;
+    IWXJscProcessManager wxJscProcessManager = WXSDKManager.getInstance().getWXJscProcessManager();
+    if(wxJscProcessManager!=null) {
+      flag = wxJscProcessManager.enableBackupThread();
+    }
+
+    if(flag == WXBridgeManager.isJsEngineMultiThreadEnable) {
+        return;
+    }
+
+    WXBridgeManager.isJsEngineMultiThreadEnable = flag;
+    //we should reinit framework if js framework has been initialized
+    if (isJSFrameworkInit()) {
+      if (isJSThread()) {
+        WXSDKEngine.reload();
+      } else {
+        post(new Runnable() {
+          @Override
+          public void run() {
+            WXSDKEngine.reload();
+          }
+        });
+      }
+    }
+  }
+  public void setSandBoxContext(final boolean flag) {
+    if (flag != isSandBoxContext) {
+      isSandBoxContext = flag;
+      // use diff context reinit jsf
+      if (isJSThread()) {
+
+        setJSFrameworkInit(false);
+        WXModuleManager.resetAllModuleState();
+        String jsf = "";
+        if (!isSandBoxContext) {
+          jsf = WXFileUtils.loadAsset("main.js", WXEnvironment.getApplication());
+        } else {
+          jsf = WXFileUtils.loadAsset("weex-main-jsfm.js", WXEnvironment.getApplication());
+        }
+        initFramework(jsf);
+        WXServiceManager.reload();
+        WXModuleManager.reload();
+        WXComponentRegistry.reload();
+      } else {
+        post(new Runnable() {
+          @Override
+          public void run() {
+            setJSFrameworkInit(false);
+            WXModuleManager.resetAllModuleState();
+            String jsf = "";
+            if (!isSandBoxContext) {
+              jsf = WXFileUtils.loadAsset("main.js", WXEnvironment.getApplication());
+            } else {
+              jsf = WXFileUtils.loadAsset("weex-main-jsfm.js", WXEnvironment.getApplication());
+            }
+            initFramework(jsf);
+            WXServiceManager.reload();
+            WXModuleManager.reload();
+            WXComponentRegistry.reload();
+          }
+        });
+      }
+    }
+  }
+
+  // setJSFrameworkInit and isJSFrameworkInit may use on diff thread
+  // use volatile
+  @RestrictTo(Scope.LIBRARY)
+  boolean isJSFrameworkInit() {
+    return mInit;
+  }
+
+  private void setJSFrameworkInit(boolean init) {
+    mInit = init;
+    WXStateRecord.getInstance().recoreJsfmInitHistory("setJsfmInitFlag:"+init);
+    if (init == true) {
+      onJsFrameWorkInitSuccees();
+      JSEngine.getInstance().engineInitFinished();
+    }
+  }
+
+  private void initWXBridge(boolean remoteDebug) {
+    if (remoteDebug && WXEnvironment.isApkDebugable()) {
+      WXEnvironment.sDebugServerConnectable = true;
+    }
+
+    if (WXEnvironment.sDebugServerConnectable && (WXEnvironment.isApkDebugable() || WXEnvironment.sForceEnableDevTool)) {
+      if (WXEnvironment.getApplication() != null) {
+        try {
+          if (clazz_debugProxy == null) {
+            clazz_debugProxy = Class.forName("com.taobao.weex.devtools.debug.DebugServerProxy");
+          }
+          if (clazz_debugProxy != null) {
+            Constructor constructor = clazz_debugProxy.getConstructor(Context.class, IWXDebugConfig.class);
+            if (constructor != null) {
+              mWxDebugProxy = constructor.newInstance(WXEnvironment.getApplication(),
+                      new IWXDebugConfig() {
+                        @Override
+                        public WXBridgeManager getWXJSManager() {
+                          return WXBridgeManager.this;
+                        }
+
+                        @Override
+                        public WXDebugJsBridge getWXDebugJsBridge() {
+                          return new WXDebugJsBridge();
+                        }
+                      });
+              if (mWxDebugProxy != null) {
+                Method method_start = clazz_debugProxy.getMethod("start");
+                if (method_start != null) {
+                  method_start.invoke(mWxDebugProxy);
+                }
+              }
+            }
+          }
+        } catch (Throwable e) {
+          //Ignore, It will throw Exception on Release environment
+        }
+        WXServiceManager.execAllCacheJsService();
+      } else {
+        WXLogUtils.e("WXBridgeManager", "WXEnvironment.sApplication is null, skip init Inspector");
+      }
+    }
+    if (remoteDebug && mWxDebugProxy != null) {
+      try {
+        if (clazz_debugProxy == null ) {
+          clazz_debugProxy = Class.forName("com.taobao.weex.devtools.debug.DebugServerProxy");
+        }
+        if (clazz_debugProxy != null) {
+          Method method_getWXBridge = clazz_debugProxy.getMethod("getWXBridge");
+          if (method_getWXBridge != null) {
+            mWXBridge = (IWXBridge) method_getWXBridge.invoke(mWxDebugProxy);
+          }
+        }
+      } catch (Throwable e) {
+        //Ignore, It will throw Exception on Release environment
+      }
+    } else {
+      mWXBridge = new WXBridge();
+    }
+  }
+
+  public String dumpIpcPageInfo(){
+    if (mWXBridge instanceof WXBridge){
+      return ((WXBridge)mWXBridge).nativeDumpIpcPageQueueInfo();
+    }
+    return "";
+  }
+
+  public boolean isRebootExceedLimit(){
+    return reInitCount > CRASHREINIT;
+  }
+
+  public void stopRemoteDebug() {
+    if (mWxDebugProxy != null) {
+      try {
+        if (clazz_debugProxy == null) {
+          clazz_debugProxy = Class.forName("com.taobao.weex.devtools.debug.DebugServerProxy");
+        }
+        if (clazz_debugProxy != null) {
+          Method method_stop = clazz_debugProxy.getMethod("stop", boolean.class);
+          if (method_stop != null) {
+            method_stop.invoke(mWxDebugProxy, true);
+          }
+        }
+      } catch (Throwable e) {
+        //Ignore, It will throw Exception on Release environment
+      }
+    }
+  }
+
+  public Object callModuleMethod(String instanceId, String moduleStr, String methodStr, JSONArray args) {
+    return callModuleMethod(instanceId, moduleStr, methodStr, args, null);
+  }
+
+  public Object callModuleMethod(String instanceId, String moduleStr, String methodStr, JSONArray args, JSONObject options) {
+    WXSDKInstance wxsdkInstance = WXSDKManager.getInstance()
+            .getSDKInstance(instanceId);
+    if (wxsdkInstance == null) {
+      return null;
+    }
+    if (wxsdkInstance.isNeedValidate()
+            && WXSDKManager.getInstance().getValidateProcessor() != null) {
+      WXValidateProcessor.WXModuleValidateResult validateResult = WXSDKManager
+              .getInstance().getValidateProcessor()
+              .onModuleValidate(wxsdkInstance, moduleStr, methodStr, args, options);
+      if (validateResult == null) {
+        return null;
+      }
+      if (validateResult.isSuccess) {
+        return WXModuleManager.callModuleMethod(instanceId, moduleStr, methodStr,
+                args);
+      } else {
+        JSONObject validateInfo = validateResult.validateInfo;
+        if (validateInfo != null) {
+          WXLogUtils.e("[WXBridgeManager] module validate fail. >>> " + validateInfo.toJSONString());
+        }
+        return validateInfo;
+      }
+    }
+    try {
+      return WXModuleManager.callModuleMethod(instanceId, moduleStr, methodStr, args);
+    }catch(NumberFormatException e){
+      ArrayMap<String, String> ext = new ArrayMap<>();
+      ext.put("moduleName", moduleStr);
+      ext.put("methodName", methodStr);
+      ext.put("args", args.toJSONString());
+      WXLogUtils.e("[WXBridgeManager] callNative : numberFormatException when parsing string to numbers in args", ext.toString());
+      return null;
+    }
+  }
+
+  /**
+   * Model switch. For now, debug model and release model are supported
+   */
+  public void restart() {
+    setJSFrameworkInit(false);
+    WXModuleManager.resetAllModuleState();
+    initWXBridge(WXEnvironment.sRemoteDebugMode);
+    mWXBridge.resetWXBridge(WXEnvironment.sRemoteDebugMode);
+  }
+
+  /**
+   * Set current Instance
+   *
+   * @param instanceId {@link WXSDKInstance#mInstanceId}
+   */
+  public synchronized void setStackTopInstance(final String instanceId) {
+    post(new Runnable() {
+
+      @Override
+      public void run() {
+        mNextTickTasks.setStackTopInstance(instanceId);
+      }
+    },instanceId, null, null);
+  }
+
+  @Override
+  public void post(Runnable r) {
+      postWithName(r,null,null);
+  }
+
+  public void postWithName(Runnable r, WXSDKInstance instance, String runnableName) {
+   Runnable secure = WXThread.secure(r,instance, runnableName);
+    if (mInterceptor != null && mInterceptor.take(secure)) {
+      //task is token by the interceptor
+      return;
+    }
+    if (mJSHandler == null) {
+      return;
+    }
+
+    mJSHandler.post(secure);
+  }
+
+  @Override
+  public void setInterceptor(Interceptor interceptor) {
+    mInterceptor = interceptor;
+  }
+
+  public void post(Runnable r, Object token, WXSDKInstance instance, String runnableName) {
+    if (mJSHandler == null) {
+      return;
+    }
+
+    Message m = Message.obtain(mJSHandler, WXThread.secure(r, instance, runnableName));
+    m.obj = token;
+    m.sendToTarget();
+  }
+
+  public void post(Runnable r, Object token) {
+    post(r, token, null, null);
+  }
+
+  public void postDelay(Runnable r,long delayMillis){
+    if (mJSHandler == null) {
+      return;
+    }
+    mJSHandler.postDelayed(WXThread.secure(r),delayMillis);
+  }
+
+  void setTimeout(String callbackId, String time) {
+    Message message = Message.obtain();
+    message.what = WXJSBridgeMsgType.SET_TIMEOUT;
+    TimerInfo timerInfo = new TimerInfo();
+    timerInfo.callbackId = callbackId;
+    timerInfo.time = (long) Float.parseFloat(time);
+    message.obj = timerInfo;
+
+    mJSHandler.sendMessageDelayed(message, timerInfo.time);
+  }
+
+  public void sendMessageDelayed(Message message, long delayMillis) {
+    if (message == null || mJSHandler == null || mJSThread == null
+            || !mJSThread.isWXThreadAlive() || mJSThread.getLooper() == null) {
+      return;
+    }
+    mJSHandler.sendMessageDelayed(message, delayMillis);
+  }
+
+  public void removeMessage(int what, Object obj) {
+    if (mJSHandler == null || mJSThread == null
+            || !mJSThread.isWXThreadAlive() || mJSThread.getLooper() == null) {
+      return;
+    }
+    mJSHandler.removeMessages(what, obj);
+  }
+
+  public Object callNativeModule(String instanceId, String module, String method, JSONArray arguments, Object options) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(module) || TextUtils.isEmpty(method)) {
+      WXLogUtils.d("[WXBridgeManager] call callNativeModule arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callNativeModule",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callNativeModule >>>> instanceId:").append(instanceId)
+              .append(", module:").append(module).append(", method:").append(method).append(", arguments:").append(arguments);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    try {
+      if (WXDomModule.WXDOM.equals(module)) {
+        WXDomModule dom = WXModuleManager.getDomModule(instanceId);
+        return dom.callDomMethod(method, arguments);
+      } else {
+        return callModuleMethod(instanceId, module,
+              method, arguments);
+      }
+    } catch (Exception e) {
+      String err = "[WXBridgeManager] callNative exception: " + WXLogUtils.getStackTrace(e);
+      WXLogUtils.e(err);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callNativeModule",
+              err, null);
+    }
+
+    return null;
+  }
+
+  public Object callNativeModule(String instanceId, String module, String method, JSONArray arguments, JSONObject options) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(module) || TextUtils.isEmpty(method)) {
+      WXLogUtils.d("[WXBridgeManager] call callNativeModule arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callNativeModule",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callNativeModule >>>> instanceId:").append(instanceId)
+              .append(", module:").append(module).append(", method:").append(method).append(", arguments:").append(arguments);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    try {
+      if (WXDomModule.WXDOM.equals(module)) {
+        WXDomModule dom = WXModuleManager.getDomModule(instanceId);
+        if(dom != null){
+          return dom.callDomMethod(method, arguments);
+        } else {
+          createDomModule(WXSDKManager.getInstance().getSDKInstance(instanceId));
+        }
+      } else {
+        return callModuleMethod(instanceId, module,
+              method, arguments, options);
+      }
+    } catch (Exception e) {
+      String err = "[WXBridgeManager] callNativeModule exception: " + WXLogUtils.getStackTrace(e);
+      WXLogUtils.e(err);
+    }
+
+    return null;
+  }
+
+  public Object callNativeComponent(String instanceId, String componentRef, String method, JSONArray arguments, Object options) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(componentRef) || TextUtils.isEmpty(method)) {
+      WXLogUtils.d("[WXBridgeManager] call callNativeComponent arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callNativeComponent",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callNativeComponent >>>> instanceId:").append(instanceId)
+              .append(", componentRef:").append(componentRef).append(", method:").append(method).append(", arguments:").append(arguments);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    try {
+      WXDomModule dom = WXModuleManager.getDomModule(instanceId);
+      if (null != dom){
+        dom.invokeMethod(componentRef, method, arguments);
+      }else {
+        WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+        if(null == instance || !instance.isDestroy()){
+          WXLogUtils.e("WXBridgeManager","callNativeComponent exception :null == dom ,method:"+method);
+        }
+      }
+
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callNativeComponent exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callNativeComponent",
+              WXLogUtils.getStackTrace(e), null);
+    }
+    return null;
+  }
+
+  /**
+   * Dispatch the native task to be executed.
+   *
+   * @param instanceId {@link WXSDKInstance#mInstanceId}
+   * @param tasks      tasks to be executed
+   * @param callback   next tick id
+   */
+  public int callNative(String instanceId, JSONArray tasks, String callback) {
+
+    if (TextUtils.isEmpty(instanceId) || tasks == null) {
+      WXLogUtils.d("[WXBridgeManager] call callNative arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callNative",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callNative >>>> instanceId:").append(instanceId)
+              .append(", tasks:").append(tasks).append(", callback:").append(callback);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+
+    long parseNanos = System.nanoTime();
+    JSONArray array = tasks;
+    parseNanos = System.nanoTime() - parseNanos;
+
+    if (null != array && array.size() > 0) {
+      int size = array.size();
+      try {
+        JSONObject task;
+        for (int i = 0; i < size; ++i) {
+          task = (JSONObject) array.get(i);
+          if (task != null && WXSDKManager.getInstance().getSDKInstance(instanceId) != null) {
+            Object module = task.get(MODULE);
+            if (module != null) {
+              if (WXDomModule.WXDOM.equals(module)) {
+                WXDomModule dom = WXModuleManager.getDomModule(instanceId);
+                dom.callDomMethod(task, parseNanos);
+              } else {
+                JSONObject optionObj = task.getJSONObject(OPTIONS);
+                WXStateRecord.getInstance().recordAction(instanceId,"callModuleMethod:"+instanceId+","+module+","+task.get(METHOD));
+                callModuleMethod(instanceId, (String) module,
+                        (String) task.get(METHOD), (JSONArray) task.get(ARGS), optionObj);
+              }
+            } else if (task.get(COMPONENT) != null) {
+              WXDomModule dom = WXModuleManager.getDomModule(instanceId);
+              WXStateRecord.getInstance().recordAction(instanceId,"callDomMethod:"+instanceId+","+task.get(METHOD));
+              dom.invokeMethod((String) task.get(REF), (String) task.get(METHOD), (JSONArray) task.get(ARGS));
+            } else {
+              throw new IllegalArgumentException("unknown callNative");
+            }
+          }
+        }
+      } catch (Exception e) {
+        WXLogUtils.e("[WXBridgeManager] callNative exception: ", e);
+        WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+                WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callNative",
+                WXLogUtils.getStackTrace(e) , null);
+      }
+    }
+
+    if (UNDEFINED.equals(callback) || NON_CALLBACK.equals(callback)) {
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+    // get next tick
+    getNextTick(instanceId, callback);
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  // callUpdateFinish
+  public int callUpdateFinish(String instanceId, String callback) {
+
+    if (TextUtils.isEmpty(instanceId)) {
+      WXLogUtils.d("[WXBridgeManager] call callUpdateFinish arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateFinish",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callUpdateFinish >>>> instanceId:").append(instanceId)
+              .append(", callback:").append(callback);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      if (WXSDKManager.getInstance().getSDKInstance(instanceId) != null) {
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callUpdateFinish exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateFinish",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    if (callback == null || callback.isEmpty() || UNDEFINED.equals(callback) || NON_CALLBACK.equals(callback)) {
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+    // get next tick
+    getNextTick(instanceId, callback);
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  // callRefreshFinish
+  public int callRefreshFinish(String instanceId, String callback) {
+
+    if (TextUtils.isEmpty(instanceId)) {
+      WXLogUtils.d("[WXBridgeManager] call callRefreshFinish arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRefreshFinish",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callRefreshFinish >>>> instanceId:").append(instanceId)
+              .append(", callback:").append(callback);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+        WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+        if (instance != null) {
+          GraphicActionRefreshFinish action = new GraphicActionRefreshFinish(instance);
+          WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(instanceId, action);
+        }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callRefreshFinish exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRefreshFinish",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    if (UNDEFINED.equals(callback) || NON_CALLBACK.equals(callback)) {
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+    // get next tick
+    getNextTick(instanceId, callback);
+    return IWXBridge.INSTANCE_RENDERING;
+
+  }
+
+  public int callReportCrashReloadPage(String instanceId, String crashFile) {
+    boolean isCrashFileEmpty = TextUtils.isEmpty(crashFile);
+    try {
+      String url = null;
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        url = instance.getBundleUrl();
+        instance.setHasException(true);
+      }
+      Map<String,String> extInfo = new HashMap<>(2);
+      extInfo.put("weexCoreThreadStackTrace:",WXBridgeManager.getInstance().getWeexCoreThreadStackTrace());
+      extInfo.put("wxStateInfo",WXStateRecord.getInstance().getStateInfo().toString());
+
+      if(!isCrashFileEmpty) {
+        try {
+            if (WXEnvironment.getApplication() != null) {
+                crashFile = mInitParams.getCrashFilePath() + crashFile;
+                Log.d("jsengine", "callReportCrashReloadPage crashFile:" + crashFile);
+            }
+        } catch (Throwable e) {
+          WXLogUtils.e(WXLogUtils.getStackTrace(e));
+        }
+        WXStateRecord.getInstance().onJSCCrash(TextUtils.isEmpty(instanceId)?"null":instanceId);
+        callReportCrash(crashFile, instanceId, url,extInfo);
+      } else {
+        WXStateRecord.getInstance().onJSEngineReload(TextUtils.isEmpty(instanceId)?"null":instanceId);
+         commitJscCrashAlarmMonitor(IWXUserTrackAdapter.JS_BRIDGE, WXErrorCode.WX_ERR_RELOAD_PAGE, "reboot jsc Engine", instanceId, url,extInfo);
+      }
+      JSEngine.getInstance().engineCrashed();
+      WXLogUtils.e("reInitCount:"+reInitCount);
+
+      if (reInitCount > CRASHREINIT) {
+        WXExceptionUtils.commitCriticalExceptionRT("jsEngine", WXErrorCode.WX_ERR_RELOAD_PAGE_EXCEED_LIMIT,
+            "callReportCrashReloadPage","reInitCount:"+reInitCount,extInfo);
+        return IWXBridge.INSTANCE_RENDERING_ERROR;
+      }
+      reInitCount++;
+      // reinit frame work
+      setJSFrameworkInit(false);
+      WXModuleManager.resetAllModuleState();
+      initScriptsFramework("");
+
+      if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+        return IWXBridge.DESTROY_INSTANCE;
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callReportCrashReloadPage exception: ", e);
+    }
+    try {
+
+      if (WXSDKManager.getInstance().getSDKInstance(instanceId) != null) {
+        boolean reloadThisInstance = shouldReloadCurrentInstance(
+                WXSDKManager.getInstance().getSDKInstance(instanceId).getBundleUrl());
+        new ActionReloadPage(instanceId, reloadThisInstance).executeAction();
+      }
+
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callReloadPage exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callReportCrashReloadPage",
+              WXLogUtils.getStackTrace(e), null);
+    }
+    return IWXBridge.INSTANCE_RENDERING_ERROR;
+  }
+
+  public boolean shouldReloadCurrentInstance(String aUrl) {
+    long time = System.currentTimeMillis();
+    String bizUrl = aUrl;
+    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
+    if (adapter != null) {
+        boolean check_biz_url = Boolean.parseBoolean(adapter
+                .getConfig("android_weex_ext_config",
+                        "check_biz_url",
+                        "true"));
+        WXLogUtils.e("check_biz_url : " + check_biz_url);
+        if(check_biz_url && !TextUtils.isEmpty(aUrl)) {
+            Uri uri = Uri.parse(aUrl);
+            if(uri != null) {
+                bizUrl = uri.buildUpon().clearQuery().build().toString();
+            }
+        }
+    }
+
+    if (crashUrl == null ||
+            (crashUrl != null && !crashUrl.equals(bizUrl)) ||
+            ((time - lastCrashTime) > 15000)) {
+      crashUrl = bizUrl;
+      lastCrashTime = time;
+      return true;
+    }
+    lastCrashTime = time;
+    return false;
+  }
+
+  public void callReportCrash(String crashFile, final String instanceId, final String url,final Map<String,String> extInfo) {
+    // statistic weex core process crash
+    Date date = new Date();
+    DateFormat format = new SimpleDateFormat("yyyyMMddHHmmss", Locale.US);
+    String time = format.format(date);
+    final String origin_filename = crashFile + "." + time;
+    File oldfile = new File(crashFile);
+    File newfile = new File(origin_filename);
+    if (oldfile.exists()) {
+      oldfile.renameTo(newfile);
+    }
+    Thread t = new Thread(new Runnable() {
+      public void run() {
+        try {
+          File file = new File(origin_filename);
+          if (file.exists()) {
+            if (file.length() > 0) {
+              StringBuilder result = new StringBuilder();
+              try {
+                BufferedReader br = new BufferedReader(new FileReader(origin_filename));
+                String s = null;
+                // boolean foundStart = false;
+                while ((s = br.readLine()) != null) {
+                  if ("".equals(s)) {
+                    continue;
+                  }
+                  // if (("r0:").equals(s)) {
+                  //  break;
+                  // }
+                  result.append(s + "\n");
+                }
+                commitJscCrashAlarmMonitor(IWXUserTrackAdapter.JS_BRIDGE, WXErrorCode.WX_ERR_JSC_CRASH, result.toString(), instanceId, url,extInfo);
+                br.close();
+              } catch (Exception e) {
+                WXLogUtils.e(WXLogUtils.getStackTrace(e));
+              }
+            } else {
+              WXLogUtils.e("[WXBridgeManager] callReportCrash crash file is empty");
+            }
+            if(!WXEnvironment.isApkDebugable())
+              file.delete();
+          }
+        } catch (Throwable throwable) {
+          WXLogUtils.e("[WXBridgeManager] callReportCrash exception: ", throwable);
+        }
+      }
+    });
+    t.start();
+  }
+
+  private void getNextTick(final String instanceId, final String callback) {
+    addJSTask(METHOD_CALLBACK, instanceId, callback, "{}");
+    sendMessage(instanceId, WXJSBridgeMsgType.CALL_JS_BATCH);
+  }
+
+  private void getNextTick(final String instanceId) {
+    addJSTask(METHOD_CALLBACK, instanceId, "", "{}");
+    sendMessage(instanceId, WXJSBridgeMsgType.CALL_JS_BATCH);
+  }
+
+  public String syncExecJsOnInstanceWithResult(final String instanceId, final String js, final int type) {
+    final CountDownLatch waitLatch = new CountDownLatch(1);
+    EventResult callback = new EventResult(){
+      @Override
+      public void onCallback(Object result) {
+        super.onCallback(result);
+        waitLatch.countDown();
+      }
+    };
+    try{
+      execJSOnInstance(callback, instanceId, js, type);
+      waitLatch.await(100, TimeUnit.MILLISECONDS);
+      if (callback != null && callback.getResult() != null) {
+        return  callback.getResult().toString();
+      }
+      return "";
+    }catch (Throwable e){
+      WXLogUtils.e("syncCallExecJsOnInstance", e);
+      return  "";
+    }
+  }
+
+  public void loadJsBundleInPreInitMode(final String instanceId, final String js){
+    post(new Runnable() {
+      @Override
+      public void run() {
+        invokeExecJSOnInstance(instanceId, js, -1);
+        WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
+        if (null != instance && instance.isPreInitMode()){
+          instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_END);
+          instance.getApmForInstance().onStageWithTime(WXInstanceApm.KEY_PAGE_STAGES_END_EXCUTE_BUNDLE,WXUtils.getFixUnixTime()+600);
+        }
+      }
+    });
+  }
+
+  /**
+   * ref, type, data, domChanges
+   * */
+  public EventResult syncCallJSEventWithResult(final String method, final String instanceId, final List<Object> params, final Object... args) {
+    final CountDownLatch waitLatch = new CountDownLatch(1);
+    EventResult callback = new EventResult(){
+      @Override
+      public void onCallback(Object result) {
+        super.onCallback(result);
+        waitLatch.countDown();
+      }
+    };
+    try{
+      asyncCallJSEventWithResult(callback, method, instanceId, params, args);
+      waitLatch.await(100, TimeUnit.MILLISECONDS);
+      return  callback;
+    }catch (Exception e){
+      WXLogUtils.e("syncCallJSEventWithResult", e);
+      return  callback;
+    }
+  }
+
+  public void asyncCallJSEventVoidResult(final String method, final String instanceId, final List<Object> params, final Object... args) {
+    post(new Runnable() {
+      @Override
+      public void run() {
+        try{
+          if (args == null || args.length == 0) {
+            return;
+          }
+
+          ArrayList<Object> argsList = new ArrayList<>();
+          for (Object arg : args) {
+            argsList.add(arg);
+          }
+          if (params != null) {
+            ArrayMap map = new ArrayMap(4);
+            map.put(KEY_PARAMS, params);
+            argsList.add(map);
+          }
+
+          WXHashMap<String, Object> task = new WXHashMap<>();
+          task.put(KEY_METHOD, method);
+          task.put(KEY_ARGS, argsList);
+          Object[] tasks = {task};
+          WXJSObject[] jsArgs = {
+                  new WXJSObject(WXJSObject.String, instanceId),
+                  WXWsonJSONSwitch.toWsonOrJsonWXJSObject(tasks)};
+          invokeExecJS(String.valueOf(instanceId), null, METHOD_CALL_JS, jsArgs, true);
+          jsArgs[0] = null;
+          jsArgs = null;
+        }catch (Exception e){
+          WXLogUtils.e("asyncCallJSEventVoidResult" , e);
+        }
+      }
+    });
+  }
+
+  /**
+   * aync call js event and return result in eventResult callback
+   * */
+  private void asyncCallJSEventWithResult(final EventResult eventCallback, final String method, final String instanceId, final List<Object> params, final Object... args) {
+    post(new Runnable() {
+      @Override
+      public void run() {
+        Object result = null;
+        try{
+          if (args == null || args.length == 0) {
+            return;
+          }
+
+          ArrayList<Object> argsList = new ArrayList<>();
+          for (Object arg : args) {
+            argsList.add(arg);
+          }
+          if (params != null) {
+            ArrayMap map = new ArrayMap(4);
+            map.put(KEY_PARAMS, params);
+            argsList.add(map);
+          }
+
+          WXHashMap<String, Object> task = new WXHashMap<>();
+          task.put(KEY_METHOD, method);
+          task.put(KEY_ARGS, argsList);
+          Object[] tasks = {task};
+          WXJSObject[] jsArgs = {
+                  new WXJSObject(WXJSObject.String, instanceId),
+                  WXWsonJSONSwitch.toWsonOrJsonWXJSObject(tasks)};
+          ResultCallback<byte[]> resultCallback = null;
+          if (eventCallback != null) {
+            resultCallback = new ResultCallback<byte[]>() {
+              @Override
+              public void onReceiveResult(byte[] result) {
+                JSONArray arrayResult = (JSONArray) WXWsonJSONSwitch.parseWsonOrJSON(result);
+                if(arrayResult != null && arrayResult.size() > 0){
+                  eventCallback.onCallback(arrayResult.get(0));
+                }
+              }
+            };
+          }
+          invokeExecJSWithCallback(String.valueOf(instanceId), null, METHOD_CALL_JS,
+                  jsArgs, resultCallback, true);
+          jsArgs[0] = null;
+        }catch (Exception e){
+          WXLogUtils.e("asyncCallJSEventWithResult" , e);
+        }
+      }
+    });
+  }
+
+  private void addJSEventTask(final String method, final String instanceId, final List<Object> params, final Object... args) {
+    post(new Runnable() {
+      @Override
+      public void run() {
+        if (args == null || args.length == 0) {
+          return;
+        }
+
+        ArrayList<Object> argsList = new ArrayList<>();
+        for (Object arg : args) {
+          argsList.add(arg);
+        }
+        if (params != null) {
+          ArrayMap map = new ArrayMap(4);
+          map.put(KEY_PARAMS, params);
+          argsList.add(map);
+        }
+
+        WXHashMap<String, Object> task = new WXHashMap<>();
+        task.put(KEY_METHOD, method);
+        task.put(KEY_ARGS, argsList);
+
+
+        if (mNextTickTasks.get(instanceId) == null) {
+          ArrayList<WXHashMap<String, Object>> list = new ArrayList<>();
+          list.add(task);
+          mNextTickTasks.put(instanceId, list);
+        } else {
+          mNextTickTasks.get(instanceId).add(task);
+        }
+      }
+    });
+  }
+
+  private void addJSTask(final String method, final String instanceId, final Object... args) {
+    addJSEventTask(method, instanceId, null, args);
+  }
+
+  private void sendMessage(String instanceId, int what) {
+    Message msg = Message.obtain(mJSHandler);
+    msg.obj = instanceId;
+    msg.what = what;
+    msg.sendToTarget();
+  }
+
+  /**
+   * Initialize JavaScript framework
+   *
+   * @param framework String representation of the framework to be init.
+   */
+  public synchronized void initScriptsFramework(String framework) {
+    Message msg = mJSHandler.obtainMessage();
+    msg.obj = framework;
+    msg.what = WXJSBridgeMsgType.INIT_FRAMEWORK;
+    msg.setTarget(mJSHandler);
+    msg.sendToTarget();
+  }
+
+  @Deprecated
+  public void fireEvent(final String instanceId, final String ref,
+                        final String type, final Map<String, Object> data) {
+    this.fireEvent(instanceId, ref, type, data, null);
+  }
+
+  /**
+   * Do not direct invoke this method in Components, use {@link WXSDKInstance#fireEvent(String, String, Map, Map)} instead.
+   *
+   * @param instanceId
+   * @param ref
+   * @param type
+   * @param data
+   * @param domChanges
+   */
+  @Deprecated
+  public void fireEvent(final String instanceId, final String ref,
+                        final String type, final Map<String, Object> data, final Map<String, Object> domChanges) {
+    fireEventOnNode(instanceId, ref, type, data, domChanges);
+  }
+
+  /**
+   * Notify the JavaScript about the event happened on Android
+   */
+  public void fireEventOnNode(final String instanceId, final String ref,
+                              final String type, final Map<String, Object> data, final Map<String, Object> domChanges) {
+    fireEventOnNode(instanceId, ref, type, data, domChanges, null, null);
+  }
+
+  /**
+   * Notify the JavaScript about the event happened on Android
+   */
+  public void fireEventOnNode(final String instanceId, final String ref,
+                              final String type, final Map<String, Object> data,
+                              final Map<String, Object> domChanges, List<Object> params){
+    fireEventOnNode(instanceId, ref, type, data, domChanges, params, null);
+  }
+
+  public void fireEventOnNode(final String instanceId, final String ref,
+                              final String type, final Map<String, Object> data,
+                              final Map<String, Object> domChanges, List<Object> params,  EventResult callback) {
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)
+            || TextUtils.isEmpty(type) || mJSHandler == null) {
+      return;
+    }
+    if (!checkMainThread()) {
+      throw new WXRuntimeException(
+              "fireEvent must be called by main thread");
+    }
+    WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
+    if (instance != null && (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER ||
+            instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY)) {
+      fireEventOnDataRenderNode(instanceId, ref, type, data, domChanges);
+    } else {
+      if(callback == null) {
+        addJSEventTask(METHOD_FIRE_EVENT, instanceId, params, ref, type, data, domChanges);
+        sendMessage(instanceId, WXJSBridgeMsgType.CALL_JS_BATCH);
+      }else{
+        asyncCallJSEventWithResult(callback, METHD_FIRE_EVENT_SYNC, instanceId, params, ref, type, data, domChanges);
+      }
+    }
+  }
+
+  private void fireEventOnDataRenderNode(final String instanceId, final String ref,
+                                         final String type, final Map<String, Object> data, final Map<String, Object> domChanges) {
+    mJSHandler.postDelayed(WXThread.secure(new Runnable() {
+      @Override
+      public void run() {
+        try {
+          WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+          long start = System.currentTimeMillis();
+          if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.d("fireEventOnDataRenderNode >>>> instanceId:" + instanceId
+                + ", data:" + data);
+          }
+          if (mWXBridge instanceof WXBridge) {
+            ((WXBridge) mWXBridge).fireEventOnDataRenderNode(instanceId, ref, type,
+                (data == null || data.isEmpty()) ? "{}" : JSON.toJSONString(data),
+                (domChanges == null || domChanges.isEmpty()) ? "{}" : JSON.toJSONString(domChanges));
+          }
+          WXLogUtils.renderPerformanceLog("fireEventOnDataRenderNode", System.currentTimeMillis() - start);
+        } catch (Throwable e) {
+          String err = "[WXBridgeManager] fireEventOnDataRenderNode " + WXLogUtils.getStackTrace(e);
+          WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "fireEventOnDataRenderNode",
+              err, null);
+          WXLogUtils.e(err);
+        }
+      }
+    }), 0);
+  }
+
+  private boolean checkMainThread() {
+    return Looper.myLooper() == Looper.getMainLooper();
+  }
+
+
+  /**
+   * Invoke JavaScript callback. Use {@link JSCallback} instead.
+   *
+   * @see #callback(String, String, String)
+   */
+  @Deprecated
+  public void callback(String instanceId, String callback, String data) {
+    callback(instanceId, callback, data, false);
+  }
+
+  /**
+   * Invoke JavaScript callback. Use {@link JSCallback} instead.
+   */
+  @Deprecated
+  public void callback(final String instanceId, final String callback,
+                       final Map<String, Object> data) {
+    callback(instanceId, callback, data, false);
+  }
+
+  /**
+   * Use {@link JSCallback} instead.
+   *
+   * @param instanceId Weex Instance Id
+   * @param callback   callback referenece handle
+   * @param data       callback data
+   * @param keepAlive  if keep callback instance alive for later use
+   */
+  @Deprecated
+  public void callback(final String instanceId, final String callback,
+                       final Object data, boolean keepAlive) {
+    callbackJavascript(instanceId, callback, data, keepAlive);
+  }
+
+  /**
+   * Callback to Javascript function.
+   *
+   * @param instanceId Weex Instance Id
+   * @param callback   callback referenece handle
+   * @param data       callback data
+   * @param keepAlive  if keep callback instance alive for later use
+   */
+  void callbackJavascript(final String instanceId, final String callback,
+                          final Object data, boolean keepAlive) {
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(callback)
+            || mJSHandler == null) {
+      return;
+    }
+
+    WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
+    if (instance != null && (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY)) {
+      callbackJavascriptOnDataRender(instanceId, callback, data, keepAlive);
+    } else {
+      addJSTask(METHOD_CALLBACK, instanceId, callback, data, keepAlive);
+      sendMessage(instanceId, WXJSBridgeMsgType.CALL_JS_BATCH);
+    }
+  }
+
+  void callbackJavascriptOnDataRender(final String instanceId, final String callback, final Object data, final boolean keepAlive){
+    mJSHandler.postDelayed(WXThread.secure(new Runnable() {
+      @Override
+      public void run() {
+        try {
+          long start = System.currentTimeMillis();
+          String data_str = JSON.toJSONString(data);
+          if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.d("callbackJavascriptOnDataRender >>>> instanceId:" + instanceId
+                + ", data:" + data_str);
+          }
+          if (mWXBridge instanceof WXBridge) {
+            ((WXBridge) mWXBridge).invokeCallbackOnDataRender(instanceId, callback,data_str ,keepAlive);
+          }
+          WXLogUtils.renderPerformanceLog("callbackJavascriptOnDataRender", System.currentTimeMillis() - start);
+        } catch (Throwable e) {
+          String err = "[WXBridgeManager] callbackJavascriptOnDataRender " + WXLogUtils.getStackTrace(e);
+          WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callbackJavascriptOnDataRender",
+              err, null);
+          WXLogUtils.e(err);
+        }
+      }
+    }), 0);
+  }
+
+  /**
+   * Refresh instance
+   */
+  public void refreshInstance(final String instanceId, final WXRefreshData jsonData) {
+    if (TextUtils.isEmpty(instanceId) || jsonData == null) {
+      return;
+    }
+    mJSHandler.postDelayed(WXThread.secure(new Runnable() {
+      @Override
+      public void run() {
+        invokeRefreshInstance(instanceId, jsonData);
+      }
+    }), 0);
+  }
+
+  private void invokeRefreshInstance(String instanceId, WXRefreshData refreshData) {
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (!isSkipFrameworkInit(instanceId) && !isJSFrameworkInit()) {
+        if (instance != null) {
+          instance.onRenderError(
+                  WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+                  WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg()
+                          + "invokeRefreshInstance FAILED for JSFrameworkInit FAILED, intance will invoke instance.onRenderError"
+          );
+        }
+        String err = "[WXBridgeManager] invokeRefreshInstance: framework.js uninitialized.";
+        WXLogUtils.e(err);
+        return;
+      }
+      long start = System.currentTimeMillis();
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.d("refreshInstance >>>> instanceId:" + instanceId
+                + ", data:" + refreshData.data + ", isDirty:" + refreshData.isDirty);
+      }
+
+      if (refreshData.isDirty) {
+        return;
+      }
+      WXJSObject instanceIdObj = new WXJSObject(WXJSObject.String,
+              instanceId);
+      WXJSObject dataObj = new WXJSObject(WXJSObject.JSON,
+              refreshData.data == null ? "{}" : refreshData.data);
+      WXJSObject[] args = {instanceIdObj, dataObj};
+      mWXBridge.refreshInstance(instanceId, null, METHOD_REFRESH_INSTANCE, args);
+    } catch (Throwable e) {
+      String err = "[WXBridgeManager] invokeRefreshInstance " + WXLogUtils.getStackTrace(e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "invokeRefreshInstance",
+              err, null);
+      WXLogUtils.e(err);
+    }
+  }
+
+  public void commitJscCrashAlarmMonitor(final String type, final WXErrorCode errorCode, String errMsg,
+                                         String instanceId, String url,Map<String, String> extInfo) {
+    if (TextUtils.isEmpty(type) || errorCode == null) {
+      return;
+    }
+
+    Log.d("ReportCrash", " commitJscCrashAlarmMonitor errMsg " + errMsg);
+    String method = "callReportCrash";
+    String exception = "weex core process crash and restart exception";
+    Map<String, String> extParams = new HashMap<String, String>();
+    extParams.put("jscCrashStack", errMsg);
+    if (null != extInfo){
+      extParams.putAll(extInfo);
+    }
+    IWXJSExceptionAdapter adapter = WXSDKManager.getInstance().getIWXJSExceptionAdapter();
+    if (adapter != null) {
+      WXJSExceptionInfo jsException = new WXJSExceptionInfo(instanceId, url, errorCode, method, exception, extParams);
+      adapter.onJSException(jsException);
+      // if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.e(jsException.toString());
+      // }
+    }
+  }
+
+  private boolean isSkipFrameworkInit(String instanceId) {
+    final WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    return isSkipFrameworkInit(instance);
+  }
+
+  private boolean isSkipFrameworkInit(WXSDKInstance instance) {
+    if (instance == null) {
+      return false;
+    }
+    return instance.skipFrameworkInit();
+  }
+
+  /**
+   * Create instance.
+   */
+  public void createInstance(final String instanceId, final String template,
+                             final Map<String, Object> options, final String data) {
+    createInstance(instanceId, new Script(template), options, data);
+  }
+
+  public void setLogLevel(final int level, final boolean isPerf) {
+    post(new Runnable() {
+      @Override
+      public void run() {
+        if(mWXBridge != null) {
+          mWXBridge.setLogType(level, isPerf);
+        }
+      }
+    });
+  }
+
+  public void createInstance(final String instanceId, final Script template,
+                             final Map<String, Object> options, final String data) {
+    final WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (instance == null) {
+      WXLogUtils.e("WXBridgeManager", "createInstance failed, SDKInstance does not exist");
+      return;
+    }
+    if (TextUtils.isEmpty(instanceId) || template == null || template.isEmpty() || mJSHandler == null) {
+      instance.onRenderError(
+              WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+              WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg() +
+                      " instanceId==" + instanceId + " template ==" + template + " mJSHandler== " + mJSHandler.toString()
+      );
+
+      instance.getApmForInstance().onStage("createInstance failed return; "+TextUtils.isEmpty(instanceId)+ ","+template.isEmpty()+","+(mJSHandler ==null));
+      return;
+    }
+
+    if (!isSkipFrameworkInit(instanceId) && !isJSFrameworkInit() && reInitCount == 1 && !WXEnvironment.sDebugServerConnectable) {
+      instance.onRenderError(
+              WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+              WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg() +
+                      " isJSFrameworkInit==" + isJSFrameworkInit() + " reInitCount == 1" );
+      instance.getApmForInstance().onStage("createInstance failed jsfm isn't init return;");
+      post(new Runnable() {
+        @Override
+        public void run() {
+          initFramework("");
+        }
+      }, instanceId, instance,"initFrameworkInCreateInstance");
+      return;
+    }
+
+    WXModuleManager.createDomModule(instance);
+    instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_START);
+    post(new Runnable() {
+      @Override
+      public void run() {
+        instance.getApmForInstance().onStage("wxLoadBundleStartOnJsThread");
+        long start = System.currentTimeMillis();
+        mWXBridge.setPageArgument(instanceId, "renderTimeOrigin", String.valueOf(instance.getWXPerformance().renderTimeOrigin));
+        mWXBridge.setInstanceRenderType(instance.getInstanceId(), instance.getRenderType());
+        invokeCreateInstance(instance, template, options, data);
+        long end = System.currentTimeMillis();
+        instance.getWXPerformance().callCreateInstanceTime = end - start;
+        instance.getWXPerformance().communicateTime =  instance.getWXPerformance().callCreateInstanceTime;
+      }
+    }, instanceId, instance,"createInstance");
+  }
+
+  private void invokeCreateInstance(@NonNull WXSDKInstance instance, Script template,
+                                    Map<String, Object> options, String data) {
+    // add for sandbox, will delete on sandbox ok
+    if (!isSkipFrameworkInit(instance)){
+      initFramework("");
+    }
+
+    if (mMock) {
+      mock(instance.getInstanceId());
+    } else {
+      if (!isSkipFrameworkInit(instance) && !isJSFrameworkInit()) {
+        String err = "[WXBridgeManager] invokeCreateInstance: framework.js uninitialized.";
+        instance.onRenderError(
+                WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+                WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg()
+        );
+        WXLogUtils.e(err);
+        instance.getApmForInstance().onStage("framework.js uninitialized and return");
+        return;
+      }
+
+      WXModuleManager.registerWhenCreateInstance();
+
+      try {
+        BundType type = BundType.Others;
+        try {
+          long start = System.currentTimeMillis();
+          type = getBundleType(instance.getBundleUrl(), template.getContent());
+
+          if (WXEnvironment.isOpenDebugLog()) {
+            long end = System.currentTimeMillis();
+            WXLogUtils.e("end getBundleType type:" + type.toString() + " time:" + (end - start));
+          }
+        } catch (Throwable e) {
+          WXLogUtils.e(WXLogUtils.getStackTrace(e));
+        }
+
+        try {
+          if (options == null) {
+            options = new HashMap<>();
+          }
+          // on file there is { "framework": "Vue" } or others
+          if (options.get(BUNDLE_TYPE) == null) {
+            // may vue or Rax
+            if (type == BundType.Vue) {
+              options.put(BUNDLE_TYPE, "Vue");
+            } else if (type == BundType.Rax) {
+              options.put(BUNDLE_TYPE, "Rax");
+            } else {
+              options.put(BUNDLE_TYPE, "Others");
+            }
+            Object recordBundleType = options.get(BUNDLE_TYPE);
+            if (recordBundleType instanceof String && "Others".equalsIgnoreCase((String)recordBundleType)){
+              //same as iOS record
+              recordBundleType = "other";
+            }
+            if (null != recordBundleType){
+              instance.getApmForInstance().addProperty(WXInstanceApm.KEY_PAGE_PROPERTIES_BUNDLE_TYPE, recordBundleType);
+            }
+          }
+          if (options.get("env") == null) {
+            options.put("env", mInitParams.toMap());
+          }
+        } catch (Throwable e) {
+          WXLogUtils.e(WXLogUtils.getStackTrace(e));
+        }
+        instance.bundleType = type;
+        if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+          WXLogUtils.d("createInstance >>>> instanceId:" + instance.getInstanceId()
+                  + ", options:"
+                  + WXJsonUtils.fromObjectToJSONString(options)
+                  + ", data:" + data);
+        }
+        WXJSObject instanceIdObj = new WXJSObject(WXJSObject.String,
+                instance.getInstanceId());
+        WXJSObject instanceObj = new WXJSObject(WXJSObject.String,
+                template.getContent());
+
+        Object extraOption = null;
+        if(options != null && options.containsKey("extraOption")) {
+           extraOption = options.get("extraOption");
+           options.remove("extraOption");
+        }
+
+        WXJSObject extraOptionObj = new WXJSObject(WXJSObject.JSON,
+                extraOption == null ? "{}"
+                        : WXJsonUtils.fromObjectToJSONString(extraOption));
+
+
+        WXJSObject optionsObj = new WXJSObject(WXJSObject.JSON,
+                options == null ? "{}"
+                        : WXJsonUtils.fromObjectToJSONString(options));
+        optionsObj = optionObjConvert(isSandBoxContext, type, optionsObj);
+        WXJSObject dataObj = new WXJSObject(WXJSObject.JSON,
+                data == null ? "{}" : data);
+
+        WXJSObject apiObj;
+        if (type == BundType.Rax || instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER) {
+          if (mRaxApi == null) {
+            IWXJsFileLoaderAdapter iwxJsFileLoaderAdapter = WXSDKEngine.getIWXJsFileLoaderAdapter();
+            if(iwxJsFileLoaderAdapter != null) {
+              mRaxApi = iwxJsFileLoaderAdapter.loadRaxApi();
+            }
+
+            if(TextUtils.isEmpty(mRaxApi)) {
+              mRaxApi =  WXFileUtils.loadAsset("weex-rax-api.js", WXEnvironment.getApplication());
+            }
+          }
+          apiObj = new WXJSObject(WXJSObject.String,
+                  mRaxApi);
+        } else {
+          apiObj = new WXJSObject(WXJSObject.String,
+                  "");
+        }
+
+        // When render strategy is data_render, put it into options. Others keep null.
+        WXJSObject renderStrategy = null;
+        if (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER) {
+          renderStrategy = new WXJSObject(WXJSObject.String, WXRenderStrategy.DATA_RENDER.getFlag());
+        } else if (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY) {
+          renderStrategy = new WXJSObject(WXJSObject.String, WXRenderStrategy.DATA_RENDER_BINARY.getFlag());
+          // In DATA_RENDER_BINARY strategy script is binary
+          instanceObj.data = template.getBinary();
+        }else if (instance.getRenderStrategy() == WXRenderStrategy.JSON_RENDER) {
+             renderStrategy = new WXJSObject(WXJSObject.String, WXRenderStrategy.JSON_RENDER.getFlag());
+        }
+
+        WXJSObject[] args = {instanceIdObj, instanceObj, optionsObj,
+                dataObj, apiObj, renderStrategy, extraOptionObj};
+
+        instance.setTemplate(template.getContent());
+
+        instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_END);
+
+        // if { "framework": "Vue" } or  { "framework": "Rax" } will use invokeCreateInstanceContext
+        // others will use invokeExecJS
+        if (!isSandBoxContext) {
+          instance.getApmForInstance().onStage("!isSandBoxContext,and excute");
+          WXLogUtils.e("Instance " + instance.getInstanceId() + " Did Not Render in SandBox Mode");
+          invokeExecJS(instance.getInstanceId(), null, METHOD_CREATE_INSTANCE, args, false);
+          return;
+        }
+        if (type == BundType.Vue || type == BundType.Rax
+                || instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER
+                || instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY
+                || instance.getRenderStrategy() == WXRenderStrategy.JSON_RENDER) {
+          instance.getApmForInstance().onStage("wxBeforeInvokeCreateInstanceContext");
+
+          WXLogUtils.d("Instance " + instance.getInstanceId() + " Render in SandBox Mode And Render Type is "
+                  + type + " Render Strategy is " + instance.getRenderStrategy());
+
+          int ret = invokeCreateInstanceContext(instance.getInstanceId(), null, "createInstanceContext", args, false);
+          instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_END);
+          if(ret == 0) {
+            String err = "[WXBridgeManager] invokeCreateInstance : " + instance.getTemplateInfo();
+            WXLogUtils.e("Instance " + instance.getInstanceId() + "Render error : " + err);
+            instance.onRenderError(
+                    WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+                    WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg() + err);
+          }
+          return;
+        } else {
+          //bad case for js bundle with out bundletype header //vue or rax
+          //WXExceptionUtils.commitCriticalExceptionRT(
+          //      instance.getInstanceId(),
+          //      WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE,
+          //      "invokeCreateInstance",
+          //      WXErrorCode.WX_KEY_EXCEPTION_NO_BUNDLE_TYPE.getErrorMsg(),
+          //      null
+          //);
+
+          WXLogUtils.d("Instance " + instance.getInstanceId() + "Did not Render in SandBox Mode And Render Type is "
+                + type + " Render Strategy is " + instance.getRenderStrategy());
+          instance.getApmForInstance().onStage("StartInvokeExecJSBadBundleType");
+          invokeExecJS(instance.getInstanceId(), null, METHOD_CREATE_INSTANCE, args, false);
+          instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_LOAD_BUNDLE_END);
+          return;
+        }
+      } catch (Throwable e) {
+        String err = "[WXBridgeManager] invokeCreateInstance " + e.getCause()
+                + instance.getTemplateInfo();
+        instance.getApmForInstance().onStage("createInstance error :"+e.toString());
+        WXLogUtils.e("Instance " + instance.getInstanceId() + "Render error : " + err);
+        instance.onRenderError(
+                WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+                WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg() + err);
+        WXLogUtils.e(err);
+      }
+    }
+  }
+
+  public WXJSObject optionObjConvert(boolean useSandBox, BundType type, WXJSObject opt) {
+    if (!useSandBox) {
+      return opt;
+    }
+    try {
+      String data = opt.data.toString();
+      JSONObject obj = JSON.parseObject(data);
+      JSONObject optEnv;
+      if ((optEnv = obj.getJSONObject("env")) != null) {
+        JSONObject opts = optEnv.getJSONObject("options");
+        if (opts != null) {
+          for (String s : opts.keySet()) {
+            optEnv.put(s, opts.getString(s));
+          }
+        }
+      }
+      return new WXJSObject(WXJSObject.JSON, obj.toString());
+    } catch (Throwable e) {
+      WXLogUtils.e(WXLogUtils.getStackTrace(e));
+    }
+    return opt;
+
+  }
+
+  /**
+   * check bundleType
+   * @param url
+   * @param temp
+   * @return
+   */
+  public BundType getBundleType(String url, String temp) {
+    try {
+      if (url != null) {
+        Uri uri = Uri.parse(url);
+        String type = uri.getQueryParameter(BUNDLE_TYPE);
+        if ("Vue".equals(type) || "vue".equals(type)) {
+          return BundType.Vue;
+        } else if ("Rax".equals(type) || "rax".equals(type)) {
+          return BundType.Rax;
+        }
+      }
+      if (temp != null) {
+        final String FRAMEWORK="framework", VUE="vue", RAX="rax";
+
+        // Find the first line that starts with '//' and convert it to json
+        int bundleTypeStart = temp.indexOf("//");
+        int bundleTypeEnd = temp.indexOf("\n", bundleTypeStart);
+        JSONObject bundleType = JSONObject.parseObject(
+            temp.substring(bundleTypeStart+2, bundleTypeEnd));
+        String type = bundleType.getString(FRAMEWORK);
+        if(VUE.equalsIgnoreCase(type)){
+          return BundType.Vue;
+        }
+        else if(RAX.equalsIgnoreCase(type)){
+          return BundType.Rax;
+        }
+        else{
+          // '//{ "framework": "Vue"}' is not found.
+          String regEx = "(use)(\\s+)(weex:vue)";
+          Pattern pattern = Pattern.compile(regEx, Pattern.CASE_INSENSITIVE);
+          if (pattern.matcher(temp).find()) {
+            return BundType.Vue;
+          }
+          regEx = "(use)(\\s+)(weex:rax)";
+          pattern = Pattern.compile(regEx, Pattern.CASE_INSENSITIVE);
+          if (pattern.matcher(temp).find()) {
+            return BundType.Rax;
+          }
+        }
+      }
+      return BundType.Others;
+    } catch (Throwable e) {
+      WXLogUtils.e(WXLogUtils.getStackTrace(e));
+      return BundType.Others;
+    }
+  }
+
+  private void mock(String instanceId) {
+
+  }
+
+  public void destroyInstance(final String instanceId) {
+    if (mJSHandler == null
+            || TextUtils.isEmpty(instanceId)) {
+      return;
+    }
+    if (mDestroyedInstanceId != null) {
+      mDestroyedInstanceId.add(instanceId);
+    }
+    // clear message with instanceId
+    mJSHandler.removeCallbacksAndMessages(instanceId);
+    post(new Runnable() {
+      @Override
+      public void run() {
+        removeTaskByInstance(instanceId);
+        invokeDestroyInstance(instanceId);
+      }
+    }, instanceId, null, "destroyInstance");
+  }
+
+  private void removeTaskByInstance(String instanceId) {
+    mNextTickTasks.removeFromMapAndStack(instanceId);
+  }
+
+  private void invokeDestroyInstance(String instanceId) {
+    try {
+      if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+        WXLogUtils.d("destroyInstance >>>> instanceId:" + instanceId);
+      }
+      WXJSObject instanceIdObj = new WXJSObject(WXJSObject.String,
+              instanceId);
+      WXJSObject[] args = {instanceIdObj};
+      if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+        invokeDestoryInstance(instanceId, null, METHOD_DESTROY_INSTANCE, args, true);
+        // invokeExecJS(instanceId, null, METHOD_DESTROY_INSTANCE, args);
+      }
+    } catch (Throwable e) {
+      String err = "[WXBridgeManager] invokeDestroyInstance " + e.getCause();
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "invokeDestroyInstance", err, null);
+      WXLogUtils.e(err);
+    }
+  }
+
+  @Override
+  public boolean handleMessage(Message msg) {
+    if (msg == null) {
+      return false;
+    }
+
+    int what = msg.what;
+    switch (what) {
+      case WXJSBridgeMsgType.INIT_FRAMEWORK:
+        invokeInitFramework(msg);
+        break;
+      case WXJSBridgeMsgType.CALL_JS_BATCH:
+        invokeCallJSBatch(msg);
+        break;
+      case WXJSBridgeMsgType.SET_TIMEOUT:
+        TimerInfo timerInfo = (TimerInfo) msg.obj;
+        if (timerInfo == null) {
+          break;
+        }
+        WXJSObject obj = new WXJSObject(WXJSObject.String, timerInfo.callbackId);
+        WXJSObject[] args = {obj};
+        invokeExecJS("", null, METHOD_SET_TIMEOUT, args);
+        break;
+      case WXJSBridgeMsgType.TAKE_HEAP_SNAPSHOT:
+        if (msg.obj != null) {
+          String filename = (String) msg.obj;
+          mWXBridge.takeHeapSnapshot(filename);
+        }
+        break;
+      default:
+        break;
+    }
+    return false;
+  }
+
+  private void invokeExecJS(String instanceId, String namespace, String function, WXJSObject[] args) {
+    invokeExecJS(instanceId, namespace, function, args, true);
+  }
+
+  public void invokeExecJS(final String instanceId, final String namespace, final String function,
+                           final WXJSObject[] args, boolean logTaskDetail) {
+    if (WXEnvironment.isOpenDebugLog() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("callJS >>>> instanceId:").append(instanceId)
+              .append("function:").append(function);
+      if (logTaskDetail) {
+        mLodBuilder.append(" tasks:").append(argsToJSON(args));
+      }
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+    final long start = System.currentTimeMillis();
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (instance != null && (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY)) {
+      Pair<Pair<String,Object>, Boolean> data = null;
+      if(args.length!=2 || !(args[0].data instanceof String)
+          || !(args[1].data instanceof String)
+          || (data = extractCallbackArgs((String) args[1].data))==null){
+        WXLogUtils.w("invokeExecJS on data render that is not a callback call");
+        return;
+      }
+      callbackJavascriptOnDataRender(instanceId, (String) data.first.first, data.first.second, data.second);
+    } else {
+
+      WXThread.secure(new Runnable() {
+        @Override
+        public void run() {
+          mWXBridge.execJS(instanceId, namespace, function, args);
+        }
+      }, instance, "ExecJs").run();
+    }
+    if (null != instance){
+      long diff = System.currentTimeMillis()-start;
+      instance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_CALL_JS_NUM,1);
+      instance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_CALL_JS_TIME,diff);
+      instance.callJsTime(diff);
+    }
+  }
+
+  private Pair<Pair<String,Object>,Boolean> extractCallbackArgs(String data) {
+    try {
+      JSONArray obj = JSON.parseArray(data);
+      JSONObject arg_obj = obj.getJSONObject(0);
+      JSONArray args = arg_obj.getJSONArray("args");
+      if (args.size()!=3){
+        return null;
+      }
+      String method = arg_obj.getString("method");
+      if (!"callback".equals(method)){
+        return null;
+      }
+
+      return new Pair<Pair<String,Object>, Boolean>(new Pair<String, Object>(args.getString(0), args.getJSONObject(1)),args.getBooleanValue(2));
+    } catch (Exception e) {
+      return null;
+    }
+  }
+
+  public int invokeCreateInstanceContext(String instanceId, String namespace, String function,
+                                          WXJSObject[] args, boolean logTaskDetail) {
+    WXLogUtils.d("invokeCreateInstanceContext instanceId:" + instanceId + " function:"
+            + function + String.format(" isJSFrameworkInit：%b", isJSFrameworkInit()));
+    mLodBuilder.append("createInstanceContext >>>> instanceId:").append(instanceId)
+            .append("function:").append(function);
+    if (logTaskDetail)
+      mLodBuilder.append(" tasks:").append(WXJsonUtils.fromObjectToJSONString(args));
+    WXLogUtils.d(mLodBuilder.substring(0));
+    mLodBuilder.setLength(0);
+    // }
+    return mWXBridge.createInstanceContext(instanceId, namespace, function, args);
+  }
+
+  public void invokeDestoryInstance(String instanceId, String namespace, String function,
+                                    WXJSObject[] args, boolean logTaskDetail) {
+    // if (WXEnvironment.isApkDebugable()) {
+    mLodBuilder.append("callJS >>>> instanceId:").append(instanceId)
+            .append("function:").append(function);
+    if (logTaskDetail)
+      mLodBuilder.append(" tasks:").append(WXJsonUtils.fromObjectToJSONString(args));
+    WXLogUtils.d(mLodBuilder.substring(0));
+    mLodBuilder.setLength(0);
+    // }
+    mWXBridge.removeInstanceRenderType(instanceId);
+    mWXBridge.destoryInstance(instanceId, namespace, function, args);
+  }
+
+  private void execJSOnInstance(final EventResult eventCallback, final String instanceId, final String js, final int type) {
+    post(new Runnable() {
+      @Override
+      public void run() {
+        String ret = invokeExecJSOnInstance(instanceId, js, type);
+        eventCallback.onCallback(ret);
+      }
+    });
+  }
+
+  private String invokeExecJSOnInstance(String instanceId, String js, int type) {
+    // if (WXEnvironment.isApkDebugable()) {
+    mLodBuilder.append("execJSOnInstance >>>> instanceId:").append(instanceId);
+    WXLogUtils.d(mLodBuilder.substring(0));
+    mLodBuilder.setLength(0);
+    // }
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      return mWXBridge.execJSOnInstance(instanceId, js, type);
+    }
+    return null;
+  }
+
+  private void invokeExecJSWithCallback(String instanceId, String namespace, String function,
+                                        WXJSObject[] args , ResultCallback callback, boolean logTaskDetail){
+    if (WXEnvironment.isOpenDebugLog() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("callJS >>>> instanceId:").append(instanceId)
+              .append("function:").append(function);
+      if(logTaskDetail) {
+        mLodBuilder.append(" tasks:").append(argsToJSON(args));
+      }
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.execJSWithCallback(instanceId, namespace, function, args, callback);
+    }
+  }
+
+  public @NonNull static String argsToJSON(WXJSObject[] args) {
+    StringBuilder builder = new StringBuilder();
+    builder.append("[");
+    for(WXJSObject object : args){
+      builder.append(WXWsonJSONSwitch.fromObjectToJSONString(object));
+      builder.append(",");
+    }
+    builder.append("]");
+    return  builder.toString();
+  }
+
+  private void invokeInitFramework(Message msg) {
+    String framework = "";
+    if (msg.obj != null) {
+      framework = (String) msg.obj;
+    }
+
+    if (WXUtils.getAvailMemory(WXEnvironment.getApplication()) > LOW_MEM_VALUE) {
+      initFramework(framework);
+    }
+  }
+
+  public static long sInitFrameWorkTimeOrigin;
+  public static StringBuilder sInitFrameWorkMsg = new StringBuilder();
+
+  private void initFramework(String framework) {
+    LogDetail logDetail = new LogDetail();
+    logDetail.name("initFramework");
+    logDetail.taskStart();
+    if (WXSDKEngine.isSoInitialized() && !isJSFrameworkInit()) {
+      sInitFrameWorkTimeOrigin = System.currentTimeMillis();
+      if (TextUtils.isEmpty(framework)) {
+        // if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.d("weex JS framework from assets");
+        // }
+
+        LogDetail logDetail2 = new LogDetail();
+        logDetail2.name("loadJSFramework");
+        logDetail2.taskStart();
+
+        IWXJsFileLoaderAdapter wxJsFileLoaderAdapter = WXSDKEngine.getIWXJsFileLoaderAdapter();
+
+        if (!isSandBoxContext) {
+          if(wxJsFileLoaderAdapter != null) {
+            framework = wxJsFileLoaderAdapter.loadJsFramework();
+          }
+
+          if(TextUtils.isEmpty(framework)) {
+            framework = WXFileUtils.loadAsset("main.js", WXEnvironment.getApplication());
+          }
+        } else {
+          if(wxJsFileLoaderAdapter != null) {
+            framework = wxJsFileLoaderAdapter.loadJsFrameworkForSandBox();
+          }
+
+          if(TextUtils.isEmpty(framework)) {
+            framework = WXFileUtils.loadAsset("weex-main-jsfm.js", WXEnvironment.getApplication());
+          }
+        }
+        sInitFrameWorkMsg.append("| weex JS framework from assets, isSandBoxContext: ").append(isSandBoxContext);
+        logDetail2.taskEnd();
+      }
+      if (TextUtils.isEmpty(framework)) {
+        setJSFrameworkInit(false);
+        sInitFrameWorkMsg.append("| framework isEmpty ");
+        WXExceptionUtils.commitCriticalExceptionRT(null, WXErrorCode.WX_ERR_JS_FRAMEWORK,
+                "initFramework", "framework is empty!! ", null);
+        return;
+      }
+      try {
+        if (WXSDKManager.getInstance().getWXStatisticsListener() != null) {
+          long start = System.currentTimeMillis();
+          WXSDKManager.getInstance().getWXStatisticsListener().onJsFrameworkStart();
+          WXEnvironment.sJSFMStartListenerTime = System.currentTimeMillis() - start;
+          try {
+            IWXUserTrackAdapter adapter = WXSDKManager.getInstance().getIWXUserTrackAdapter();
+            if (null != adapter){
+              Map<String,Serializable> params = new HashMap<>(1);
+              params.put("time",String.valueOf(WXEnvironment.sJSFMStartListenerTime));
+              adapter.commit(WXEnvironment.getApplication(),"sJSFMStartListener",IWXUserTrackAdapter.COUNTER,null,params);
+            }
+          }catch (Exception e){
+            WXLogUtils.e(WXLogUtils.getStackTrace(e));
+          }
+        }
+
+        long start = System.currentTimeMillis();
+        String crashFile = "";
+        try {
+          crashFile = WXEnvironment.getApplication().getApplicationContext().getCacheDir().getPath();
+        } catch (Exception e) {
+          WXLogUtils.e(WXLogUtils.getStackTrace(e));
+        }
+        boolean pieSupport = true;
+        try {
+          if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
+            pieSupport = false;
+          }
+        } catch (Exception e) {
+          WXLogUtils.e(WXLogUtils.getStackTrace(e));
+        }
+        sInitFrameWorkMsg.append(" | pieSupport:").append(pieSupport);
+        WXLogUtils.d("[WXBridgeManager] initFrameworkEnv crashFile:" + crashFile + " pieSupport:" + pieSupport);
+        // extends initFramework
+        LogDetail logDetail3 = new LogDetail();
+        logDetail3.name("native initFrameworkEnv");
+        logDetail3.taskStart();
+        if (mWXBridge.initFrameworkEnv(framework, assembleDefaultOptions(), crashFile, pieSupport) == INIT_FRAMEWORK_OK) {
+          logDetail3.taskEnd();
+          WXEnvironment.sJSLibInitTime = System.currentTimeMillis() - start;
+          WXEnvironment.sSDKInitTime = System.currentTimeMillis() - WXEnvironment.sSDKInitStart;
+          setJSFrameworkInit(true);
+          logDetail.taskEnd();
+          if (WXSDKManager.getInstance().getWXStatisticsListener() != null) {
+            WXSDKManager.getInstance().getWXStatisticsListener().onJsFrameworkReady();
+          }
+
+          execRegisterFailTask();
+          WXEnvironment.JsFrameworkInit = true;
+          sInitFrameWorkCount++;
+          WXLogUtils.e("initFrameWorkCount :"+ sInitFrameWorkCount);
+          registerDomModule();
+          trackComponentAndModulesTime();
+        } else {
+          sInitFrameWorkMsg.append(" | ExecuteJavaScript fail, reInitCount").append(reInitCount);
+          if (reInitCount > 1) {
+            WXLogUtils.e("[WXBridgeManager] invokeReInitFramework  ExecuteJavaScript fail");
+          } else {
+            WXLogUtils.e("[WXBridgeManager] invokeInitFramework  ExecuteJavaScript fail");
+          }
+        }
+      } catch (Throwable e) {
+        sInitFrameWorkMsg.append(" | invokeInitFramework exception ").append(e.toString());
+        if (reInitCount > 1) {
+          WXLogUtils.e("[WXBridgeManager] invokeInitFramework ", e);
+        } else {
+          WXLogUtils.e("[WXBridgeManager] invokeInitFramework ", e);
+        }
+      }
+
+    }
+  }
+
+  private void trackComponentAndModulesTime() {
+    post(new Runnable() {
+      @Override
+      public void run() {
+        WXEnvironment.sComponentsAndModulesReadyTime = System.currentTimeMillis() - WXEnvironment.sSDKInitStart;
+      }
+    });
+  }
+
+  @SuppressWarnings("unchecked")
+  private void invokeCallJSBatch(Message message) {
+    if (mNextTickTasks.isEmpty() || !isJSFrameworkInit()) {
+      if (!isJSFrameworkInit()) {
+        WXLogUtils.e("[WXBridgeManager] invokeCallJSBatch: framework.js uninitialized!!  message:" + message.toString());
+      }
+      return;
+    }
+
+    try {
+      Object instanceId = message.obj;
+
+      Object task = null;
+      Stack<String> instanceStack = mNextTickTasks.getInstanceStack();
+      int size = instanceStack.size();
+      for (int i = size - 1; i >= 0; i--) {
+        instanceId = instanceStack.get(i);
+        task = mNextTickTasks.remove(instanceId);
+        if (task != null && !((ArrayList) task).isEmpty()) {
+          break;
+        }
+      }
+      if (null != task){
+        task = ((ArrayList) task).toArray();
+
+        WXJSObject[] args = {
+            new WXJSObject(WXJSObject.String, instanceId),
+            WXWsonJSONSwitch.toWsonOrJsonWXJSObject(task)};
+
+        invokeExecJS(String.valueOf(instanceId), null, METHOD_CALL_JS, args);
+      }
+    } catch (Throwable e) {
+      WXLogUtils.e("WXBridgeManager", e);
+      String err = "invokeCallJSBatch#" + WXLogUtils.getStackTrace(e);
+      WXExceptionUtils.commitCriticalExceptionRT(null, WXErrorCode.WX_ERR_JS_FRAMEWORK,
+              "invokeCallJSBatch", err, null);
+    }
+
+    // If task is not empty, loop until it is empty
+    if (!mNextTickTasks.isEmpty()) {
+      mJSHandler.sendEmptyMessage(WXJSBridgeMsgType.CALL_JS_BATCH);
+    }
+  }
+
+  private WXParams assembleDefaultOptions() {
+    checkJsEngineMultiThread();
+
+    Map<String, String> config = WXEnvironment.getConfig();
+    WXParams wxParams = new WXParams();
+    wxParams.setPlatform(config.get(WXConfig.os));
+    wxParams.setCacheDir(config.get(WXConfig.cacheDir));
+    wxParams.setOsVersion(config.get(WXConfig.sysVersion));
+    wxParams.setAppVersion(config.get(WXConfig.appVersion));
+    wxParams.setWeexVersion(config.get(WXConfig.weexVersion));
+    wxParams.setDeviceModel(config.get(WXConfig.sysModel));
+    wxParams.setShouldInfoCollect(config.get("infoCollect"));
+    wxParams.setLogLevel(config.get(WXConfig.logLevel));
+    wxParams.setLayoutDirection(config.get(WXConfig.layoutDirection));
+    wxParams.setUseSingleProcess(isUseSingleProcess ? "true" : "false");
+    wxParams.setCrashFilePath(WXEnvironment.getCrashFilePath(WXEnvironment.getApplication().getApplicationContext()));
+    wxParams.setLibJsbPath(WXEnvironment.CORE_JSB_SO_PATH);
+    wxParams.setLibJssPath(WXEnvironment.getLibJssRealPath());
+    wxParams.setLibIcuPath(WXEnvironment.getLibJssIcuPath());
+    wxParams.setLibLdPath(WXEnvironment.getLibLdPath());
+    String libJScRealPath = WXEnvironment.getLibJScRealPath();
+    wxParams.setLibJscPath(TextUtils.isEmpty(libJScRealPath)? "" : new File(libJScRealPath).getParent());
+    String appName = config.get(WXConfig.appName);
+    if (!TextUtils.isEmpty(appName)) {
+      wxParams.setAppName(appName);
+    }
+    wxParams.setDeviceWidth(TextUtils.isEmpty(config.get("deviceWidth")) ? String.valueOf(WXViewUtils.getScreenWidth(WXEnvironment.sApplication)) : config.get("deviceWidth"));
+    wxParams.setDeviceHeight(TextUtils.isEmpty(config.get("deviceHeight")) ? String.valueOf(WXViewUtils.getScreenHeight(WXEnvironment.sApplication)) : config.get("deviceHeight"));
+    Map<String, String> customOptions = WXEnvironment.getCustomOptions();
+    customOptions.put("enableBackupThread", String.valueOf(jsEngineMultiThreadEnable()));
+    IWXJscProcessManager wxJscProcessManager = WXSDKManager.getInstance().getWXJscProcessManager();
+    if(wxJscProcessManager != null) {
+      customOptions.put("enableBackupThreadCache", String.valueOf(wxJscProcessManager.enableBackUpThreadCache()));
+    }
+
+    if (!WXEnvironment.sUseRunTimeApi){
+      customOptions.put("__enable_native_promise__","true");
+    }
+
+    String enableAlarmSignal = "true";
+    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
+    if (null != adapter){
+      try {
+        if (adapter.checkMode("white_screen_fix_open")){
+          WXEnvironment.isWsFixMode = true;
+          enableAlarmSignal = "true";
+        }else {
+          enableAlarmSignal = adapter.getConfigWhenInit("wxapm","enableAlarmSignal",enableAlarmSignal);
+          WXEnvironment.isWsFixMode = "true".equalsIgnoreCase(enableAlarmSignal);
+        }
+      }catch (Exception e){
+        e.printStackTrace();
+      }
+    }
+    if (null != enableAlarmSignal){
+      customOptions.put("enableAlarmSignal",enableAlarmSignal);
+    }
+    WXLogUtils.e("weex","enableAlarmSignal:"+enableAlarmSignal);
+
+    wxParams.setOptions(customOptions);
+    wxParams.setNeedInitV8(WXSDKManager.getInstance().needInitV8());
+    mInitParams = wxParams;
+    return wxParams;
+  }
+
+  public WXParams getInitParams() {
+    return mInitParams;
+  }
+
+  private void execRegisterFailTask() {
+
+    if (mRegisterModuleFailList.size() > 0) {
+      List<Map<String, Object>> moduleReceiver = new ArrayList<>();
+      for (int i = 0, moduleCount = mRegisterModuleFailList.size(); i < moduleCount; ++i) {
+        invokeRegisterModules(mRegisterModuleFailList.get(i), moduleReceiver);
+      }
+      mRegisterModuleFailList.clear();
+      if (moduleReceiver.size() > 0) {
+        mRegisterModuleFailList.addAll(moduleReceiver);
+      }
+    }
+
+    if (mRegisterComponentFailList.size() > 0) {
+      List<Map<String, Object>> receiver = new ArrayList<>();
+      invokeRegisterComponents(mRegisterComponentFailList, receiver);
+      mRegisterComponentFailList.clear();
+      if (receiver.size() > 0) {
+        mRegisterComponentFailList.addAll(receiver);
+      }
+    }
+
+    if (mRegisterServiceFailList.size() > 0) {
+      List<String> receiver = new ArrayList<>();
+      for (String service : mRegisterServiceFailList) {
+        invokeExecJSService(service, receiver);
+      }
+      mRegisterServiceFailList.clear();
+      if (receiver.size() > 0) {
+        mRegisterServiceFailList.addAll(receiver);
+      }
+    }
+  }
+
+  /**
+   * Register Android module
+   *
+   * @param modules the format is like
+   *                {'dom':['updateAttrs','updateStyle'],'event':['openUrl']}
+   */
+
+  public void registerModules(final Map<String, Object> modules) {
+    if (modules != null && modules.size() != 0) {
+      if (isJSThread()) {
+        invokeRegisterModules(modules, mRegisterModuleFailList);
+      } else {
+        post(new Runnable() {
+          @Override
+          public void run() {
+            invokeRegisterModules(modules, mRegisterModuleFailList);
+          }
+        });
+      }
+    }
+  }
+
+  /**
+   * Registered component
+   */
+  public void registerComponents(final List<Map<String, Object>> components) {
+    if (mJSHandler == null || components == null
+            || components.size() == 0) {
+      return;
+    }
+    Runnable runnable = new Runnable() {
+      @Override
+      public void run() {
+        invokeRegisterComponents(components, mRegisterComponentFailList);
+      }
+    };
+
+    if(isJSThread() && isJSFrameworkInit()){
+      runnable.run();
+    }else{
+      post(runnable);
+    }
+  }
+
+  public void execJSService(final String service) {
+    postWithName(new Runnable() {
+      @Override
+      public void run() {
+        invokeExecJSService(service, mRegisterServiceFailList);
+      }
+    },null,"execJSService");
+  }
+
+  private void invokeExecJSService(String service, List<String> receiver) {
+    try {
+      if (!isJSFrameworkInit()) {
+        WXLogUtils.e("[WXBridgeManager] invoke execJSService: framework.js uninitialized.");
+        receiver.add(service);
+        return;
+      }
+      mWXBridge.execJSService(service);
+    } catch (Throwable e) {
+      WXLogUtils.e("[WXBridgeManager] invokeRegisterService:", e);
+
+      Map<String, String> data = new HashMap<String, String>();
+      data.put("inputParams",service + "||" + receiver.toString());
+
+      WXExceptionUtils.commitCriticalExceptionRT("invokeExecJSService",
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_JSSERVICE_EXECUTE,
+              "invokeExecJSService",
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_JSSERVICE_EXECUTE.getErrorMsg()
+                      + "[WXBridgeManager] invokeRegisterService:"
+                      + WXLogUtils.getStackTrace(e),
+              data);
+    }
+  }
+
+  public boolean isJSThread() {
+    return mJSThread != null && mJSThread.getId() == Thread.currentThread().getId();
+  }
+
+  private void invokeRegisterModules(Map<String, Object> modules, List<Map<String, Object>> failReceiver) {
+    if (modules == null || !isJSFrameworkInit()) {
+      if (!isJSFrameworkInit()) {
+        WXLogUtils.d("[WXinvokeRegisterModulesBridgeManager] invokeRegisterModules: framework.js uninitialized.");
+      }
+      failReceiver.add(modules);
+      return;
+    }
+
+    WXJSObject[] args = {WXWsonJSONSwitch.toWsonOrJsonWXJSObject(modules)};
+    String errorMsg = null;
+    try{
+      // TODO use a better way
+      if (mWXBridge instanceof WXBridge) {
+        ((WXBridge) mWXBridge).registerModuleOnDataRenderNode(WXJsonUtils.fromObjectToJSONString(modules));
+      }
+    } catch (Throwable e){
+      WXLogUtils.e("Weex [data_render register err]", e);
+    }
+    try {
+        if(0 == mWXBridge.execJS("", null, METHOD_REGISTER_MODULES, args)) {
+            errorMsg = "execJS error";
+        }
+      try {
+        Iterator<String> iter = modules.keySet().iterator();
+        while (iter.hasNext()) {
+          String module = iter.next();
+          if (module != null) {
+            WXModuleManager.resetModuleState(module, true);
+            //WXLogUtils.e("[WXBridgeManager]invokeRegisterModules METHOD_REGISTER_MODULES success module:" + module);
+          }
+        }
+      } catch (Throwable e) {
+        WXLogUtils.e("Weex [invokeRegisterModules]", e);
+      }
+    } catch (Throwable e) {
+      errorMsg = WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_MODULES.getErrorMsg() +
+                " \n " + e.getMessage() + modules.entrySet().toString();
+    }
+
+    if(!TextUtils.isEmpty(errorMsg)) {
+        WXLogUtils.e("[WXBridgeManager] invokeRegisterModules:", errorMsg);
+        WXExceptionUtils.commitCriticalExceptionRT(null,
+                WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_MODULES,
+                "invokeRegisterModules", errorMsg,
+                null );
+    }
+  }
+
+  private void invokeRegisterComponents(List<Map<String, Object>> components, List<Map<String, Object>> failReceiver) {
+    if (components == failReceiver) {
+      throw new RuntimeException("Fail receiver should not use source.");
+    }
+    if (!isJSFrameworkInit()) {
+      //WXLogUtils.e("[WXBridgeManager] invokeRegisterComponents: framework.js uninitialized.");
+
+      for (Map<String, Object> comp : components) {
+        failReceiver.add(comp);
+      }
+      return;
+    }
+    if (components == null) {
+      return;
+    }
+
+    try{
+      // TODO use a better way
+      if (mWXBridge instanceof WXBridge) {
+        ((WXBridge) mWXBridge).registerComponentOnDataRenderNode(WXJsonUtils.fromObjectToJSONString(components));
+      }
+    } catch (Throwable e){
+      WXLogUtils.e("Weex [data_render register err]", e);
+    }
+
+    WXJSObject[] args = {WXWsonJSONSwitch.toWsonOrJsonWXJSObject(components)};
+    String errorMsg = null;
+    try {
+      if(0 == mWXBridge.execJS("", null, METHOD_REGISTER_COMPONENTS, args)) {
+          errorMsg = "execJS error";
+      }
+    } catch (Throwable e) {
+        errorMsg = WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT
+                + args.toString()
+                + WXLogUtils.getStackTrace(e);
+    }
+
+    if(!TextUtils.isEmpty(errorMsg)) {
+        WXLogUtils.e("[WXBridgeManager] invokeRegisterComponents ", errorMsg);
+        WXExceptionUtils.commitCriticalExceptionRT(null,
+                WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT,
+                METHOD_REGISTER_COMPONENTS, errorMsg,
+                null);
+    }
+  }
+
+  public void destroy() {
+    if (mJSThread != null) {
+      mJSThread.quit();
+    }
+    mBridgeManager = null;
+    if (mDestroyedInstanceId != null) {
+      mDestroyedInstanceId.clear();
+    }
+
+  }
+
+  /**
+   * Report JavaScript Exception
+   */
+  public void reportJSException(String instanceId, String function,
+                                String exception) {
+    WXLogUtils.e("reportJSException >>>> instanceId:" + instanceId
+            + ", exception function:" + function + ", exception:"
+            + exception);
+    WXSDKInstance instance = null;
+    WXErrorCode reportErrorCode = WXErrorCode.WX_ERR_JS_EXECUTE;
+    if (instanceId != null && (instance = WXSDKManager.getInstance().getSDKInstance(instanceId)) != null) {
+      instance.setHasException(true);
+      exception +=   "\n getTemplateInfo==" +instance.getTemplateInfo();//add network header info
+      if ((METHOD_CREATE_INSTANCE.equals(function)) || !instance.isContentMd5Match()) {
+        try {
+          //data render mode should report exception instead of reload page,
+          // so we use !isSkipFrameworkInit(instanceId) to skip the positive branch of if clause.
+          if (!isSkipFrameworkInit(instanceId) && isJSFrameworkInit() && (reInitCount > 1 && reInitCount < 10) && !instance.isNeedReLoad()) {
+            new ActionReloadPage(instanceId, true).executeAction();
+            instance.setNeedLoad(true);
+            return;
+          } else {
+            String errorMsg = new StringBuilder()
+                .append(WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorMsg())
+                .append(", exception function:").append(function)
+                .append(", exception:").append(exception)
+                .append(", extInitTime:").append(System.currentTimeMillis()-WXBridgeManager.sInitFrameWorkTimeOrigin).append("ms")
+                .append(", extInitErrorMsg:").append(WXBridgeManager.sInitFrameWorkMsg.toString())
+                .toString();
+            instance.onRenderError(//DegradPassivity to H5
+                     WXErrorCode.WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED.getErrorCode(),
+                     errorMsg
+            );
+            if (!WXEnvironment.sInAliWeex){
+              WXExceptionUtils.commitCriticalExceptionRT(instanceId, WXErrorCode.WX_RENDER_ERR_JS_CREATE_INSTANCE, function,exception,null);
+            }
+            return;
+          }
+        } catch (Exception e) {
+          WXLogUtils.e(WXLogUtils.getStackTrace(e));
+        }
+      }
+      if (METHOD_CREATE_INSTANCE.equals(function) && !instance.getApmForInstance().hasAddView){
+        reportErrorCode = WXErrorCode.WX_RENDER_ERR_JS_CREATE_INSTANCE;
+      } else if ( METHOD_CREATE_INSTANCE_CONTEXT.equals(function) && !instance.getApmForInstance().hasAddView){
+        reportErrorCode = WXErrorCode.WX_RENDER_ERR_JS_CREATE_INSTANCE_CONTEXT;
+      } else if (
+          (METHOD_UPDATE_COMPONENT_WITH_DATA.equals(function) ||
+          METHOD_CREATE_PAGE_WITH_CONTENT.equals(function) ||
+          METHOD_POST_TASK_TO_MSG_LOOP.equals(function) ||
+              METHOD_JSFM_NOT_INIT_IN_EAGLE_MODE.equals(function) )
+          && !instance.getApmForInstance().hasAddView){
+        reportErrorCode = WXErrorCode.WX_DEGRAD_EAGLE_RENDER_ERROR;
+      } else if (METHOD_MOVE_RENDER_OBJECT.equals(function)) {
+        reportErrorCode = WXErrorCode.WX_ERROR_MOVE_RENDER_OBJECT_OUT_OF_BOUNDS;
+      }
+      instance.onJSException(reportErrorCode.getErrorCode(), function, exception);
+    }
+    doReportJSException(instanceId,function,reportErrorCode,exception);
+  }
+
+  private void doReportJSException(String instanceId, String function,WXErrorCode reportCode, String exception){
+    WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
+    IWXJSExceptionAdapter adapter = WXSDKManager.getInstance().getIWXJSExceptionAdapter();
+    if (adapter != null) {
+      String exceptionId = instanceId;
+
+      if (TextUtils.isEmpty(instanceId)) {
+        exceptionId = "instanceIdisNull";
+      }
+
+      if (instance == null) {
+        if (("initFramework").equals(function)) {
+          String exceptionExt = null;
+          try {
+            if (WXEnvironment.getApplication() != null) {
+              final String fileName = WXEnvironment.getApplication().getApplicationContext().getCacheDir().getPath() + INITLOGFILE;
+              try {
+                File file = new File(fileName);
+                if (file.exists()) {
+                  if (file.length() > 0) {
+                    StringBuilder result = new StringBuilder();
+                    try {
+                      InputStreamReader read = new InputStreamReader(new FileInputStream(file), "UTF-8");
+                      BufferedReader br = new BufferedReader(read);
+                      String s = null;
+                      while ((s = br.readLine()) != null) {
+                        result.append(s + "\n");
+                      }
+                      exceptionExt = result.toString();
+                      br.close();
+                    } catch (Exception e) {
+                      WXLogUtils.e(WXLogUtils.getStackTrace(e));
+                    }
+                  }
+                  file.delete();
+                }
+              } catch (Throwable throwable) {
+                WXLogUtils.e(WXLogUtils.getStackTrace(throwable));
+              }
+            }
+          } catch (Throwable e) {
+            WXLogUtils.e(WXLogUtils.getStackTrace(e));
+          }
+          exception += "\n" + exceptionExt;
+          WXLogUtils.e("reportJSException:" + exception);
+
+        }
+      }
+
+
+      WXExceptionUtils.commitCriticalExceptionRT(exceptionId, reportCode,
+            function,
+          reportCode.getErrorMsg() + exception,
+            null);
+
+    }
+  }
+
+  private void registerDomModule() throws WXException {
+    /** Tell Javascript Framework what methods you have. This is Required.**/
+    Map<String, Object> domMap = new HashMap<>();
+    domMap.put(WXDomModule.WXDOM, WXDomModule.METHODS);
+    registerModules(domMap);
+  }
+
+  //This method is deprecated because of performance issue.
+  @Deprecated
+  public void notifyTrimMemory() {
+
+  }
+
+  /**
+   * update js server global config, current support turn wson off
+   * by pass wson_off
+   * */
+  public static void  updateGlobalConfig(String config) {
+    if(TextUtils.isEmpty(config)){
+      config = "none";
+    }
+    if(!TextUtils.equals(config, globalConfig)){
+      globalConfig = config;
+      WXEnvironment.addCustomOptions(GLOBAL_CONFIG_KEY, globalConfig);
+      Runnable runnable = new Runnable() {
+        @Override
+        public void run() {
+          if(mBridgeManager != null){
+            if(mBridgeManager.isJSFrameworkInit()){
+              if(mBridgeManager.mWXBridge instanceof WXBridge) {
+                final WXBridge bridge = (WXBridge) mBridgeManager.mWXBridge;
+                bridge.nativeUpdateGlobalConfig(globalConfig);
+              }
+            }
+          }
+          if(globalConfig.contains(WXWsonJSONSwitch.WSON_OFF)){
+            WXWsonJSONSwitch.USE_WSON = false;
+          }else{
+            WXWsonJSONSwitch.USE_WSON = true;
+          }
+        }
+      };
+      if(mBridgeManager != null && mBridgeManager.isJSFrameworkInit()){
+        mBridgeManager.post(runnable);
+      }else{
+        runnable.run();
+      }
+    }
+  }
+
+  public
+  @Nullable
+  Looper getJSLooper() {
+    Looper ret = null;
+    if (mJSThread != null) {
+      ret = mJSThread.getLooper();
+    }
+    return ret;
+  }
+
+  public void notifySerializeCodeCache() {
+    post(new Runnable() {
+      @Override
+      public void run() {
+        if (!isJSFrameworkInit())
+          return;
+
+        invokeExecJS("", null, METHOD_NOTIFY_SERIALIZE_CODE_CACHE, new WXJSObject[0]);
+      }
+    });
+  }
+
+  public void takeJSHeapSnapshot(String filename) {
+    Message msg = mJSHandler.obtainMessage();
+    msg.obj = filename;
+    msg.what = WXJSBridgeMsgType.TAKE_HEAP_SNAPSHOT;
+    msg.setTarget(mJSHandler);
+    msg.sendToTarget();
+  }
+
+  public static class TimerInfo {
+
+    public String callbackId;
+    public long time;
+    public String instanceId;
+  }
+
+  public int callCreateBody(String pageId, String componentType, String ref,
+                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
+                            float[] margins, float[] paddings, float[] borders) {
+
+    if (TextUtils.isEmpty(pageId) || TextUtils.isEmpty(componentType) || TextUtils.isEmpty(ref)) {
+      WXLogUtils.d("[WXBridgeManager] call callCreateBody arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(pageId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callCreateBody",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callCreateBody >>>> pageId:").append(pageId)
+              .append(", componentType:").append(componentType).append(", ref:").append(ref)
+              .append(", styles:").append(styles == null ? "{}" : styles.toString())
+              .append(", attributes:").append(attributes)
+              .append(", events:").append(events);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(pageId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(pageId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionCreateBody(instance, ref, componentType,
+                styles, attributes, events, margins, paddings, borders);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callCreateBody exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(pageId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callCreateBody",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callAddElement(String pageId, String componentType, String ref, int index, String parentRef,
+                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
+                            float[] margins, float[] paddings, float[] borders,boolean willLayout) {
+    if (TextUtils.isEmpty(pageId) || TextUtils.isEmpty(componentType) || TextUtils.isEmpty(ref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callAddElement arguments is null");
+      }
+      WXExceptionUtils.commitCriticalExceptionRT(pageId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callAddElement",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callAddElement >>>> pageId:").append(pageId)
+              .append(", componentType:").append(componentType).append(", ref:").append(ref).append(", index:").append(index)
+              .append(", parentRef:").append(parentRef)
+              .append(", styles:").append(styles == null ? "{}" : styles.toString())
+              .append(", attributes:").append(attributes)
+              .append(", events:").append(events);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(pageId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(pageId);
+      if (instance != null) {
+        final GraphicActionAddElement action = new GraphicActionAddElement(instance, ref, componentType, parentRef, index,
+            styles, attributes, events, margins, paddings, borders);
+        if(willLayout) {
+          instance.addInActiveAddElementAction(ref, action);
+        }else{
+          WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(pageId, action);
+        }
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callAddElement exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(pageId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callAddElement",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callRemoveElement(String instanceId, String ref) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callRemoveElement arguments is null");
+      }
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRemoveElement",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callRemoveElement >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionRemoveElement(instance, ref);
+        if(instance.getInActiveAddElementAction(ref)!=null){
+          instance.removeInActiveAddElmentAction(ref);
+        }
+        else {
+          WXSDKManager.getInstance().getWXRenderManager()
+              .postGraphicAction(action.getPageId(), action);
+        }
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callRemoveElement exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRemoveElement",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callMoveElement(String instanceId, String ref, String parentref, int index) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref) || TextUtils.isEmpty(parentref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callMoveElement arguments is null");
+      }
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callMoveElement",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callMoveElement >>>> instanceId:").append(instanceId)
+              .append(", parentref:").append(parentref)
+              .append(", index:").append(index)
+              .append(", ref:").append(ref);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionMoveElement(instance, ref, parentref, index);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callMoveElement exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callMoveElement",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callAddEvent(String instanceId, String ref, String event) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref) || TextUtils.isEmpty(event)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callAddEvent arguments is null");
+      }
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callAddEvent",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callAddEvent >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref)
+              .append(", event:").append(event);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        new GraphicActionAddEvent(instance, ref, event).executeActionOnRender();
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callAddEvent exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callAddEvent",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    // get next tick
+    getNextTick(instanceId);
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callRemoveEvent(String instanceId, String ref, String event) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref) || TextUtils.isEmpty(event)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callRemoveEvent arguments is null");
+      }
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRemoveEvent",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callRemoveEvent >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref)
+              .append(", event:").append(event);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        new GraphicActionRemoveEvent(instance, ref, event).executeActionOnRender();
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callRemoveEvent exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRemoveEvent",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    // get next tick
+    getNextTick(instanceId);
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callUpdateStyle(String instanceId, String ref, HashMap<String, Object> styles,
+                             HashMap<String, String> paddings,
+                             HashMap<String, String> margins,
+                             HashMap<String, String> borders) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callUpdateStyle arguments is null");
+      }
+
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateStyle",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callUpdateStyle >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref).append(", styles:").append(styles == null ? "{}" : styles.toString())
+              .append(", paddings:").append(paddings.toString())
+                      .append(", margins:").append(margins.toString())
+                              .append(", borders:").append(borders.toString());
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionUpdateStyle(instance, ref, styles, paddings, margins, borders);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callUpdateStyle exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateStyle",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callUpdateAttrs(String instanceId, String ref, HashMap<String, String> attrs) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callUpdateAttrs arguments is null");
+      }
+
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateAttrs",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callUpdateAttrs >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref).append(", attrs:").append(attrs.toString());
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionUpdateAttr(instance, ref, attrs);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callUpdateAttrs exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateAttrs",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  private void setExceedGPULimitComponentsInfo(String instanceId,String ref,GraphicSize layoutSize){
+    float limit = WXRenderManager.getOpenGLRenderLimitValue();
+    if(limit > 0 && (layoutSize.getHeight() > limit || layoutSize.getWidth() > limit)){
+      JSONObject ext = new JSONObject();
+      WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(instanceId,ref);
+      ext.put("GPU limit",String.valueOf(limit));
+      ext.put("component.width",String.valueOf(layoutSize.getWidth()));
+      ext.put("component.height",String.valueOf(layoutSize.getHeight()));
+      if (component.getComponentType() != null && !component.getComponentType().isEmpty()) {
+        ext.put("component.type", component.getComponentType());
+      }
+      if (component.getStyles() != null && !component.getStyles().isEmpty()) {
+        ext.put("component.style", component.getStyles().toString());
+      }
+      if (component.getAttrs() != null && !component.getAttrs().isEmpty()) {
+        ext.put("component.attr", component.getAttrs().toString());
+      }
+      if (component.getEvents() != null && !component.getEvents().isEmpty()) {
+        ext.put("component.event", component.getEvents().toString());
+      }
+      if (component.getMargin() != null) {
+        ext.put("component.margin", component.getMargin().toString());
+      }
+      if (component.getPadding() != null) {
+        ext.put("component.padding", component.getPadding().toString());
+      }
+      if (component.getBorder() != null) {
+        ext.put("component.border", component.getBorder().toString());
+      }
+      WXSDKManager.getInstance().getSDKInstance(instanceId).setComponentsInfoExceedGPULimit(ext);
+    }
+  }
+
+  public int callAddChildToRichtext(String instanceId, String nodeType, String ref, String parentRef, String richTextRef,
+                                    HashMap<String, String> styles, HashMap<String, String> attrs){
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callAddChildToRichtext arguments is null");
+      }
+
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callAddChildToRichtext",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callAddChildToRichtext >>>> instanceId:").append(instanceId)
+              .append(", nodeType:").append(nodeType).append(", ref:").append(ref).append(", parentRef:")
+              .append(parentRef).append(", richTextRef:").append(richTextRef).append(", styles:")
+              .append(styles.toString()).append(", attrs:").append(attrs.toString());
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionAddChildToRichtext(instance,nodeType,ref,parentRef,richTextRef,styles,attrs
+        );
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callAddChildToRichtext exception: ", WXLogUtils.getStackTrace(e));
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callAddChildToRichtext",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callRemoveChildFromRichtext(String instanceId, String ref, String parentRef, String richTextRef){
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callRemoveChildFromRichtext arguments is null");
+      }
+
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRemoveChildFromRichtext",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callRemoveChildFromRichtext >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref).append(", parentRef:").append(parentRef).append(", richTextRef:").append(richTextRef);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionRemoveChildFromRichtext(instance, ref, parentRef, richTextRef);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callRemoveChildFromRichtext exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRemoveChildFromRichtext",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callUpdateRichtextStyle(String instanceId, String ref, HashMap<String, String> styles, String parentRef, String richTextRef){
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callUpdateRichtextStyle arguments is null");
+      }
+
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateRichtextStyle",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callUpdateRichtextStyle >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref).append(", styles:").append(styles.toString()).append(", parentRef:")
+              .append(parentRef).append(", richTextRef:").append(richTextRef);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionUpdateRichtextStyle(instance, ref, styles, parentRef, richTextRef);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callUpdateRichtextStyle exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateRichtextStyle",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+  public int callUpdateRichtextChildAttr(String instanceId, String ref, HashMap<String, String> attrs, String parentRef, String richTextRef){
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
+      if (WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("[WXBridgeManager] call callUpdateRichtextChildAttr arguments is null");
+      }
+
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callUpdateRichtextChildAttr",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callUpdateRichtextChildAttr >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref).append(", attrs:").append(attrs.toString()).append(", parentRef:")
+              .append(parentRef).append(", richTextRef:").append(richTextRef);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        final BasicGraphicAction action = new GraphicActionUpdateRichtextAttr(instance, ref, attrs, parentRef, richTextRef);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callUpdateRichtextChildAttr exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callUpdateRichtextChildAttr",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callLayout(String pageId, String ref, int top, int bottom, int left, int right, int height, int width, boolean isRTL, int index) {
+
+    if (TextUtils.isEmpty(pageId) || TextUtils.isEmpty(ref)) {
+        if (WXEnvironment.isApkDebugable()){
+            WXLogUtils.d("[WXBridgeManager] call callLayout arguments is null");
+        }
+
+      WXExceptionUtils.commitCriticalExceptionRT(pageId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callLayout",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callLayout >>>> instanceId:").append(pageId)
+            .append(", ref:").append(ref).append(", height:").append(height).append(", width:").append(width)
+              .append(", top:").append(top)
+              .append(", bottom:").append(bottom)
+              .append(", left:").append(left)
+              .append(", right:").append(right);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(pageId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(pageId);
+      if (instance != null) {
+        GraphicSize size = new GraphicSize(width, height);
+        GraphicPosition position = new GraphicPosition(left, top, right, bottom);
+        setExceedGPULimitComponentsInfo(pageId,ref,size);
+        GraphicActionAddElement addAction = instance.getInActiveAddElementAction(ref);
+        if(addAction!=null) {
+          addAction.setRTL(isRTL);
+          addAction.setSize(size);
+          addAction.setPosition(position);
+          if(!TextUtils.equals(ref, WXComponent.ROOT)) {
+            addAction.setIndex(index);
+          }
+          WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(pageId, addAction);
+          instance.removeInActiveAddElmentAction(ref);
+        }
+        else {
+          final BasicGraphicAction action = new GraphicActionLayout(instance, ref, position, size, isRTL);
+          WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+        }
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callLayout exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(pageId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callLayout",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callAppendTreeCreateFinish(String instanceId, String ref) {
+
+    if (TextUtils.isEmpty(instanceId) || TextUtils.isEmpty(ref)) {
+      WXLogUtils.d("[WXBridgeManager] call callAppendTreeCreateFinish arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callAppendTreeCreateFinish",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callAppendTreeCreateFinish >>>> instanceId:").append(instanceId)
+              .append(", ref:").append(ref);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      GraphicActionAppendTreeCreateFinish action = new GraphicActionAppendTreeCreateFinish(instance, ref);
+      WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(instanceId, action);
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callAppendTreeCreateFinish exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callAppendTreeCreateFinish",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callCreateFinish(String instanceId) {
+
+    if (TextUtils.isEmpty(instanceId)) {
+      WXLogUtils.d("[WXBridgeManager] call callCreateFinish arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callCreateFinish",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callCreateFinish >>>> instanceId:").append(instanceId);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      long start = System.currentTimeMillis();
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        instance.getApmForInstance().onStage("callCreateFinish");
+        instance.firstScreenCreateInstanceTime(start);
+        GraphicActionCreateFinish action = new GraphicActionCreateFinish(instance);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(instanceId, action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callCreateFinish exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callCreateFinish",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public int callRenderSuccess(String instanceId) {
+
+    if (TextUtils.isEmpty(instanceId)) {
+      WXLogUtils.d("[WXBridgeManager] call callRenderSuccess arguments is null");
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_RENDER_ERR_BRIDGE_ARG_NULL, "callRenderSuccess",
+              "arguments is empty, INSTANCE_RENDERING_ERROR will be set", null);
+      return IWXBridge.INSTANCE_RENDERING_ERROR;
+    }
+
+    if (WXEnvironment.isApkDebugable() && BRIDGE_LOG_SWITCH) {
+      mLodBuilder.append("[WXBridgeManager] callRenderSuccess >>>> instanceId:").append(instanceId);
+      WXLogUtils.d(mLodBuilder.substring(0));
+      mLodBuilder.setLength(0);
+    }
+
+    if (mDestroyedInstanceId != null && mDestroyedInstanceId.contains(instanceId)) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    try {
+      WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+      if (instance != null) {
+        instance.getApmForInstance().onStage("callRenderSuccess");
+        GraphicActionRenderSuccess action = new GraphicActionRenderSuccess(instance);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(instanceId, action);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXBridgeManager] callRenderSuccess exception: ", e);
+      WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+              WXErrorCode.WX_KEY_EXCEPTION_INVOKE_BRIDGE, "callRenderSuccess",
+              WXLogUtils.getStackTrace(e), null);
+    }
+
+    return IWXBridge.INSTANCE_RENDERING;
+  }
+
+  public ContentBoxMeasurement getMeasurementFunc(String instanceId, long renderObjectPtr) {
+    ContentBoxMeasurement contentBoxMeasurement = null;
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (instance != null) {
+      contentBoxMeasurement = instance.getContentBoxMeasurement(renderObjectPtr);
+    }
+    return contentBoxMeasurement;
+  }
+
+  public void bindMeasurementToRenderObject(long ptr){
+    if (isJSFrameworkInit()) {
+      mWXBridge.bindMeasurementToRenderObject(ptr);
+    }
+  }
+
+
+  /**
+   * Native: Layout
+   * @param instanceId
+   * @return
+   */
+  @UiThread
+  public boolean notifyLayout(String instanceId) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      return mWXBridge.notifyLayout(instanceId);
+    }
+    return false;
+  }
+
+  @UiThread
+  public void forceLayout(String instanceId) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.forceLayout(instanceId);
+    }
+  }
+
+  /**
+   * native: OnInstanceClose
+   * should be called on JSThread
+   * @param instanceId
+   */
+  public void onInstanceClose(String instanceId) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.onInstanceClose(instanceId);
+    }
+  }
+
+  /**
+   * native: SetDefaultHeightAndWidthIntoRootDom
+   * @param instanceId
+   * @param defaultWidth
+   * @param defaultHeight
+   */
+  public void setDefaultRootSize(final String instanceId, final float defaultWidth, final float defaultHeight, final boolean isWidthWrapContent, final boolean isHeightWrapContent) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setDefaultHeightAndWidthIntoRootDom(instanceId, defaultWidth, defaultHeight, isWidthWrapContent, isHeightWrapContent);
+    }
+  }
+
+  public void setRenderContentWrapContentToCore(boolean wrap, final String instanceId) {
+    if (isJSFrameworkInit()) {
+      mWXBridge.setRenderContainerWrapContent(wrap, instanceId);
+    }
+  }
+
+  public void setStyleWidth(String instanceId, String ref, float value) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setStyleWidth(instanceId, ref, value);
+    }
+  }
+
+  public void setStyleHeight(String instanceId, String ref, float value) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setStyleHeight(instanceId, ref, value);
+    }
+  }
+
+  public long[] getFirstScreenRenderTime(String instanceId) {
+    if (isJSFrameworkInit()) {
+      return mWXBridge.getFirstScreenRenderTime(instanceId);
+    }
+    return new long[]{0, 0, 0};
+  }
+
+  public long[] getRenderFinishTime(String instanceId) {
+    if (isJSFrameworkInit()) {
+      return mWXBridge.getRenderFinishTime(instanceId);
+    }
+    return new long[]{0, 0, 0};
+  }
+
+  public void setDeviceDisplay(final String instanceId, final float deviceWidth, final float deviceHeight, final float scale) {
+    post(new Runnable() {
+      @Override
+      public void run() {
+        mWXBridge.setDeviceDisplay(instanceId, deviceWidth, deviceHeight, scale);
+      }
+    });
+  }
+
+  public void updateInitDeviceParams(final String width, final String height, final String density, final String statusHeight){
+    if(!isJSFrameworkInit()){
+      return;
+    }
+    post(new Runnable() {
+      @Override
+      public void run() {
+        mWXBridge.updateInitFrameworkParams(WXConfig.deviceWidth, width, WXConfig.deviceWidth);
+      }
+    });
+    post(new Runnable() {
+      @Override
+      public void run() {
+        mWXBridge.updateInitFrameworkParams(WXConfig.deviceHeight, height, WXConfig.deviceHeight);
+      }
+    });
+
+    post(new Runnable() {
+      @Override
+      public void run() {
+        mWXBridge.updateInitFrameworkParams(WXConfig.scale,  density, WXConfig.scale);
+      }
+    });
+
+    if(statusHeight != null){
+      post(new Runnable() {
+        @Override
+        public void run() {
+          mWXBridge.updateInitFrameworkParams(WXConfig.androidStatusBarHeight,  statusHeight, WXConfig.androidStatusBarHeight);
+        }
+      });
+    }
+  }
+
+  public void setMargin(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setMargin(instanceId, ref, edge, value);
+    }
+  }
+
+  public void setPadding(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setPadding(instanceId, ref, edge, value);
+    }
+  }
+
+  public void setPosition(String instanceId, String ref, CSSShorthand.EDGE edge, float value) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setPosition(instanceId, ref, edge, value);
+    }
+  }
+
+  public void markDirty(String instanceId, String ref, boolean dirty) {
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.markDirty(instanceId, ref, dirty);
+    }
+  }
+  public void setViewPortWidth(String instanceId,float viewPortWidth){
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setViewPortWidth(instanceId,viewPortWidth);
+    }
+  }
+  public void setPageArgument(String instanceId,String key,String value){
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setPageArgument(instanceId,key,value);
+    }
+  }
+  public void reloadPageLayout(String instanceId){
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.reloadPageLayout(instanceId);
+    }
+  }
+
+  public void setDeviceDisplayOfPage(String instanceId,float width,float height){
+    if (isSkipFrameworkInit(instanceId) || isJSFrameworkInit()) {
+      mWXBridge.setDeviceDisplayOfPage(instanceId,width,height);
+    }
+  }
+
+  public int callHasTransitionPros(String instanceId, String ref, HashMap<String, String> styles) {
+    WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(instanceId, ref);
+    if (null == component || null == component.getTransition() || null == component.getTransition().getProperties()) {
+      return IWXBridge.DESTROY_INSTANCE;
+    }
+
+    for(String property : component.getTransition().getProperties()){
+      if(styles.containsKey(property)){
+        return IWXBridge.INSTANCE_RENDERING;
+      }
+    }
+    return IWXBridge.INSTANCE_RENDERING_ERROR;
+  }
+
+  public void registerCoreEnv(String key, String value) {
+    if (isJSFrameworkInit())
+      mWXBridge.registerCoreEnv(key, value);
+    else
+      mWeexCoreEnvOptions.put(key, value);
+  }
+
+  private void onJsFrameWorkInitSuccees() {
+    for (Map.Entry<String, String> entry : mWeexCoreEnvOptions.entrySet()) {
+      mWXBridge.registerCoreEnv(entry.getKey(), entry.getValue());
+    }
+    mWeexCoreEnvOptions.clear();
+  }
+
+  public  String getWeexCoreThreadStackTrace(){
+    if (null == mJSThread){
+      return "null == mJSThread";
+    }
+    StringBuilder stringBuilder = new StringBuilder();
+
+    try {
+      stringBuilder.append(String.format("Thread Name: '%s'\n", mJSThread.getName()));
+      stringBuilder.append(String.format(Locale.ENGLISH,"\"%s\" prio=%d tid=%d %s\n", mJSThread.getName(), mJSThread.getPriority(), mJSThread.getId(), mJSThread.getState()));
+
+      for (StackTraceElement e: mJSThread.getStackTrace()){
+        stringBuilder.append(String.format("\tat %s\n", e.toString()));
+      }
+    } catch (Exception var8) {
+      Log.e("weex", "getJSThreadStackTrace error:", var8);
+    }
+    return stringBuilder.toString();
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXDebugJsBridge.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXDebugJsBridge.java
new file mode 100644
index 0000000..bed2a43
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXDebugJsBridge.java
@@ -0,0 +1,101 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import com.alibaba.fastjson.JSON;
+import org.apache.weex.utils.WXWsonJSONSwitch;
+import org.apache.weex.wson.WsonUtils;
+
+/**
+ * Created by darin on 27/03/2018.
+ */
+
+public class WXDebugJsBridge {
+
+    public native void resetWXBridge(Object bridge, String className);
+
+    public native void jsHandleSetJSVersion(String jsVersion);
+
+    public native void jsHandleReportException(String instanceId, String func, String exceptionString);
+
+    public native void jsHandleCallNative(String instanceId, byte[] tasks, String callback);
+
+    public void jsHandleCallNativeModule(String instanceId, String module, String method, byte[] arguments, byte[] options) {
+        jsHandleCallNativeModule(instanceId, module, method,
+                WXWsonJSONSwitch.convertJSONToWsonIfUseWson(arguments), WXWsonJSONSwitch.convertJSONToWsonIfUseWson(options), true);
+    }
+
+    public native void jsHandleCallNativeModule(String instanceId, String module, String method, byte[] arguments, byte[] options, boolean h5);
+
+    public void jsHandleCallNativeComponent(String instanceId, String componentRef, String method, byte[] arguments, byte[] options){
+        jsHandleCallNativeComponent(instanceId, componentRef, method, WXWsonJSONSwitch.convertJSONToWsonIfUseWson(arguments), WXWsonJSONSwitch.convertJSONToWsonIfUseWson(options), true);
+    }
+
+
+    public native void jsHandleCallNativeComponent(String instanceId, String componentRef, String method, byte[] arguments, byte[] options, boolean from);
+
+    public void jsHandleCallAddElement(String instanceId, String ref, String dom, String index){
+        jsHandleCallAddElement(instanceId, ref, WsonUtils.toWson(JSON.parse(dom)), index, true);
+    }
+
+    public native void jsHandleCallAddElement(String instanceId, String ref, byte[] dom, String index, boolean h5);
+
+    public native void jsHandleSetTimeout(String callbackId, String time);
+
+    public native void jsHandleCallNativeLog(byte[] str_array);
+
+    public void jsHandleCallCreateBody(String pageId, String domStr){
+        jsHandleCallCreateBody(pageId, WsonUtils.toWson(JSON.parse(domStr)), true);
+    }
+
+    public native void jsHandleCallCreateBody(String pageId, byte[] domStr, boolean h5);
+
+    public native void jsHandleCallUpdateFinish(String instanceId, byte[] tasks, String callback);
+
+    public native void jsHandleCallCreateFinish(String pageId);
+
+    public native void jsHandleCallRefreshFinish(String instanceId, byte[] tasks, String callback);
+
+    public void jsHandleCallUpdateAttrs(String pageId, String ref, String data){
+        jsHandleCallUpdateAttrs(pageId, ref, WsonUtils.toWson(JSON.parseObject(data)), true);
+    }
+
+    public native void jsHandleCallUpdateAttrs(String pageId, String ref, byte[] data, boolean h5);
+
+    public void jsHandleCallUpdateStyle(String pageId, String ref, String data){
+        byte[] data1 = WsonUtils.toWson(JSON.parseObject(data));
+        jsHandleCallUpdateStyleNative(pageId, ref, data1, true);
+    }
+
+    public native void jsHandleCallUpdateStyleNative(String pageId, String ref, byte[] data, boolean h5);
+
+    public native void jsHandleCallRemoveElement(String pageId, String ref);
+
+    public native void jsHandleCallMoveElement(String pageId, String ref, String parentRef, String index_str);
+
+    public native void jsHandleCallAddEvent(String pageId, String ref, String event);
+
+    public native void jsHandleCallRemoveEvent(String pageId, String ref, String event);
+
+    public native void jsHandleSetInterval(String instanceId, String callbackId, String time);
+
+    public native void jsHandleClearInterval(String instanceId, String callbackId);
+
+    public native void jsHandleCallGCanvasLinkNative(String contextId, int type, String val);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXHashMap.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXHashMap.java
new file mode 100644
index 0000000..68ca5e2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXHashMap.java
@@ -0,0 +1,90 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import android.text.TextUtils;
+
+import java.util.HashMap;
+import java.util.Stack;
+
+/**
+ * HashMap for Weex
+ */
+public class WXHashMap<K, V> extends HashMap<K, V> {
+
+  private static final long serialVersionUID = 4294272345728974369L;
+
+  private Stack<String> instancesStack = new Stack<String>();
+  private String mTag;
+
+  @Override
+  public V put(K key, V value) {
+    if (key != null && key.toString() != null) {
+      if (instancesStack.contains(key)) {
+        instancesStack.remove(key);
+      }
+      instancesStack.push(key.toString());
+    }
+    return super.put(key, value);
+  }
+
+  @Override
+  public V remove(Object key) {
+    return super.remove(key);
+  }
+
+  public V removeFromMapAndStack(Object key) {
+    instancesStack.remove(key);
+    return super.remove(key);
+  }
+
+  /**
+   * Get instance Id of the top of the stack
+   *
+   * @return
+   */
+  public String getStackTopInstanceId() {
+    return instancesStack.isEmpty() ? "" : instancesStack.pop();
+  }
+
+  /**
+   * Move instanceId to the top of the stack
+   *
+   * @param id
+   */
+  public void setStackTopInstance(String id) {
+    if (!TextUtils.isEmpty(id)) {
+      instancesStack.remove(id);
+      instancesStack.push(id);
+    }
+  }
+
+  public Stack<String> getInstanceStack() {
+    return instancesStack;
+  }
+
+  public String getTag() {
+    return mTag;
+  }
+
+  public void setTag(String tag) {
+    this.mTag = tag;
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXJSObject.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXJSObject.java
new file mode 100644
index 0000000..7642cad
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXJSObject.java
@@ -0,0 +1,72 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+
+import org.apache.weex.utils.WXJsonUtils;
+
+public class WXJSObject {
+
+    public static final int NUMBER = 1;
+    public static final int String = 2;
+    public static final int JSON = 3;
+    public static final int WSON = 4;
+
+    public Object data;
+    public int type;
+    public String key;
+
+    public WXJSObject(int type, Object data) {
+        this.type = type;
+        this.data = data;
+    }
+
+    public WXJSObject(int type, Object data, String key) {
+        this.type = type;
+        this.data = data;
+        this.key = key;
+    }
+
+    public WXJSObject(Object object) {
+
+        if(null == object){
+            type= String;
+            data = "";
+            return;
+        }
+
+        data = object;
+        if (object instanceof Integer) {
+            type = NUMBER;
+            data = (double) (Integer) object;
+        } else if (object instanceof Double) {
+            type = NUMBER;
+        } else if (object instanceof Float) {
+            type = NUMBER;
+            data = (double) ((Float) object).intValue();
+        } else if (object instanceof String) {
+            type = String;
+        } else if (object instanceof Object) {
+            type = JSON;
+            data = WXJsonUtils.fromObjectToJSONString(object,true);
+        }
+    }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXModuleManager.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXModuleManager.java
new file mode 100644
index 0000000..25fdbe6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXModuleManager.java
@@ -0,0 +1,535 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import android.content.Intent;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+import android.view.Menu;
+
+import com.alibaba.fastjson.JSONArray;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.WXSDKEngine;
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.common.Destroyable;
+import org.apache.weex.common.WXException;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.ui.config.ConfigModuleFactory;
+import org.apache.weex.ui.module.WXDomModule;
+import org.apache.weex.ui.module.WXTimerModule;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.cache.RegisterCache;
+
+import java.io.Serializable;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Map.Entry;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ConcurrentMap;
+import org.apache.weex.utils.cache.RegisterCache.ModuleCache;
+
+/**
+ * Manager class for weex module. There are two types of modules in weex, one is instance-level module,
+ * the other is global-level module. Instance-level module will be created every time an instance
+ * is created, while global-level module will be singleton in {@link WXSDKEngine}.
+ */
+public class WXModuleManager {
+
+  /**
+   * module class object dictionary
+   */
+  private static volatile ConcurrentMap<String, ModuleFactoryImpl> sModuleFactoryMap = new ConcurrentHashMap<>();
+  private static Map<String, WXModule> sGlobalModuleMap = new HashMap<>();
+  private static Map<String, WXDomModule> sDomModuleMap = new HashMap<>();
+
+
+  /**
+   * module object dictionary
+   * K : instanceId, V : Modules
+   */
+  private static Map<String, Map<String, WXModule>> sInstanceModuleMap = new ConcurrentHashMap<>();
+
+
+  public static boolean registerModule(Map<String, ModuleCache> moduleCacheMap) {
+    if (moduleCacheMap.isEmpty())
+      return true;
+
+    final Iterator<Entry<String, ModuleCache>> iterator = moduleCacheMap.entrySet().iterator();
+    WXBridgeManager.getInstance()
+            .postWithName(new Runnable() {
+              @Override
+              public void run() {
+                Map<String, Object> modules = new HashMap<>();
+
+                while (iterator.hasNext()) {
+                  Entry<String, ModuleCache> next = iterator.next();
+                  ModuleCache value = next.getValue();
+                  String moduleName = value.name;
+                  if (TextUtils.equals(moduleName, WXDomModule.WXDOM)) {
+                    WXLogUtils.e("Cannot registered module with name 'dom'.");
+                    continue;
+                  }
+
+                  if (sModuleFactoryMap != null && sModuleFactoryMap.containsKey(moduleName)) {
+                    WXLogUtils.w("WXComponentRegistry Duplicate the Module name: " + moduleName);
+                  }
+                  ModuleFactory factory = value.factory;
+                  try {
+                    registerNativeModule(moduleName, factory);
+                  } catch (WXException e) {
+                    WXLogUtils.e("registerNativeModule" + e);
+                  }
+
+                  if (value.global) {
+                    try {
+                      WXModule wxModule = factory.buildInstance();
+                      wxModule.setModuleName(moduleName);
+                      sGlobalModuleMap.put(moduleName, wxModule);
+                    } catch (Exception e) {
+                      WXLogUtils.e(moduleName + " class must have a default constructor without params. ", e);
+                    }
+                  }
+
+                  try {
+                    sModuleFactoryMap.put(moduleName, new ModuleFactoryImpl(factory));
+                  } catch (Throwable e) {
+
+                  }
+                  modules.put(moduleName, factory.getMethods());
+                }
+                WXSDKManager.getInstance().registerModules(modules);
+              }
+            },null,"registerModule From Cache");
+    return true;
+  }
+
+  /**
+   * Register module to JavaScript and Android
+   */
+  public static boolean registerModule(final String moduleName, final ModuleFactory factory, final boolean global) throws WXException {
+    if (moduleName == null || factory == null) {
+      return false;
+    }
+
+    if (TextUtils.equals(moduleName,WXDomModule.WXDOM)) {
+      WXLogUtils.e("Cannot registered module with name 'dom'.");
+      return false;
+    }
+
+    if(RegisterCache.getInstance().cacheModule(moduleName,factory,global)) {
+      return true;
+    }
+
+    //execute task in js thread to make sure register order is same as the order invoke register method.
+    WXBridgeManager.getInstance()
+            .postWithName(new Runnable() {
+              @Override
+              public void run() {
+                if (sModuleFactoryMap != null && sModuleFactoryMap.containsKey(moduleName)) {
+                  WXLogUtils.w("WXComponentRegistry Duplicate the Module name: " + moduleName);
+                }
+                try {
+                  registerNativeModule(moduleName, factory);
+                } catch (WXException e) {
+                  WXLogUtils.e("registerNativeModule" + e);
+                }
+
+                if (global) {
+                  try {
+                    WXModule wxModule = factory.buildInstance();
+                    wxModule.setModuleName(moduleName);
+                    sGlobalModuleMap.put(moduleName, wxModule);
+                  } catch (Exception e) {
+                    WXLogUtils.e(moduleName + " class must have a default constructor without params. ", e);
+                  }
+                }
+
+                registerJSModule(moduleName, factory);
+
+                try {
+                  sModuleFactoryMap.put(moduleName, new ModuleFactoryImpl(factory));
+                } catch (Throwable e) {
+
+                }
+              }
+            },null,"registerModule");
+    return true;
+
+  }
+
+  static boolean registerNativeModule(String moduleName, ModuleFactory factory) throws WXException {
+    if (factory == null) {
+      return false;
+    }
+
+    try {
+      if (!sModuleFactoryMap.containsKey(moduleName) ) {
+        sModuleFactoryMap.put(moduleName, new ModuleFactoryImpl(factory));
+      }
+    }catch (ArrayStoreException e){
+      e.printStackTrace();
+      //ignore:
+      //may throw this exception:
+      //java.lang.String cannot be stored in an array of type java.util.HashMap$HashMapEntry[]
+
+      WXLogUtils.e("[WXModuleManager] registerNativeModule Error moduleName:"  + moduleName + " Error:" + e.toString());
+    }
+    return true;
+  }
+
+  static boolean registerJSModule(String moduleName, ModuleFactory factory) {
+    Map<String, Object> modules = new HashMap<>();
+    modules.put(moduleName, factory.getMethods());
+    WXSDKManager.getInstance().registerModules(modules);
+    return true;
+  }
+
+  static Object callModuleMethod(final String instanceId, String moduleStr, String methodStr, JSONArray args) {
+    ModuleFactory factory = sModuleFactoryMap.get(moduleStr).mFactory;
+    if(factory == null){
+      WXLogUtils.e("[WXModuleManager] module factory not found.");
+      return null;
+    }
+    final WXModule wxModule = findModule(instanceId, moduleStr,factory);
+    if (wxModule == null) {
+      return null;
+    }
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    wxModule.mWXSDKInstance = instance;
+
+    final Invoker invoker = factory.getMethodInvoker(methodStr);
+    try {
+      if(instance != null) {
+        IWXUserTrackAdapter userTrackAdapter = WXSDKManager.getInstance().getIWXUserTrackAdapter();
+        if(userTrackAdapter != null) {
+          HashMap<String, Serializable> data = new HashMap<String, Serializable>();
+          data.put(IWXUserTrackAdapter.MONITOR_ERROR_CODE, "101");
+          data.put(IWXUserTrackAdapter.MONITOR_ARG, moduleStr + "." + methodStr);
+          data.put(IWXUserTrackAdapter.MONITOR_ERROR_MSG, instance.getBundleUrl());
+          userTrackAdapter.commit(instance.getContext(), null, IWXUserTrackAdapter.INVOKE_MODULE, null, data);
+        }
+        return dispatchCallModuleMethod(instance,wxModule,args,invoker);
+      } else {
+        WXLogUtils.e("callModuleMethod >>> instance is null");
+        return null;
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("callModuleMethod >>> invoke module:" + moduleStr + ", method:" + methodStr + " failed. ", e);
+      return null;
+    } finally {
+      if (wxModule instanceof WXDomModule || wxModule instanceof WXTimerModule) {
+        wxModule.mWXSDKInstance = null;
+      }
+    }
+  }
+
+  private static Object dispatchCallModuleMethod(@NonNull WXSDKInstance instance, @NonNull WXModule wxModule,
+                                                 @NonNull JSONArray args, @NonNull Invoker invoker) throws Exception{
+    if(!instance.isPreRenderMode()) {
+      return instance.getNativeInvokeHelper().invoke(wxModule,invoker,args);
+    }
+    // we are in preRender mode
+    if(invoker.isRunOnUIThread()) {/*ASYNC CALL*/
+//      DOMAction moduleInvocationAction = Actions.getModuleInvocationAction(wxModule,args,invoker);
+//      WXSDKManager.getInstance().getWXDomManager().postAction(instance.getInstanceId(), moduleInvocationAction,false);
+      return null;
+    } else {/*SYNC CALL*/
+      return instance.getNativeInvokeHelper().invoke(wxModule,invoker,args);
+    }
+  }
+
+  public static boolean hasModule(String module) {
+    return sGlobalModuleMap.containsKey(module) || sModuleFactoryMap.containsKey(module);
+  }
+
+  private static WXModule findModule(String instanceId, String moduleStr,ModuleFactory factory) {
+    // find WXModule
+    WXModule wxModule = sGlobalModuleMap.get(moduleStr);
+
+    //not global module
+    if (wxModule == null) {
+      Map<String, WXModule> moduleMap = sInstanceModuleMap.get(instanceId);
+      if (moduleMap == null) {
+        moduleMap = new ConcurrentHashMap<>();
+        sInstanceModuleMap.put(instanceId, moduleMap);
+      }
+      // if cannot find the Module, create a new Module and save it
+      wxModule = moduleMap.get(moduleStr);
+      if (wxModule == null) {
+        try {
+          if(factory instanceof ConfigModuleFactory){
+            WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+            wxModule = ((ConfigModuleFactory) factory).buildInstance(instance);
+          }else{
+            wxModule = factory.buildInstance();
+          }
+          wxModule.setModuleName(moduleStr);
+        } catch (Exception e) {
+          WXLogUtils.e(moduleStr + " module build instace failed.", e);
+          return null;
+        }
+        moduleMap.put(moduleStr, wxModule);
+      }
+    }
+
+    return wxModule;
+  }
+
+  /**Hook Activity life cycle callback begin***/
+
+
+  public static void onActivityCreate(String instanceId){
+
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onActivityCreate();
+        } else {
+          WXLogUtils.w("onActivityCreate can not find the " + key + " module");
+        }
+      }
+    }
+
+  }
+
+  public static void onActivityStart(String instanceId){
+
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onActivityStart();
+        } else {
+          WXLogUtils.w("onActivityStart can not find the " + key + " module");
+        }
+      }
+    }
+  }
+
+  public static void onActivityPause(String instanceId){
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onActivityPause();
+        } else {
+          WXLogUtils.w("onActivityPause can not find the " + key + " module");
+        }
+      }
+    }
+  }
+
+  public static void onActivityResume(String instanceId){
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onActivityResume();
+        } else {
+          WXLogUtils.w("onActivityResume can not find the " + key + " module");
+        }
+      }
+    }
+  }
+
+  public static void onActivityStop(String instanceId){
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onActivityStop();
+        } else {
+          WXLogUtils.w("onActivityStop can not find the " + key + " module");
+        }
+      }
+    }
+  }
+
+  public static void onActivityDestroy(String instanceId){
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onActivityDestroy();
+        } else {
+          WXLogUtils.w("onActivityDestroy can not find the " + key + " module");
+        }
+      }
+    }
+  }
+
+  public static boolean onActivityBack(String instanceId){
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          return module.onActivityBack();
+        } else {
+          WXLogUtils.w("onActivityCreate can not find the " + key + " module");
+        }
+      }
+    }
+    return false;
+  }
+
+  public static void onActivityResult(String instanceId,int requestCode, int resultCode, Intent data){
+
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onActivityResult(requestCode, resultCode, data);
+        } else {
+          WXLogUtils.w("onActivityResult can not find the " + key + " module");
+        }
+      }
+    }
+  }
+
+  public static boolean onCreateOptionsMenu(String instanceId,Menu menu) {
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onCreateOptionsMenu(menu);
+        } else {
+          WXLogUtils.w("onActivityResult can not find the " + key + " module");
+        }
+      }
+    }
+    return false;
+  }
+
+  public static void onRequestPermissionsResult(String instanceId ,int requestCode, String[] permissions, int[] grantResults) {
+    Map<String, WXModule> modules = sInstanceModuleMap.get(instanceId);
+    if(modules!=null) {
+      for (String key : modules.keySet()) {
+        WXModule module = modules.get(key);
+        if (module != null) {
+          module.onRequestPermissionsResult(requestCode, permissions, grantResults);
+        } else {
+          WXLogUtils.w("onActivityResult can not find the " + key + " module");
+        }
+      }
+    }
+  }
+
+  public static void destroyInstanceModules(String instanceId) {
+    sDomModuleMap.remove(instanceId);
+    Map<String, WXModule> moduleMap = sInstanceModuleMap.remove(instanceId);
+    if (moduleMap == null || moduleMap.size() < 1) {
+      return;
+    }
+    Iterator<Entry<String, WXModule>> iterator = moduleMap.entrySet().iterator();
+    Entry<String, WXModule> entry;
+    while (iterator.hasNext()) {
+      entry = iterator.next();
+      WXModule module = entry.getValue();
+      if(module instanceof Destroyable){
+        ((Destroyable)module).destroy();
+      }
+
+    }
+  }
+
+  public static void createDomModule(WXSDKInstance instance){
+    if(instance != null) {
+      sDomModuleMap.put(instance.getInstanceId(), new WXDomModule(instance));
+    }
+  }
+
+  public static void destoryDomModule(String instanceID){
+    sDomModuleMap.remove(instanceID);
+  }
+
+  public static WXDomModule getDomModule(String instanceId){
+    return sDomModuleMap.get(instanceId);
+  }
+
+  public static void reload(){
+    if (sModuleFactoryMap != null && sModuleFactoryMap.size() > 0) {
+      for (Map.Entry<String, ModuleFactoryImpl> entry : sModuleFactoryMap.entrySet()) {
+        try {
+          registerJSModule(entry.getKey(), entry.getValue().mFactory);
+        } catch (Throwable e) {
+
+        }
+      }
+    }
+  }
+
+  /**
+   * registerWhenCreateInstance
+   */
+  public static void registerWhenCreateInstance(){
+    if (sModuleFactoryMap != null && sModuleFactoryMap.size() > 0) {
+      for (Map.Entry<String, ModuleFactoryImpl> entry : sModuleFactoryMap.entrySet()) {
+        try {
+          if (!entry.getValue().hasRigster) {
+            registerJSModule(entry.getKey(), entry.getValue().mFactory);
+          }
+        } catch (Throwable e) {
+
+        }
+      }
+    }
+  }
+
+  /**
+   * resetAllModuleState
+   */
+  public static void resetAllModuleState() {
+    if (sModuleFactoryMap != null && sModuleFactoryMap.size() > 0) {
+      for (Map.Entry<String, ModuleFactoryImpl> entry : sModuleFactoryMap.entrySet()) {
+        entry.getValue().hasRigster = false;
+      }
+    }
+  }
+
+  /**
+   * resetModuleState
+   * @param module
+   * @param state
+   */
+  public static void resetModuleState(String module, boolean state) {
+    if (sModuleFactoryMap != null && sModuleFactoryMap.size() > 0) {
+      for (Map.Entry<String, ModuleFactoryImpl> entry : sModuleFactoryMap.entrySet()) {
+        try {
+          if (entry.getKey() != null && entry.getKey().equals(module)) {
+            entry.getValue().hasRigster = state;
+          }
+        } catch (Throwable e) {
+
+        }
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXParams.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXParams.java
new file mode 100644
index 0000000..7f2c265
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXParams.java
@@ -0,0 +1,303 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.base.CalledByNative;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.io.Serializable;
+import java.util.HashMap;
+import java.util.Map;
+
+public class WXParams implements Serializable {
+
+  private String platform;
+  private String osVersion;
+  private String appVersion;
+  private String weexVersion;
+  private String deviceModel;
+  private String appName;
+  private String deviceWidth;
+  private String deviceHeight;
+  private String shouldInfoCollect;
+  private String logLevel;
+  private String needInitV8;
+  private String cacheDir;
+  private String useSingleProcess;
+  private String crashFilePath;
+  private String libJssPath;
+  private String layoutDirection;
+
+  private String libJscPath;
+  private String libIcuPath;
+  private String libLdPath;
+  private String libJsbPath;
+
+  private Map<String, String> options;
+
+  @CalledByNative
+  public Object getOptions() {
+    return options;
+  }
+
+  public void setOptions(Map<String, String> options) {
+    this.options = options;
+  }
+
+  public String getShouldInfoCollect() {
+    return shouldInfoCollect;
+  }
+
+  public void setShouldInfoCollect(String shouldInfoCollect) {
+    this.shouldInfoCollect = shouldInfoCollect;
+  }
+
+  @CalledByNative
+  public String getPlatform() {
+    return platform;
+  }
+
+  public void setPlatform(String platform) {
+    this.platform = platform;
+  }
+
+  public void setCacheDir(String cache) {
+    this.cacheDir = cache;
+  }
+
+  @CalledByNative
+  public String getCacheDir() {
+    return this.cacheDir;
+  }
+
+  @CalledByNative
+  public String getOsVersion() {
+    return osVersion;
+  }
+
+  public void setOsVersion(String osVersion) {
+    this.osVersion = osVersion;
+  }
+
+  @CalledByNative
+  public String getAppVersion() {
+    return appVersion;
+  }
+
+  public void setAppVersion(String appVersion) {
+    this.appVersion = appVersion;
+  }
+
+  @CalledByNative
+  public String getWeexVersion() {
+    return weexVersion;
+  }
+
+  public void setWeexVersion(String weexVersion) {
+    this.weexVersion = weexVersion;
+  }
+
+  @CalledByNative
+  public String getDeviceModel() {
+    return deviceModel;
+  }
+
+  public void setDeviceModel(String deviceModel) {
+    this.deviceModel = deviceModel;
+  }
+
+  @CalledByNative
+  public String getLayoutDirection() {return layoutDirection;}
+
+  public void setLayoutDirection(String direction) { this.layoutDirection = direction; }
+
+  @CalledByNative
+  public String getAppName() {
+    return appName;
+  }
+
+  public void setAppName(String appName) {
+    this.appName = appName;
+  }
+
+  @CalledByNative
+  public String getDeviceWidth() {
+    return deviceWidth;
+  }
+
+  @CalledByNative
+  public boolean getReleaseMap() {
+    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
+    if (null == adapter){
+      return false;
+    }
+    String doRelease = adapter.getConfigWhenInit("wxapm","release_map","true");
+    WXLogUtils.e("getReleaseMap:"+doRelease);
+    return "true".equalsIgnoreCase(doRelease);
+  }
+
+
+  /**
+   * Device should not be set manually, instead it suppose to represent the width of device and
+   * initialized automatically.
+   * @param deviceWidth
+   */
+  @Deprecated
+  public void setDeviceWidth(String deviceWidth) {
+    this.deviceWidth = deviceWidth;
+  }
+
+  @CalledByNative
+  public String getDeviceHeight() {
+    return deviceHeight;
+  }
+
+  public void setDeviceHeight(String deviceHeight) {
+    this.deviceHeight = deviceHeight;
+  }
+
+  public String getLogLevel() {
+    if(logLevel == null){
+      return "";
+    }
+    return logLevel;
+  }
+
+  @CalledByNative
+  public String getUseSingleProcess() {
+    WXLogUtils.e("getUseSingleProcess is running " + useSingleProcess);
+    return useSingleProcess;
+  }
+
+  public void setUseSingleProcess(String useSingleProcess) {
+    this.useSingleProcess = useSingleProcess;
+  }
+
+  public void setLogLevel(String logLevel) {
+    this.logLevel = logLevel;
+  }
+
+  public String getNeedInitV8() {
+    if(needInitV8 ==null){
+      return "";
+    }
+    return this.needInitV8;
+  }
+
+  public void setNeedInitV8(boolean need) {
+    if (need) {
+      this.needInitV8 = "1";
+    } else {
+      this.needInitV8 = "0";
+    }
+  }
+
+  public void setCrashFilePath(String crashFilePath) {
+    WXLogUtils.e("WXParams","setCrashFilePath: " + crashFilePath);
+    this.crashFilePath = crashFilePath;
+  }
+
+  @CalledByNative
+  public String getCrashFilePath() {
+    WXLogUtils.e("WXParams", "getCrashFilePath:" + crashFilePath);
+    return this.crashFilePath;
+  }
+
+  @CalledByNative
+  public String getLibJssPath() {
+    WXLogUtils.e("getLibJssPath is running " + libJssPath);
+    return libJssPath;
+  }
+
+  @CalledByNative
+  public String getLibJsbPath() {
+    WXLogUtils.e("getLibJsbPath is running " + libJsbPath);
+    return libJsbPath;
+  }
+
+  public void setLibJsbPath(String libJsbPath) {
+    this.libJsbPath = libJsbPath;
+  }
+
+  @CalledByNative
+  public String getLibJscPath() {
+    WXLogUtils.e("getLibJscPath is running " + libJscPath);
+    return libJscPath;
+  }
+  public void setLibJscPath(String libJscPath) {
+    this.libJscPath = libJscPath;
+  }
+  public void setLibJssPath(String libJssPath) {
+    this.libJssPath = libJssPath;
+  }
+  @CalledByNative
+  public String getLibIcuPath() {
+    WXLogUtils.e("getLibIcuPath is running " + libIcuPath);
+    return libIcuPath;
+  }
+
+  public void setLibIcuPath(String libIcuPath) {
+    this.libIcuPath = libIcuPath;
+  }
+
+  @CalledByNative
+  public String getLibLdPath() {
+    WXLogUtils.e("getLibLdPath is running " + libLdPath);
+    return libLdPath;
+  }
+
+  public void setLibLdPath(String libLdPath) {
+    this.libLdPath = libLdPath;
+  }
+
+  @CalledByNative
+  public String getUseRunTimeApi() {
+    return String.valueOf(WXEnvironment.sUseRunTimeApi);
+  }
+
+  public Map<String, Object> toMap() {
+    HashMap<String, Object> map  = new HashMap<>();
+    map.put("appName", appName);
+    map.put("appVersion", appVersion);
+    map.put("cacheDir", cacheDir);
+    map.put("deviceHeight", deviceHeight);
+    map.put("deviceModel", deviceModel);
+    map.put("deviceWidth", deviceWidth);
+    map.put("layoutDirection", layoutDirection);
+    map.put("libJssPath", libJssPath);
+    map.put("logLevel", logLevel);
+    map.put("needInitV8", needInitV8);
+    map.put("osVersion", osVersion);
+    map.put("platform", platform);
+    map.put("useSingleProcess", useSingleProcess);
+    map.put("shouldInfoCollect", shouldInfoCollect);
+    map.put("weexVersion", weexVersion);
+    map.put("crashFilePath", crashFilePath);
+    map.put("libJscPath", libJscPath);
+    map.put("libIcuPath", libIcuPath);
+    map.put("libLdPath", libLdPath);
+    map.put("options", options);
+    map.put("useRunTimeApi",WXEnvironment.sUseRunTimeApi);
+    map.put("__enable_native_promise__",!WXEnvironment.sUseRunTimeApi);
+    return map;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXServiceManager.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXServiceManager.java
new file mode 100644
index 0000000..69ab29a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXServiceManager.java
@@ -0,0 +1,98 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import android.text.TextUtils;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.common.WXJSService;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+public class WXServiceManager {
+
+    private static volatile ConcurrentHashMap<String, WXJSService> sInstanceJSServiceMap = new ConcurrentHashMap<>();
+
+    public static boolean registerService(String name, String serviceScript, Map<String, Object> options) {
+        if (TextUtils.isEmpty(name) || TextUtils.isEmpty(serviceScript)) return false;
+
+        String param1 = "register: global.registerService, unregister: global.unregisterService";
+        String param2 = "serviceName: \"" + name + "\"";
+        for (String key: options.keySet()) {
+            // TODO - why always string?
+            Object value = options.get(key);
+            if (value instanceof  String) {
+                param2 += ", \'" + key + "\': \'" + value + "\'";
+            } else {
+                param2 += ", \'" + key + "\': " + value;
+            }
+        }
+        String serviceJs = String.format(";(function(service, options){ ;%s; })({ %s }, { %s });", serviceScript, param1, param2);
+
+        WXJSService service = new WXJSService();
+        service.setName(name);
+        service.setScript(serviceScript);
+        service.setOptions(options);
+        sInstanceJSServiceMap.put(name, service);
+
+        WXBridgeManager.getInstance().execJSService(serviceJs);
+        return true;
+    }
+
+    public static boolean unRegisterService(String name) {
+        if (TextUtils.isEmpty(name)) return false;
+
+        if(WXEnvironment.isApkDebugable()) {
+            sInstanceJSServiceMap.remove(name);
+        }
+
+        String js = String.format("global.unregisterService( \"%s\" );", name);
+        WXBridgeManager.getInstance().execJSService(js);
+        return true;
+    }
+
+
+    public static void execAllCacheJsService() {
+        for (String serviceName: sInstanceJSServiceMap.keySet()) {
+            WXJSService service = sInstanceJSServiceMap.get(serviceName);
+            registerService(service.getName(), service.getScript(), service.getOptions());
+        }
+    }
+
+    public static WXJSService getService(String serviceName) {
+        if (sInstanceJSServiceMap != null) {
+            return sInstanceJSServiceMap.get(serviceName);
+        }
+        return null;
+    }
+
+    public static void reload() {
+        if(sInstanceJSServiceMap != null && sInstanceJSServiceMap.size() > 0) {
+            WXBridgeManager.getInstance().post(new Runnable() {
+                @Override
+                public void run() {
+                    for (Map.Entry<String, WXJSService> entry : sInstanceJSServiceMap.entrySet()) {
+                        WXJSService service = entry.getValue();
+                        registerService(service.getName(), service.getScript(), service.getOptions());
+                    }
+                }
+            });
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXTask.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXTask.java
new file mode 100644
index 0000000..3f5e526
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXTask.java
@@ -0,0 +1,45 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import org.apache.weex.common.IWXObject;
+
+import java.util.ArrayList;
+
+/**
+ * Weex JS Native task
+ */
+public class WXTask implements IWXObject {
+
+  /**
+   * Native module
+   */
+  public String module;
+
+  /**
+   * The method of native module
+   */
+  public String method;
+
+  /**
+   * The method parameters
+   */
+  public ArrayList<String> args;
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/bridge/WXValidateProcessor.java b/android/sdk/src/main/java/org/apache/weex/bridge/WXValidateProcessor.java
new file mode 100644
index 0000000..f167835
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/bridge/WXValidateProcessor.java
@@ -0,0 +1,58 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.bridge;
+
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by fengjunjie
+ */
+public interface WXValidateProcessor {
+
+    WXModuleValidateResult onModuleValidate(WXSDKInstance wxsdkInstance, String moduleStr,
+                                            String methodStr, JSONArray params,
+                                            JSONObject options);
+
+    WXComponentValidateResult onComponentValidate(WXSDKInstance wxsdkInstance,
+                                                  String componentName,
+                                                  WXComponent parentComponent);
+
+    boolean needValidate(String bundleUrl);
+
+    class WXComponentValidateResult {
+
+        public boolean isSuccess;
+
+        public String replacedComponent;
+
+        public JSONObject validateInfo;
+
+    }
+
+    class WXModuleValidateResult {
+
+        public boolean isSuccess;
+
+        public JSONObject validateInfo;
+
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/Constants.java b/android/sdk/src/main/java/org/apache/weex/common/Constants.java
new file mode 100644
index 0000000..d3d3232
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/Constants.java
@@ -0,0 +1,388 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public class Constants {
+
+  public interface Orientation {
+
+    int HORIZONTAL = 0;
+    int VERTICAL = 1;
+  }
+
+  public interface Weex {
+    String REF = "ref";
+    String INSTANCEID = "instanceid";
+    String TYPE = "type";
+  }
+
+  public interface Name {
+
+    String DEFAULT_WIDTH = "defaultWidth";
+    String DEFAULT_HEIGHT = "defaultHeight";
+    String HREF = "href";
+    String WIDTH = "width";
+    String MIN_WIDTH = "minWidth";
+    String MAX_WIDTH = "maxWidth";
+    String HEIGHT = "height";
+    String MIN_HEIGHT = "minHeight";
+    String MAX_HEIGHT = "maxHeight";
+    String ALIGN_ITEMS = "alignItems";
+    String ALIGN_SELF = "alignSelf";
+    String FLEX = "flex";
+    String FLEX_DIRECTION = "flexDirection";
+    String JUSTIFY_CONTENT = "justifyContent";
+    String FLEX_WRAP = "flexWrap";
+
+    String MARGIN = "margin";
+    String MARGIN_TOP = "marginTop";
+    String MARGIN_LEFT = "marginLeft";
+    String MARGIN_RIGHT = "marginRight";
+    String MARGIN_BOTTOM = "marginBottom";
+    String PADDING = "padding";
+    String PADDING_TOP = "paddingTop";
+    String PADDING_LEFT = "paddingLeft";
+    String PADDING_RIGHT = "paddingRight";
+    String PADDING_BOTTOM = "paddingBottom";
+
+    String LEFT = "left";
+    String TOP = "top";
+    String RIGHT = "right";
+    String BOTTOM = "bottom";
+
+
+    String BACKGROUND_COLOR = "backgroundColor";
+    String BACKGROUND_IMAGE = "backgroundImage";
+    String OPACITY = "opacity";
+    String BORDER_RADIUS = "borderRadius";
+    String BORDER_WIDTH = "borderWidth";
+    String BORDER_COLOR = "borderColor";
+    String BORDER_STYLE = "borderStyle";
+    String BORDER_TOP_WIDTH = "borderTopWidth";
+    String BORDER_RIGHT_WIDTH = "borderRightWidth";
+    String BORDER_BOTTOM_WIDTH = "borderBottomWidth";
+    String BORDER_LEFT_WIDTH = "borderLeftWidth";
+    String BORDER_TOP_COLOR = "borderTopColor";
+    String BORDER_RIGHT_COLOR = "borderRightColor";
+    String BORDER_BOTTOM_COLOR = "borderBottomColor";
+    String BORDER_LEFT_COLOR = "borderLeftColor";
+    String BORDER_TOP_LEFT_RADIUS = "borderTopLeftRadius";
+    String BORDER_TOP_RIGHT_RADIUS = "borderTopRightRadius";
+    String BORDER_BOTTOM_RIGHT_RADIUS = "borderBottomRightRadius";
+    String BORDER_BOTTOM_LEFT_RADIUS = "borderBottomLeftRadius";
+    String BORDER_RIGHT_STYLE = "borderRightStyle";
+    String BORDER_BOTTOM_STYLE = "borderBottomStyle";
+    String BORDER_LEFT_STYLE = "borderLeftStyle";
+    String BORDER_TOP_STYLE = "borderTopStyle";
+    String BOX_SHADOW = "boxShadow";
+    String SHADOW_QUALITY = "shadowQuality";
+
+    String POSITION = "position";
+
+    String KEEP_SCROLL_POSITION = "keepScrollPosition";
+
+    String TEXT_DECORATION = "textDecoration";
+    String TEXT_ALIGN = "textAlign";
+    String FONT_WEIGHT = "fontWeight";
+    String FONT_STYLE = "fontStyle";
+    String FONT_SIZE = "fontSize";
+    String COLOR = "color";
+    String LINES = "lines";
+    String FONT_FAMILY = "fontFamily";
+    String TEXT_OVERFLOW = "textOverflow";
+    String ELLIPSIS = "ellipsis";
+    String LINE_HEIGHT = "lineHeight";
+    String DISABLED = "disabled";
+    String VALUE = "value";
+    String IMAGE_QUALITY = "imageQuality";
+    String FILTER = "filter";
+    String QUALITY = "quality";
+    String SRC = "src";
+    String SOURCE = "source";
+    String PLACE_HOLDER = "placeHolder";
+    String RESIZE_MODE = "resizeMode";
+    String AUTO_RECYCLE = "autoBitmapRecycle";
+    String SHOW_INDICATORS = "showIndicators";
+    String AUTO_PLAY = "autoPlay";
+    String AUTOPLAY = "autoplay";
+    String CONTROLS = "controls";
+    String ZORDERTOP = "zOrderTop";
+    String SCROLL_DIRECTION = "scrollDirection";
+    String SCOPE = "scope";
+    String RECYCLE = "recycle";
+    String LOADMORERETRY = "loadmoreretry";
+    String LOADMOREOFFSET = "loadmoreoffset";
+    String RECYCLE_IMAGE = "recycleImage";
+    String LAYOUT = "layout";
+    String SPAN_OFFSETS = "spanOffsets";
+    String COLUMN_WIDTH = "columnWidth";
+    String COLUMN_COUNT = "columnCount";
+    String COLUMN_GAP = "columnGap";
+    String SHOW_SCROLLBAR = "showScrollbar";
+    String LEFT_GAP= "leftGap";
+    String RIGHT_GAP= "rightGap";
+    String OVERFLOW = "overflow";
+    String TYPE = "type";
+    String PLACEHOLDER = "placeholder";
+    String PLACEHOLDER_COLOR = "placeholderColor";
+    String AUTOFOCUS = "autofocus";
+    String SINGLELINE = "singleline";
+    String MAX_LENGTH = "maxLength";
+    String MAXLENGTH = "maxlength";
+    String ROWS = "rows";
+    String CHECKED = "checked";
+    String ANIMATING = "animating";
+    String VISIBILITY = "visibility";
+    String ITEM_COLOR = "itemColor";
+    String ITEM_SELECTED_COLOR = "itemSelectedColor";
+    String ITEM_SIZE = "itemSize";
+    String DISPLAY = "display";
+    String SHOW_LOADING = "show-loading";
+    String SUFFIX = "suffix";
+    String RESIZE = "resize";
+    String IMAGE_SHARPEN = "imageSharpen";
+    String SHARPEN = "sharpen";
+    String PREFIX = "prefix";
+    String INDEX = "index";
+    String INTERVAL = "interval";
+    String PLAY_STATUS = "playStatus";
+    String FONT_FACE = "fontFace";
+    String MAX = "max";
+    String MIN = "min";
+    String NAV_BAR_VISIBILITY = "hidden";
+    String OFFSET_X_ACCURACY = "offsetXAccuracy";
+    String OFFSET_X_RATIO = "offsetXRatio";
+    String ELEVATION = "elevation";
+    String PERSPECTIVE = "perspective";
+    String SCROLLABLE = "scrollable";
+    String DRAGGABLE = "draggable";
+    String DISTANCE_Y = "dy";
+    String PULLING_DISTANCE = "pullingDistance";
+    String VIEW_HEIGHT = "viewHeight";
+    String PREVENT_MOVE_EVENT = "preventMoveEvent";
+    String SELECTION_START = "selectionStart";
+    String SELECTION_END = "selectionEnd";
+    String OFFSET_ACCURACY = "offsetAccuracy";
+    String CONTENT_SIZE = "contentSize";
+    String CONTENT_OFFSET = "contentOffset";
+    String ISDRAGGING = "isDragging";
+    String X = "x";
+    String Y = "y";
+    String RETURN_KEY_TYPE = "returnKeyType";
+    String OFFSET = "offset";
+    String ANIMATED = "animated";
+    String STABLE = "stable";
+    String TRANSFORM = "transform";
+    String TRANSFORM_ORIGIN = "transformOrigin";
+    String KEEP_INDEX = "keepIndex";
+    String KEEP_SELECTION_INDEX = "keepSelectionIndex";
+
+    String INSERT_CELL_ANIMATION = "insertAnimation";
+    String DELETE_CELL_ANIMATION = "deleteAnimation";
+    String AUTO = "auto";
+    String NORMAL = "normal";
+    String ARIA_LABEL = "ariaLabel";
+    String ARIA_HIDDEN = "ariaHidden";
+    String ROLE = "role";
+
+    String LAYERLIMIT = "layerLimit";
+    String LAYER_LIMIT = "layer-limit";
+
+    String DIRECTION = "direction";
+    String RTL = "rtl";
+
+    String STICKY_OFFSET = "stickyOffset";
+    String HAS_FIXED_SIZE = "hasFixedSize";
+    String KEEP_POSITION_LAYOUT_DELAY = "keepPositionLayoutDelay";
+
+    String OVERFLOW_HIDDEN_HEIGHT = "overflowHiddenHeight";
+    String OVERFLOW_HIDDEN_WIDTH = "overflowHiddenWidth";
+
+    String PRIORITY  = "priority";
+
+    String STRATEGY  = "strategy";
+
+    String ALLOW_COPY_PASTE = "allowCopyPaste";
+    String INCLUDE_FONT_PADDING = "includeFontPadding";
+    String ENABLE_COPY = "enableCopy";
+
+    String PAGE_ENABLED = "pagingEnabled";
+    String PAGE_SIZE = "pageSize";
+
+
+
+    interface  Recycler{
+      String LIST_DATA = "listData";
+      String LIST_DATA_ITEM  ="alias";
+      String LIST_DATA_ITEM_INDEX = "index";
+      String LIST_DATA_TEMPLATE_SWITCH_KEY = "switch";
+      String SLOT_TEMPLATE_CASE = "case";
+      String SLOT_TEMPLATE_DEFAULT = "default";
+      String CELL_INDEX = "cellIndex";
+      String TYPE_INDEX = "typeIndex";
+    }
+
+
+    String VIF_FALSE = "ifFalse";
+    String UNDEFINED = "undefined";
+    String FLAT = "flat";
+    String RIPPLE_ENABLED = "rippleEnabled";
+
+    String SHOULD_STOP_PROPAGATION_INIT_RESULT = "shouldStopPropagationInitResult";
+    String SHOULD_STOP_PROPAGATION_INTERVAL = "shouldStopPropagationInterval";
+
+
+    String NEST_SCROLLING_ENABLED = "nestedScrollingEnabled";
+
+    String ORIENTATION  = "orientation";
+  }
+
+  public interface Value {
+
+    int DENSITY = 3;
+    int NAV_BAR_SHOWN = 0;
+    int NAV_BAR_HIDDEN = 1;
+    int AUTO = -1;
+    int COLUMN_GAP_NORMAL = 32;
+    int COLUMN_COUNT_NORMAL = 1;
+    String MULTI_COLUMN = "multi-column";
+    String GRID = "grid";
+    String STICKY = "sticky";
+    String FIXED = "fixed";
+    String LEFT = "left";
+    String RIGHT = "right";
+    String CENTER = "center";
+    String BOLD = "bold";
+    String ITALIC = "italic";
+    String ORIGINAL = "original";
+    String LOW = "low";
+    String NORMAL = "normal";
+    String HIGH = "high";
+    String VISIBLE = "visible";
+    String HIDDEN = "hidden";
+    String TEXT = "text";
+    String PASSWORD = "password";
+    String TEL = "tel";
+    String EMAIL = "email";
+    String URL = "url";
+    String DATE = "date";
+    String TIME = "time";
+    String DATETIME = "datetime";
+    String PLAY = "play";
+    String PAUSE = "pause";
+    String STOP = "stop";
+    String DIRECTION_LEFT = "left";
+    String DIRECTION_RIGHT = "right";
+    String DIRECTION_UP = "up";
+    String DIRECTION_DOWN = "down";
+    String NUMBER = "number";
+
+    String NONE = "none";
+    String DEFAULT = "default";
+
+    String HORIZONTAL = "horizontal";
+  }
+
+  public interface Event {
+
+    String CLICK = "click";
+    String APPEAR = "appear";
+    String DISAPPEAR = "disappear";
+    String LOADMORE = "loadmore";
+    String FOCUS = "focus";
+    String BLUR = "blur";
+    String INPUT = "input";
+    String VIEWAPPEAR = "viewappear";
+    String VIEWDISAPPEAR = "viewdisappear";
+    String START = "start";
+    String PAUSE = "pause";
+    String FINISH = "finish";
+    String FAIL = "fail";
+    String ERROR = "error";
+    String RECEIVEDTITLE = "receivedtitle";
+    String PAGEFINISH = "pagefinish";
+    String PAGESTART = "pagestart";
+    String ONREFRESH = "refresh";
+    String ONLOADING = "loading";
+    String ONLOAD = "load";
+    String CHANGE = "change";
+    String ONPULLING_DOWN = "pullingdown";
+    String ONPULLING_UP = "pullingup";
+    String SCROLL = "scroll";
+    String SCROLL_START = "scrollstart";
+    String SCROLL_END = "scrollend";
+    String CLICKBACKITEM = "clickbackitem";
+    String RESUME_EVENT = "WXApplicationDidBecomeActiveEvent";
+    String PAUSE_EVENT = "WXApplicationWillResignActiveEvent";
+    String RETURN = "return";
+    String KEYBOARD = "keyboard";
+
+    String UNSTICKY = "unsticky";
+    String STICKY = "sticky";
+
+    String ON_TRANSITION_END = "transitionEnd";
+
+    String LAYEROVERFLOW = "layeroverflow";
+
+    interface SLOT_LIFECYCLE {
+      String CREATE = "create";
+      String ATTACH = "attach";
+      String DETACH = "detach";
+      String DESTORY = "destroy";
+    }
+
+    String STOP_PROPAGATION = "stopPropagation";
+    String STOP_PROPAGATION_RAX = "stoppropagation";
+    String ONMESSAGE = "message";
+    String NATIVE_BACK = "nativeback";
+  }
+
+  public interface PSEUDO {
+    String ACTIVE = ":active";
+    String ENABLED = ":enabled";
+    String DISABLED = ":disabled";
+    String FOCUS = ":focus";
+  }
+
+  public interface Scheme {
+
+    String FILE = "file";
+    String HTTPS = "https";
+    String HTTP = "http";
+    String LOCAL = "local";
+    String DATA = "data";
+  }
+
+  public interface CodeCache {
+    String URL = "bundleUrl";
+    String DIGEST = "bundleDigest";
+    String PATH = "codeCachePath";
+    String BANNER_DIGEST = "digest";
+    String SAVE_PATH = "v8";
+  }
+
+  public interface TimeFunction {
+    String LINEAR = "linear";
+    String EASE_IN_OUT = "ease-in-out";
+    String EASE_IN = "ease-in";
+    String EASE_OUT = "ease-out";
+    String EASE = "ease";
+    String CUBIC_BEZIER = "cubic-bezier";
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/Destroyable.java b/android/sdk/src/main/java/org/apache/weex/common/Destroyable.java
new file mode 100644
index 0000000..8beca57
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/Destroyable.java
@@ -0,0 +1,26 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+/**
+ * Created by sospartan on 5/20/16.
+ */
+public interface Destroyable {
+    public void destroy();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/ICheckBindingScroller.java b/android/sdk/src/main/java/org/apache/weex/common/ICheckBindingScroller.java
new file mode 100644
index 0000000..3a4ab5d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/ICheckBindingScroller.java
@@ -0,0 +1,27 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.common;
+
+/**
+ * Created by zhengshihan on 2017/6/5.
+ */
+
+public interface ICheckBindingScroller {
+  boolean isNeedScroller(String ref,Object option);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/IWXBridge.java b/android/sdk/src/main/java/org/apache/weex/common/IWXBridge.java
new file mode 100755
index 0000000..f829306
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/IWXBridge.java
@@ -0,0 +1,234 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import org.apache.weex.bridge.ResultCallback;
+import org.apache.weex.bridge.WXJSObject;
+import org.apache.weex.bridge.WXParams;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.layout.ContentBoxMeasurement;
+import java.util.HashMap;
+import java.util.HashSet;
+
+/**
+ * Bridge interface, native bridge and debug bridge both need to implement this interface
+ */
+public interface IWXBridge extends IWXObject {
+
+  int DESTROY_INSTANCE = -1;
+  int INSTANCE_RENDERING = 1;
+  int INSTANCE_RENDERING_ERROR = 0;
+
+  /**
+   * init Weex
+   *
+   * @param framework assets/main.js
+   * @return
+   */
+  int initFramework(String framework, WXParams params);
+
+
+  /**
+   * init Weex
+   *
+   * @param framework assets/main.js
+   * @return
+   */
+  int initFrameworkEnv(String framework, WXParams params, String cacheDir, boolean pieSupport);
+
+
+  /**
+   * Update InitFramework Params
+   * */
+  void updateInitFrameworkParams(String key, String value, String desc);
+
+
+  void setLogType(float type, boolean isPerf);
+
+  void refreshInstance(String instanceId, String namespace, String function, WXJSObject[] args);
+
+  /**
+   * execute javascript function
+   */
+  int execJS(String instanceId, String namespace, String function, WXJSObject[] args);
+
+  /**
+   * execute javascript function with asynchronous callback
+   */
+  void execJSWithCallback(String instanceId, String namespace, String function, WXJSObject[] args, ResultCallback callback);
+
+  int execJSService(String javascript);
+
+  /**
+   * take the heap snapshot and serialize the heap to a local file.
+   *
+   * @param filename
+   */
+  void takeHeapSnapshot(String filename);
+
+  /**
+   * createInstance
+   * @param instanceId
+   * @param namespace
+   * @param function
+   * @param args
+   * @return
+   */
+  int createInstanceContext(String instanceId, String namespace, String function, WXJSObject[] args);
+
+  /**
+   * destoryInstance
+   * @param instanceId
+   * @param namespace
+   * @param function
+   * @param args
+   * @return
+   */
+  int destoryInstance(String instanceId, String namespace, String function, WXJSObject[] args);
+
+  /**
+   * execJSOnInstance
+   * @param instanceId
+   * @param script
+   * @param type
+   * @return
+   */
+  String execJSOnInstance(String instanceId, String script, int type);
+
+  /**
+   * js call native
+   */
+  int callNative(String instanceId, byte[] tasks, String callback);
+
+
+  int callNative(String instanceId, String tasks, String callback);
+
+  void reportJSException(String instanceId, String func, String exception);
+
+  Object callNativeModule(String instanceId, String module, String method, byte[] arguments, byte[] options);
+
+  void callNativeComponent(String instanceId, String ref, String method, byte[] arguments, byte[] options);
+
+  int callUpdateFinish(String instanceId, byte[] tasks, String callback);
+
+  int callRefreshFinish(String instanceId, byte[] tasks, String callback);
+
+  void reportServerCrash(String instanceId, String crashFile);
+
+
+  int callCreateBody(String instanceId, String componentType, String ref,
+                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
+                            float[] margins, float[] paddings, float[] borders);
+
+  int callAddElement(String instanceId, String componentType, String ref, int index, String parentRef,
+                            HashMap<String, String> styles, HashMap<String, String> attributes, HashSet<String> events,
+                            float[] margins, float[] paddings, float[] borders, boolean willLayout);
+
+  int callRemoveElement(String instanceId, String ref);
+
+  int callMoveElement(String instanceId, String ref, String parentref, int index);
+
+  int callAddEvent(String instanceId, String ref, String event);
+
+  int callRemoveEvent(String instanceId, String ref, String event);
+
+  int callUpdateStyle(String instanceId, String ref,
+                             HashMap<String, Object> styles,
+                             HashMap<String, String> paddings,
+                             HashMap<String, String> margins,
+                             HashMap<String, String> borders);
+
+  int callUpdateAttrs(String instanceId, String ref,
+                      HashMap<String, String> attrs);
+
+  int callAddChildToRichtext(String instanceId, String nodeType, String ref, String parentRef, String richTextRef,
+                             HashMap<String, String> styles, HashMap<String, String> attrs);
+
+  int callRemoveChildFromRichtext(String instanceId, String ref, String parentRef, String richTextRef);
+
+  int callUpdateRichtextStyle(String instanceId, String ref, HashMap<String, String> styles, String parentRef, String richTextRef);
+
+  int callUpdateRichtextChildAttr(String instanceId, String ref, HashMap<String, String> attrs, String parentRef, String richTextRef);
+
+  int callLayout(String instanceId, String ref, int top, int bottom, int left, int right, int height, int width, boolean isRTL, int index);
+
+  int callCreateFinish(String instanceId);
+
+  int callRenderSuccess(String instanceId);
+
+  int callAppendTreeCreateFinish(String instanceId, String ref);
+
+  int callHasTransitionPros(String instanceId, String ref, HashMap<String, String> styles);
+
+  ContentBoxMeasurement getMeasurementFunc(String instanceId, long renderObjectPtr);
+
+  void bindMeasurementToRenderObject(long ptr);
+
+  void setRenderContainerWrapContent(boolean wrap, String instanceId);
+
+  long[] getFirstScreenRenderTime(String instanceId);
+
+  long[] getRenderFinishTime(String instanceId);
+
+  void setDefaultHeightAndWidthIntoRootDom(String instanceId, float defaultWidth, float defaultHeight, boolean isWidthWrapContent, boolean isHeightWrapContent);
+
+  void onInstanceClose(String instanceId);
+
+  void forceLayout(String instanceId);
+
+  boolean notifyLayout(String instanceId);
+
+  void setStyleWidth(String instanceId, String ref, float value);
+
+  void setStyleHeight(String instanceId, String ref, float value);
+
+  void setMargin(String instanceId, String ref, CSSShorthand.EDGE edge, float value);
+
+  void setPadding(String instanceId, String ref, CSSShorthand.EDGE edge, float value);
+
+  void setPosition(String instanceId, String ref, CSSShorthand.EDGE edge, float value);
+
+  void markDirty(String instanceId, String ref, boolean dirty);
+
+  void setDeviceDisplay(String instanceId, float width, float height, float scale);
+
+  void registerCoreEnv(String key, String value);
+
+  void reportNativeInitStatus(String statusCode, String errorMsg);
+
+  void setTimeoutNative(String callbackId, String time);
+
+  void setJSFrmVersion(String version);
+
+  void resetWXBridge(boolean remoteDebug);
+
+  void setInstanceRenderType(String instanceId, String renderType);
+
+  void removeInstanceRenderType(String instanceId);
+
+  void setPageArgument(String instanceId, String key, String value);
+
+  void setViewPortWidth(String instanceId,float viewPortWidth);
+
+  void reloadPageLayout(String instanceId);
+
+  void setDeviceDisplayOfPage(String instanceId, float width, float height);
+
+  void setPageDirty(String instanceId, boolean dirty);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/IWXDebugConfig.java b/android/sdk/src/main/java/org/apache/weex/common/IWXDebugConfig.java
new file mode 100644
index 0000000..6d76268
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/IWXDebugConfig.java
@@ -0,0 +1,29 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.common;
+
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.bridge.WXDebugJsBridge;
+
+public interface IWXDebugConfig {
+
+  WXBridgeManager getWXJSManager();
+
+  WXDebugJsBridge getWXDebugJsBridge();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/IWXObject.java b/android/sdk/src/main/java/org/apache/weex/common/IWXObject.java
new file mode 100644
index 0000000..4b3ae4a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/IWXObject.java
@@ -0,0 +1,23 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public interface IWXObject {
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/OnWXScrollListener.java b/android/sdk/src/main/java/org/apache/weex/common/OnWXScrollListener.java
new file mode 100644
index 0000000..450b8ae
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/OnWXScrollListener.java
@@ -0,0 +1,56 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import android.support.v7.widget.RecyclerView;
+import android.view.View;
+
+
+public interface OnWXScrollListener {
+
+  /**
+   * The  view is not currently scrolling.
+   */
+  int IDLE = RecyclerView.SCROLL_STATE_IDLE;
+  /**
+   * The view is currently being dragged by outside input such as user touch input.
+   */
+  int DRAGGING = RecyclerView.SCROLL_STATE_DRAGGING;
+  /**
+   * The view is currently animating to a final position while not under
+   * outside control.
+   */
+  int SETTLING = RecyclerView.SCROLL_STATE_SETTLING;
+
+  /**
+   * Callback method to be invoked when the view has been scrolled. This will be
+   * called after the scroll has completed.
+   * <p>
+   * This callback will also be called if visible item range changes after a layout
+   * calculation. In that case, dx and dy will be 0.
+   *
+   */
+  void onScrolled(View view, int x, int y);
+
+  /**
+   * Callback method to be invoked when view's scroll state changes.
+   *
+   */
+  void onScrollStateChanged(View view, int x, int y, int newState);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/RenderTypes.java b/android/sdk/src/main/java/org/apache/weex/common/RenderTypes.java
new file mode 100644
index 0000000..8e3a105
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/RenderTypes.java
@@ -0,0 +1,27 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.common;
+
+public class RenderTypes {
+
+    public static final String RENDER_TYPE_NATIVE = "platform";
+
+    public static final String RENDER_TYPE_HERON = "heron";
+    public static final String RENDER_TYPE_HERON_URL_PARAM = "wx_heron=true";
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/TypeModuleFactory.java b/android/sdk/src/main/java/org/apache/weex/common/TypeModuleFactory.java
new file mode 100644
index 0000000..f31ef93
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/TypeModuleFactory.java
@@ -0,0 +1,98 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.Invoker;
+import org.apache.weex.bridge.MethodInvoker;
+import org.apache.weex.bridge.ModuleFactory;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.lang.annotation.Annotation;
+import java.lang.reflect.Method;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Use class
+ * Created by sospartan on 6/17/16.
+ */
+public class TypeModuleFactory<T extends WXModule> implements ModuleFactory<T> {
+  public static final String TAG = "TypeModuleFactory";
+  Class<T> mClazz;
+  Map<String, Invoker> mMethodMap;
+
+  public TypeModuleFactory(Class<T> clz) {
+    mClazz = clz;
+  }
+
+  private void generateMethodMap() {
+    if(WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d(TAG, "extractMethodNames:" + mClazz.getSimpleName());
+    }
+    HashMap<String, Invoker> methodMap = new HashMap<>();
+    try {
+      for (Method method : mClazz.getMethods()) {
+        // iterates all the annotations available in the method
+        for (Annotation anno : method.getDeclaredAnnotations()) {
+          if (anno != null) {
+            if(anno instanceof JSMethod) {
+              JSMethod methodAnnotation = (JSMethod) anno;
+              String name = JSMethod.NOT_SET.equals(methodAnnotation.alias())? method.getName():methodAnnotation.alias();
+              methodMap.put(name, new MethodInvoker(method, methodAnnotation.uiThread()));
+              break;
+            }else if(anno instanceof WXModuleAnno) {
+              WXModuleAnno methodAnnotation = (WXModuleAnno)anno;
+              methodMap.put(method.getName(), new MethodInvoker(method,methodAnnotation.runOnUIThread()));
+              break;
+            }
+          }
+        }
+      }
+    } catch (Throwable e) {
+      WXLogUtils.e("[WXModuleManager] extractMethodNames:", e);
+    }
+    mMethodMap = methodMap;
+  }
+
+
+  @Override
+  public T buildInstance() throws IllegalAccessException, InstantiationException {
+    return mClazz.newInstance();
+  }
+
+  @Override
+  public String[] getMethods() {
+    if (mMethodMap == null) {
+      generateMethodMap();
+    }
+    Set<String> keys = mMethodMap.keySet();
+    return keys.toArray(new String[keys.size()]);
+  }
+
+  @Override
+  public Invoker getMethodInvoker(String name) {
+    if (mMethodMap == null) {
+      generateMethodMap();
+    }
+    return mMethodMap.get(name);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXCompatModule.java b/android/sdk/src/main/java/org/apache/weex/common/WXCompatModule.java
new file mode 100644
index 0000000..1cbf4b0
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXCompatModule.java
@@ -0,0 +1,84 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import android.app.Activity;
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.support.v4.content.LocalBroadcastManager;
+
+import org.apache.weex.WXEnvironment;
+
+/**
+ * Created by lixinke on 16/10/10.
+ */
+
+public abstract class WXCompatModule extends WXModule implements Destroyable {
+
+  private ModuleReceive mModuleReceive;
+
+  public WXCompatModule() {
+    mModuleReceive = new ModuleReceive(this);
+    LocalBroadcastManager.getInstance(WXEnvironment.getApplication())
+        .registerReceiver(mModuleReceive, new IntentFilter(WXModule.ACTION_ACTIVITY_RESULT));
+    LocalBroadcastManager.getInstance(WXEnvironment.getApplication())
+        .registerReceiver(mModuleReceive, new IntentFilter(WXModule.ACTION_REQUEST_PERMISSIONS_RESULT));
+  }
+
+  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
+  }
+
+  public void onActivityResult(int requestCode, int resultCode, Intent data) {
+  }
+
+  @Override
+  public void destroy() {
+    LocalBroadcastManager.getInstance(WXEnvironment.getApplication())
+        .unregisterReceiver(mModuleReceive);
+  }
+
+  static class ModuleReceive extends BroadcastReceiver {
+
+    private WXCompatModule mWXCompatModule;
+
+    ModuleReceive(WXCompatModule module) {
+      mWXCompatModule = module;
+    }
+
+    @Override
+    public void onReceive(Context context, Intent intent) {
+      String action = intent.getAction();
+      switch (action) {
+        case WXModule.ACTION_ACTIVITY_RESULT:
+          int requestCode = intent.getIntExtra(WXModule.REQUEST_CODE, -1);
+          int resultCode = intent.getIntExtra(WXModule.RESULT_CODE, Activity.RESULT_OK);
+          mWXCompatModule.onActivityResult(requestCode, resultCode, intent);
+          break;
+        case WXModule.ACTION_REQUEST_PERMISSIONS_RESULT:
+          requestCode = intent.getIntExtra(WXModule.REQUEST_CODE, -1);
+          String[] permissions = intent.getStringArrayExtra(WXModule.PERMISSIONS);
+          int[] grantResults = intent.getIntArrayExtra(WXModule.GRANT_RESULTS);
+          mWXCompatModule.onRequestPermissionsResult(requestCode, permissions, grantResults);
+          break;
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXConfig.java b/android/sdk/src/main/java/org/apache/weex/common/WXConfig.java
new file mode 100644
index 0000000..88fd5f1
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXConfig.java
@@ -0,0 +1,44 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public interface WXConfig {
+
+  String os = "os";
+  String osName = "osName";
+  String appVersion="appVersion";
+  String cacheDir = "cacheDir";
+  String devId="devId";
+  String sysVersion="sysVersion";
+  String sysModel="sysModel";
+  String weexVersion="weexVersion";
+  String appName="appName";
+  String appGroup="appGroup";
+  String externalUserAgent="externalUserAgent";
+  String logLevel="logLevel";
+  String scale = "scale";
+  String layoutDirection = "layoutDirection";
+  String debugMode = "debugMode";
+  String androidStatusBarHeight = "androidStatusBarHeight";
+  String deviceHeight = "deviceHeight";
+  String deviceWidth = "deviceWidth";
+
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXErrorCode.java b/android/sdk/src/main/java/org/apache/weex/common/WXErrorCode.java
new file mode 100644
index 0000000..8b886a2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXErrorCode.java
@@ -0,0 +1,344 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.common;
+
+
+public enum WXErrorCode {
+
+
+  /*
+   * environment
+   **/
+  /**
+   * Failure for load so library
+   */
+  WX_ERR_LOAD_SO("-2001", "load so error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * Failure for load JSLib
+   */
+  WX_ERR_LOAD_JSLIB("-2002", "unzip JSLib error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * So library corrupted
+   */
+  WX_ERR_BAD_SO("-2003", "so size error, to reload apk so",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * Failure for extract and copy so from apk
+   */
+  WX_ERR_COPY_FROM_APK("-2007", "system load so error，copy from APK also error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * jsBridge
+   **/
+  /**
+   * Error for JavaScript function parameter
+   */
+  WX_ERR_JSFUNC_PARAM("-2009", "JS params error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * Error for parsing JSON object
+   */
+  WX_ERR_JSON_OBJECT("-2008", "transform JSON->OBJ  error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * Failure for invoking JavaScript function
+   */
+  WX_ERR_INVOKE_NATIVE("-2012", "Native-> Call ->JS  error!",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * Failure for executing JavaScript function.
+   */
+  WX_ERR_JS_EXECUTE("-2013", "JavaScript execute error!",ErrorType.JS_ERROR,ErrorGroup.JS),
+
+
+  /*
+   * domModule
+   **/
+  WX_SUCCESS("0", "successful",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for createBody
+   */
+  WX_ERR_DOM_CREATEBODY("-2100", "createBody error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for updateAttrs
+   */
+  WX_ERR_DOM_UPDATEATTRS("-2101", "updateAttrs error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for updateAttr
+   */
+  WX_ERR_DOM_UPDATESTYLE("-2102", "updateStyle error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for addElement
+   */
+  WX_ERR_DOM_ADDELEMENT("-2103", "addElement error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for removeElement
+   */
+  WX_ERR_DOM_REMOVEELEMENT("-2104", "removeElement error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for moveElement
+   */
+  WX_ERR_DOM_MOVEELEMENT("-2105", "moveElement error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for addEvent
+   */
+  WX_ERR_DOM_ADDEVENT("-2106", "addEvent error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for removeEvent
+   */
+  WX_ERR_DOM_REMOVEEVENT("-2107", "removeEvent error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for invoking createFinish
+   */
+  WX_ERROR_DOM_CREATEFINISH("-2108", "createFinish error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for invoking refreshFinish
+   */
+  WX_ERROR_DOM_REFRESHFINISH("-2109", "refreshFinish error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Failure for scrollToElement
+   */
+  WX_ERR_DOM_SCROLLTO("-2110", "scrollToElement",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   *
+   */
+  WX_ERR_RELOAD_PAGE("-2111", "reloadPage",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERR_RELOAD_PAGE_EXCEED_LIMIT("-2114", "RELOAD_PAGE_EXCEED_LIMIT",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERROR_WHITE_SCREEN("-2116", "WHITE_SCREEN",ErrorType.RENDER_ERROR,ErrorGroup.JS),
+  WHITE_SCREEN_RESPONSE_TIMEOUT("-2117", "WHITE_SCREEN_RESPONSE_TIMEOUT",ErrorType.RENDER_ERROR,ErrorGroup.JS),
+  WHITE_SCREEN_REBOOT_EXCEED_LIMIT("-2118", "WHITE_SCREEN_REBOOT_EXCEED_LIMIT",ErrorType.RENDER_ERROR,ErrorGroup.JS),
+
+  /**
+   *
+   */
+  WX_ERR_JSC_CRASH("-2112", "weexjscCrash",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   *dom actions invalid for native
+   */
+  WX_ERR_FIRST_DOM_ACTION_EXCEPTION("-2113", "dom action is invalid ",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * JS Bundle download error
+   */
+
+  WX_ERR_JSDOWNLOAD_START("-2201", "js bundle download start",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERR_JSBUNDLE_DOWNLOAD("-2299", "js bundle download err",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERR_JSBUNDLE_EMPTY("-2203", "js bundle empty",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERR_JSDOWNLOAD_END("-2299", "js bundle download end",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  // for js framework
+  WX_JS_FRAMEWORK_INIT_SUCCESS("-1000", "js framework success",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_JS_FRAMEWORK_REINIT_SUCCESS("-1001", "js framework reinit success",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * JS Framework run error
+   */
+  WX_ERR_JS_FRAMEWORK("-1002", "js framework error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERR_JS_REINIT_FRAMEWORK("-1003", "js reinit framework error",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * Single progress init error
+   */
+  WX_ERR_SINGLE_PROCESS_DLOPEN_FILE_NOT_EXIST("-1004", "so file does not exist",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERR_SINGLE_PROCESS_DLOPEN_FLAIED("-1005", "dlopen so file failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERR_SINGLE_PROCESS_DLSYM_FAILED("-1006", "find function from so file failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERR_SINGLE_PROCESS_JS_FRAMEWORK("-1007", "js framework  init singleProcess failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_JS_FRAMEWORK_INIT_MULPROCESS_FAILED("-1008", "js framework init multiProcess failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_JS_FRAMEWORK_REINIT_MULPROCESS_FAILED("-1009", "js framework reinit multiProcess failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_JS_FRAMEWORK_INIT_FAILED("-1010", "js framework init failed",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_JS_FRAMEWORK_INIT_SINGLE_PROCESS_SUCCESS("-1011", "js framework init success in single process",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_JS_FRAMEWORK_INIT_FAILED_PARAMS_NULL("-1012", "js framework init failed due to params null",ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+  WX_JS_FRAMEWORK_INIT_FAILED_FIND_ICU_TIMEOUT("-1013", "find icu failed",ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+
+  /**
+   * WX Key Exception Commit RT SDK Init
+   */
+  WX_KEY_EXCEPTION_SDK_INIT("-9000", "[WX_KEY_EXCEPTION_SDK_INIT]",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT("-9001", "[WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT] for android cpu is x86",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_SDK_INIT_TABLE_NOT_SUPPORT("-9002", "[WX_KEY_EXCEPTION_SDK_INIT_TABLE_NOT_SUPPORT] for device isTabletDevice",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_SDK_INIT_JSFM_INIT_FAILED("-9003", "[WX_KEY_EXCEPTION_SDK_INIT_JSFM_INIT_FAILED] for jsfm init failed|detail error is:",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * WX Key Exception Commit RT Register
+   */
+  WX_KEY_EXCEPTION_INVOKE_BRIDGE("-9100", "[WX_KEY_EXCEPTION_INVOKE_BRIDGE]",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_INVOKE_REGISTER_CONTENT_FAILED("-9101", "[WX_KEY_EXCEPTION_INVOKE_REGISTER_CONTENT_FAILED] details",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_INVOKE_JSSERVICE_EXECUTE("-9102", "[WX_KEY_EXCEPTION_INVOKE_JSSERVICE_EXECUTE] details",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_INVOKE_REGISTER_MODULES("-9103", "[WX_KEY_EXCEPTION_INVOKE_REGISTER_MODULES] details",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT("-9104", "[WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT] details",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+  /**
+   * WX Key Exception Commit Bundle Js Download
+   */
+  WX_KEY_EXCEPTION_JS_DOWNLOAD("-9200", "[WX_KEY_EXCEPTION_JS_DOWNLOAD]|",ErrorType.DOWN_LOAD_ERROR,ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_JS_DOWNLOAD_FAILED("-9201", "[WX_KEY_EXCEPTION_JS_DOWNLOAD_FAILED] | details",ErrorType.DOWN_LOAD_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * WX Key Exception Commit RT JsBridge eg. js excute runtime error
+   */
+  WX_KEY_EXCEPTION_WXBRIDGE("-9400", "[js excute runtime error] detail js stack -> ",ErrorType.JS_ERROR,ErrorGroup.JS),
+  WX_KEY_EXCEPTION_WXBRIDGE_EXCEPTION("-9401", "[js excute runtime error] detail js stack -> ",ErrorType.JS_ERROR,ErrorGroup.JS),
+
+  /**
+   * renderErrorCode
+   */
+  WX_RENDER_ERR_JS_CREATE_INSTANCE("-9600", "white screen cause create instance failed,check js stack ->",ErrorType.RENDER_ERROR,ErrorGroup.JS),
+  WX_RENDER_ERR_JS_CREATE_INSTANCE_CONTEXT("-9700", "white screen cause create instanceContext failed,check js stack ->",ErrorType.RENDER_ERROR,ErrorGroup.JS),
+  WX_RENDER_ERR_LAYER_OVERFLOW("-9602", "WX_RENDER_ERR_LAYER_OVERFLOW", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+  WX_RENDER_ERR_NULL_KEY("-9603", "WX_RENDER_ERR_NULL_KEY", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+  WX_RENDER_ERR_NATIVE_RUNTIME("-9604", "WX_RENDER_ERR for js error", ErrorType.RENDER_ERROR, ErrorGroup.NATIVE),
+  WX_RENDER_ERR_COMPONENT_NOT_REGISTER("-9605", "WX_RENDER_ERR_COMPONENT_NOT_REGISTER", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+  WX_RENDER_ERR_COMPONENT_ATTR_KEY("-9606", "The key passed to Component.updateAttr() is not string", ErrorType.NATIVE_ERROR, ErrorGroup.JS),
+  WX_RENDER_ERR_BRIDGE_ARG_NULL("-9610", "WX_RENDER_ERR_BRIDGE_ARG_NULL", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+  WX_RENDER_ERR_CONTAINER_TYPE("-9611", "WX_RENDER_ERR_CONTAINER_TYPE", ErrorType.JS_ERROR,ErrorGroup.JS),
+  WX_RENDER_ERR_TRANSITION("-9616", "WX_RENDER_ERR_TRANSITION", ErrorType.JS_ERROR, ErrorGroup.JS),
+  WX_RENDER_ERR_INSTANCE_ID_NULL("-9618", "WX_RENDER_ERR_INSTANCE_ID_NULL", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+  WX_RENDER_ERR_LIST_INVALID_COLUMN_COUNT("-9619", "WX_RENDER_ERR_LIST_INVALID_COLUMNJ_CONUNT", ErrorType.JS_ERROR, ErrorGroup.JS),
+  WX_RENDER_ERR_TEXTURE_SETBACKGROUND("-9620", "WX_RENDER_ERR_TEXTURE_SETBACKGROUND", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+  WX_RENDER_WAR_GPU_LIMIT_LAYOUT("-9621", "WX_RENDER_WAR_GPU_LIMIT_LAYOUT", ErrorType.JS_ERROR,ErrorGroup.JS),
+
+  WX_KEY_EXCEPTION_HERON("Heron_-9900", "Error of Heron engine: ", ErrorType.NATIVE_ERROR, ErrorGroup.NATIVE),
+  WX_KEY_EXCEPTION_HERON_RENDER("Heron_-9901", "Render error of Heron engine: ", ErrorType.RENDER_ERROR, ErrorGroup.NATIVE),
+
+  WX_KEY_EXCEPTION_NO_BUNDLE_TYPE("-9801", "Fatal Error : No bundle type in js bundle head, cause white screen or memory leak!!", ErrorType.JS_ERROR, ErrorGroup.JS),
+  /**
+   * degrade code.
+   */
+  WX_DEGRAD_ERR("-1000", "degradeToH5|Weex DegradPassivity ->",ErrorType.DEGRAD_ERROR,ErrorGroup.JS),
+
+  /**
+   * degrade for instance create failed, once this case occured,detail js stack and other specific
+   * cause need track into errmsg.
+   */
+  WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED("-1001", "degradeToH5|createInstance fail|wx_create_instance_error",ErrorType.DEGRAD_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * degrade for network failed download js bundle.once this case occured,network requist response header
+   * and statuscode need track into errmsg.
+   */
+  WX_DEGRAD_ERR_NETWORK_BUNDLE_DOWNLOAD_FAILED("-1002", "|wx_network_error|js bundle download failed",ErrorType.DOWN_LOAD_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * degrade for network failed for bundlejs is unbroken , once this case occured,network requist response header
+   * and statuscode need track into errmsg.
+   */
+  WX_DEGRAD_ERR_NETWORK_CHECK_CONTENT_LENGTH_FAILED("-1003", "degradeToH5|wx_network_error|js bundle content-length check failed",ErrorType.DEGRAD_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * degrade for Response header Content-Type is null or not "application/javascript".
+   * once this case occured,network requist response header and statuscode need track into errmsg.
+   */
+  WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR("-1004", "degradeToH5|wx_user_intercept_error |Content-Type is not application/javascript, " +
+          "Weex render template must be javascript, please check your request!",ErrorType.DEGRAD_ERROR,ErrorGroup.NATIVE),
+
+  /**
+   * degrade for other reason. such as white screen which block error for some unknown reason.
+   * once this case occured,detail msg need track.
+   */
+  WX_DEGRAD_ERR_OTHER_CAUSE_DEGRADTOH5("-1005", "degradeToH5|for other reason|",ErrorType.DEGRAD_ERROR,ErrorGroup.NATIVE),
+
+
+  WX_DEGRAD_ERR_INSTANCE_CREATE_FAILED_JS("-1006", "degradeToH5|createInstance fail|wx_create_instance_error",ErrorType.DEGRAD_ERROR,ErrorGroup.JS),
+
+  WX_DEGRAD_EAGLE_RENDER_ERROR ("Eagle_-1007", "degradeToH5|eagleRenderErr", ErrorType.DEGRAD_ERROR, ErrorGroup.NATIVE),
+
+  WX_ERR_HASH_MAP_TMP("-10010", "WX_ERR_HASH_MAP_TMP",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE),
+
+  WX_ERROR_MOVE_RENDER_OBJECT_OUT_OF_BOUNDS("-2120", "Index out of bounds when move element",
+      ErrorType.NATIVE_ERROR, ErrorGroup.JS),
+
+  /**
+   * TEST
+   */
+
+  WX_ERR_TEST("test", "test",ErrorType.NATIVE_ERROR,ErrorGroup.NATIVE);
+
+  private String errorCode;
+  private String errorMsg;
+  private String appendMsg="";
+  private String args;
+  private ErrorType mErrorType;
+  private ErrorGroup mErrorGroup;
+
+  WXErrorCode(String errorCode, String errorMsg,ErrorType errorType,ErrorGroup errorGroup) {
+    this.errorCode = errorCode;
+    this.errorMsg = errorMsg;
+    this.mErrorType = errorType;
+    this.mErrorGroup = errorGroup;
+  }
+
+  public void appendErrMsg(String err) {
+    appendMsg=err;
+  }
+
+  public String getErrorCode() {
+    return this.errorCode;
+  }
+
+  public String getErrorMsg() {
+    StringBuilder builder=new StringBuilder(errorMsg);
+    builder.append(appendMsg);
+    return builder.toString();
+  }
+
+  public ErrorType getErrorType() {
+    return mErrorType;
+  }
+
+  public ErrorGroup getErrorGroup() {
+    return mErrorGroup;
+  }
+
+  public String getArgs() {
+    return args;
+  }
+
+  public void setArgs(String args) {
+    this.args = args;
+  }
+
+  public enum ErrorType{
+    JS_ERROR,
+    NATIVE_ERROR,
+    RENDER_ERROR,
+    DEGRAD_ERROR,
+    DOWN_LOAD_ERROR
+  }
+
+  public enum ErrorGroup{
+    JS,
+    NATIVE
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXException.java b/android/sdk/src/main/java/org/apache/weex/common/WXException.java
new file mode 100644
index 0000000..4afb5e7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXException.java
@@ -0,0 +1,28 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public class WXException extends Exception {
+
+  private static final long serialVersionUID = 7265837506862157379L;
+
+  public WXException(String msg) {
+    super(msg);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXImageSharpen.java b/android/sdk/src/main/java/org/apache/weex/common/WXImageSharpen.java
new file mode 100644
index 0000000..6904ce6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXImageSharpen.java
@@ -0,0 +1,24 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public enum WXImageSharpen {
+  UNSHARPEN,
+  SHARPEN
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXImageStrategy.java b/android/sdk/src/main/java/org/apache/weex/common/WXImageStrategy.java
new file mode 100644
index 0000000..e32e370
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXImageStrategy.java
@@ -0,0 +1,83 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import android.widget.ImageView;
+
+import org.apache.weex.WXSDKInstance;
+
+import java.util.Map;
+
+public class WXImageStrategy {
+
+
+  /**
+   * <strong>Never!</strong>
+   * <strong>Never!</strong>
+   * <strong>Never!</strong>
+   * Never use this flag, ImageView has done all the job of clipping!
+   * There is no method to read this flag any more.
+   * This field will be removed when it's appropriate.
+   */
+  @Deprecated
+  public boolean isClipping;
+
+  /**
+   * Whether to sharp the image. The default is false.
+   */
+  public boolean isSharpen;
+
+  /**
+   * The blur radius of the image. 0 means no blur.
+   * */
+  public int blurRadius;
+
+  public String placeHolder;
+
+  /**
+   * running weex instanceId
+   * @see WXSDKInstance#mInstanceId
+   */
+  public String instanceId;
+
+  public WXImageStrategy()
+  {
+
+  }
+
+  public WXImageStrategy(String instanceId)
+  {
+    this.instanceId = instanceId;
+  }
+
+
+  public ImageListener getImageListener() {
+    return imageListener;
+  }
+
+  public void setImageListener(ImageListener imageListener) {
+    this.imageListener = imageListener;
+  }
+
+  ImageListener imageListener;
+
+  public interface ImageListener{
+    public void onImageFinish(String url,ImageView imageView,boolean  result,Map extra);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXInstanceWrap.java b/android/sdk/src/main/java/org/apache/weex/common/WXInstanceWrap.java
new file mode 100644
index 0000000..e51fe02
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXInstanceWrap.java
@@ -0,0 +1,41 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.JSMethod;
+
+/**
+ * Report template error.
+ */
+public class WXInstanceWrap extends WXModule {
+
+  @JSMethod
+  public void error(String type, String code, String info) {
+    if (mWXSDKInstance != null) {
+      WXSDKInstance root = mWXSDKInstance;
+      if(info != null && info.contains("downgrade_to_root")){
+        while (root.getParentInstance() != null){
+          root = root.getParentInstance();
+        }
+      }
+      root.onRenderError(type + "|" + code, info);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXJSBridgeMsgType.java b/android/sdk/src/main/java/org/apache/weex/common/WXJSBridgeMsgType.java
new file mode 100644
index 0000000..f2e3307
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXJSBridgeMsgType.java
@@ -0,0 +1,38 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public class WXJSBridgeMsgType {
+
+  public static final int SET_TIMEOUT = 0x01;
+  public static final int NATIVE_CALL = 0x02;
+  public static final int FIRE_EVENT = 0x03;
+  public static final int CALLBACK = 0x04;
+  public static final int CALL_JS = 0x05;
+  public static final int CALL_JS_BATCH = 0x06;
+  public static final int INIT_FRAMEWORK = 0x07;
+  public static final int REGISTER_COMPONENTS = 0x08;
+  public static final int REGISTER_MODULES = 0x09;
+  public static final int REFRESH_INSTANCE = 0x0a;
+  public static final int MODULE_TIMEOUT = 0x0b;
+  public static final int MODULE_INTERVAL = 0x0c;
+  public static final int TAKE_HEAP_SNAPSHOT = 0x0d;
+
+  public static final int RELOAD_PAGE_NATIVE = 0x0e;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXJSEngineListener.java b/android/sdk/src/main/java/org/apache/weex/common/WXJSEngineListener.java
new file mode 100644
index 0000000..8d1b358
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXJSEngineListener.java
@@ -0,0 +1,36 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public interface WXJSEngineListener {
+
+  void createInstanceSuccess(String instanceId);
+
+  void destroyInstanceSuccess(String instanceId);
+
+  void createInstanceFailed(String instanceId);
+
+  void destroyInstanceFailed(String instanceId);
+
+  void fireEvent(boolean success, String instanceId, String ref, String type);
+
+  void callback(boolean success, String instanceId, String funcId, String data);
+
+  void initFramework(boolean success, String version, double jslibSize);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXJSExceptionInfo.java b/android/sdk/src/main/java/org/apache/weex/common/WXJSExceptionInfo.java
new file mode 100644
index 0000000..9b627c3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXJSExceptionInfo.java
@@ -0,0 +1,142 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.common;
+
+
+import org.apache.weex.WXEnvironment;
+
+import java.util.Map;
+
+public class WXJSExceptionInfo {
+
+  /**
+   * instance id
+   */
+  private String mInstanceId;
+  /**
+   * The URL where the exception occurred
+   */
+  private String mBundleUrl;
+  /**
+   * error code
+   */
+  private WXErrorCode mErrCode;
+  /**
+   * The function name of the exception
+   */
+  private String mFunction;
+  /**
+   * Exception details
+   */
+  private String mException;
+
+  /**
+   * Extended field
+   */
+  private Map<String,String> mExtParams;
+
+  /**
+   * weex sdk version
+   */
+  private String mWeexVersion = WXEnvironment.WXSDK_VERSION;
+
+  public long time;
+
+  /**
+   * js framework verison
+   */
+  private String mJsFrameworkVersion = WXEnvironment.JS_LIB_SDK_VERSION;
+
+  public WXJSExceptionInfo(String instanceId, String bundleUrl, WXErrorCode errCode, String function, String exception, Map<String,String> extParams) {
+    this.mInstanceId = instanceId;
+    this.mBundleUrl = bundleUrl;
+    this.mErrCode = errCode;
+    this.mFunction = function;
+    this.mException = exception;
+    this.mExtParams = extParams;
+    this.time = System.currentTimeMillis();
+  }
+
+  public String getInstanceId() {
+    return mInstanceId;
+  }
+
+  public void setInstanceId(String instanceId) {
+    mInstanceId = instanceId;
+  }
+
+  public String getBundleUrl() {
+    return mBundleUrl;
+  }
+
+  public void setBundleUrl(String bundleUrl) {
+    mBundleUrl = bundleUrl;
+  }
+
+  public WXErrorCode getErrCode() {
+    return mErrCode;
+  }
+
+  public void setErrCode(WXErrorCode errCode) {
+    mErrCode = errCode;
+  }
+
+  public String getFunction() {
+    return mFunction;
+  }
+
+  public void setFunction(String function) {
+    mFunction = function;
+  }
+
+  public String getException() {
+    return mException;
+  }
+
+  public void setException(String exception) {
+    mException = exception;
+  }
+
+  public Map<String, String> getExtParams() {
+    return mExtParams;
+  }
+
+  public void setExtParams(Map<String, String> extParams) {
+    mExtParams = extParams;
+  }
+
+  public String getWeexVersion() {
+    return mWeexVersion;
+  }
+
+
+  public String getJsFrameworkVersion() {
+    return mJsFrameworkVersion;
+  }
+
+
+  @Override
+  public String toString() {
+    return new StringBuilder()
+        .append(" errCode:").append(null == mErrCode?"unSetErrorCode":mErrCode.getErrorCode())
+        .append(",function:").append(null == mFunction?"unSetFuncName":mFunction)
+        .append(",exception:").append(null == mException?"unSetException":mException)
+        .toString();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXJSService.java b/android/sdk/src/main/java/org/apache/weex/common/WXJSService.java
new file mode 100644
index 0000000..bd2d347
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXJSService.java
@@ -0,0 +1,43 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import java.util.HashMap;
+import java.util.Map;
+
+public class WXJSService implements IWXObject {
+    private String name;
+    private String script;
+    private Map<String, Object> options = new HashMap<>();
+
+    public String getName() { return name; }
+    public void setName(String name) {
+        this.name = name;
+    }
+
+    public String getScript() { return script; }
+    public void setScript(String script) {
+        this.script = script;
+    }
+
+    public Map<String, Object> getOptions() { return options; }
+    public void setOptions(Map<String, Object> options) {
+        this.options = options;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXModule.java b/android/sdk/src/main/java/org/apache/weex/common/WXModule.java
new file mode 100644
index 0000000..4086a02
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXModule.java
@@ -0,0 +1,137 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import android.content.Intent;
+import android.text.TextUtils;
+import android.view.Menu;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * All modules must extend this class
+ */
+public abstract class WXModule implements IWXObject {
+
+  public static final String ACTION_ACTIVITY_RESULT = "actionActivityResult";
+  public static final String ACTION_REQUEST_PERMISSIONS_RESULT = "actionRequestPermissionsResult";
+  public static final String REQUEST_CODE = "requestCode";
+  public static final String RESULT_CODE = "resultCode";
+  public static final String PERMISSIONS = "permissions";
+  public static final String GRANT_RESULTS = "grantResults";
+
+
+  public WXSDKInstance mWXSDKInstance;
+  private String mModuleName;
+
+
+  protected final WXComponent findComponent(String ref){
+    if(mWXSDKInstance != null && ref != null){
+      return WXSDKManager.getInstance()
+          .getWXRenderManager()
+          .getWXComponent(mWXSDKInstance.getInstanceId(), ref);
+    }
+    return null;
+  }
+
+  /** hook the Activity life cycle to Instance module**/
+  public void onActivityResult(int requestCode, int resultCode, Intent data){}
+
+  public void onActivityCreate(){}
+
+  public void onActivityStart(){}
+
+  public void onActivityPause(){}
+
+  public void onActivityResume(){}
+
+  public void onActivityStop(){}
+
+  public void onActivityDestroy(){}
+
+  public boolean onActivityBack() {return false;}
+
+  public boolean onCreateOptionsMenu(Menu menu){return false;}
+
+  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {}
+
+    /** end **/
+
+  private Map<String, List<String>> mEvents = new HashMap<>();
+  private Map<String, Boolean> mKeepAlives = new HashMap<>();
+
+
+
+  @JSMethod
+  public void addEventListener(String eventName, String callback, Map<String, Object> options) {
+    if (TextUtils.isEmpty(eventName) || TextUtils.isEmpty(callback)) {
+      return;
+    }
+    boolean isOnce = false;
+    if (options != null && options.size() > 0 && options.containsKey("once")) {
+      Object temp = options.get("once");
+      if (WXUtils.getBoolean(temp,false)) {
+        isOnce = true;
+      }
+    }
+    mKeepAlives.put(callback, isOnce);
+    if(mEvents.get(eventName)==null){
+      mEvents.put(eventName,new ArrayList<String>());
+    }
+    mEvents.get(eventName).add(callback);
+  }
+
+  @JSMethod
+  public void removeAllEventListeners(String eventName) {
+    if (mEvents.containsKey(eventName)) {
+      List<String> callbacks = mEvents.remove(eventName);
+      for(String callback:callbacks){
+        mKeepAlives.remove(callback);
+      }
+    }
+  }
+
+  /**
+   * Check whether the EventName has been registered
+   */
+  public List<String> getEventCallbacks(String eventName) {
+    return mEvents.get(eventName);
+  }
+
+  public boolean isOnce(String callback){
+    return mKeepAlives.get(callback);
+  }
+
+  public String getModuleName() {
+    return mModuleName;
+  }
+
+  public void setModuleName(String moduleName) {
+    mModuleName = moduleName;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXModuleAnno.java b/android/sdk/src/main/java/org/apache/weex/common/WXModuleAnno.java
new file mode 100644
index 0000000..038771c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXModuleAnno.java
@@ -0,0 +1,37 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import org.apache.weex.annotation.JSMethod;
+
+import java.lang.annotation.Inherited;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+
+/** Use {@link JSMethod} instead. **/
+@Retention(RetentionPolicy.RUNTIME)
+@Inherited
+@Deprecated
+public @interface WXModuleAnno {
+
+  @Deprecated
+  boolean moduleMethod() default true;
+
+  boolean runOnUIThread() default true;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXPerformance.java b/android/sdk/src/main/java/org/apache/weex/common/WXPerformance.java
new file mode 100644
index 0000000..7024086
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXPerformance.java
@@ -0,0 +1,569 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.common;
+
+import android.support.annotation.RestrictTo;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import org.apache.weex.bridge.WXBridgeManager;
+
+@Deprecated
+public class WXPerformance {
+
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  public enum Dimension {
+    JSLibVersion,
+    WXSDKVersion,
+    pageName,
+    spm,
+    scheme,
+    cacheType,
+    requestType,
+    networkType,
+    connectionType,
+    zcacheInfo,
+    wxContainerName,
+    wxInstanceType,
+    wxParentPage,
+    wxdim1,
+    wxdim2,
+    wxdim3,
+    wxdim4,
+    wxdim5,
+    bizType,
+    templateUrl,
+    useScroller
+  }
+
+  public enum Measure {
+    /**
+     * range : [min,max)
+     */
+    JSLibSize(0D, Double.MAX_VALUE),
+    //normal 300ms.. first install apk 30s ?
+    JSLibInitTime(0D, 80000D),
+    SDKInitTime(0D, 120000D),
+    SDKInitInvokeTime(0D, 5000D),
+    SDKInitExecuteTime(0D, 5000D),
+    JSTemplateSize(0D, 5000D),
+    pureNetworkTime(0D, 15000D),
+    networkTime(0D, 15000D),
+    fsCreateInstanceTime(0D, 3000D),
+    fsCallJsTotalTime(0D, 5000D),
+    fsCallJsTotalNum(0D, Double.MAX_VALUE),
+    fsCallNativeTotalTime(0D, 5000D),
+    fsCallNativeTotalNum(0D, Double.MAX_VALUE),
+    fsCallEventTotalNum(0D, Double.MAX_VALUE),
+    fsComponentCount(0D,100000D),
+    fsComponentCreateTime(0D,Double.MAX_VALUE),
+    fsRenderTime(0D, 5000D),
+    fsRequestNum(0D, 100D),
+    callCreateFinishTime(0D, 10000D),
+    cellExceedNum(0D, Double.MAX_VALUE),
+    communicateTotalTime(0D, 5000D),
+    maxDeepViewLayer(0D, Double.MAX_VALUE),
+    maxDeepVDomLayer(0D, Double.MAX_VALUE),
+    componentCount(0D, 1000000),
+    componentCreateTime(0D,Double.MAX_VALUE),
+    avgFps(0D, 61D),
+    timerCount(0D, Double.MAX_VALUE),
+
+    MaxImproveMemory(0D, Double.MAX_VALUE),
+    BackImproveMemory(0D, Double.MAX_VALUE),
+    PushImproveMemory(0D, Double.MAX_VALUE),
+    measureTime1(0D, Double.MAX_VALUE),
+    measureTime2(0D, Double.MAX_VALUE),
+    measureTime3(0D, Double.MAX_VALUE),
+    measureTime4(0D, Double.MAX_VALUE),
+    measureTime5(0D, Double.MAX_VALUE),
+
+    callBridgeTime(0D, Double.MAX_VALUE),
+    cssLayoutTime(0D, Double.MAX_VALUE),
+    parseJsonTime(0D, Double.MAX_VALUE),
+
+    communicateTime(0D, 5000D),
+    screenRenderTime(0D, 5000D),
+    totalTime(0D, 5000D),
+    localReadTime(0D, 5000D),
+    templateLoadTime(0D, 5000D),
+    packageSpendTime(0D, 5000D),
+    syncTaskTime(0D, 5000D),
+    actualNetworkTime(0D, 5000D),
+    firstScreenJSFExecuteTime(0D, 5000D),
+    //..
+
+    fluency(0D, 101D),
+    imgSizeCount(0D, 2000D),
+    interactionTime(0D,10000D),
+    interactionViewAddCount(0D, Double.MAX_VALUE),
+    interactionViewAddLimitCount(0D, Double.MAX_VALUE),
+    newFsRenderTime(0D, 10000D);
+
+    private double mMinRange, mMaxRange;
+
+    Measure(double min, double max) {
+      this.mMinRange = min;
+      this.mMaxRange = max;
+    }
+
+    public double getMinRange() {
+      return mMinRange;
+    }
+
+    public double getMaxRange() {
+      return mMaxRange;
+    }
+  }
+
+  public static final String DEFAULT = "default";
+
+  @RestrictTo(RestrictTo.Scope.LIBRARY_GROUP)
+  public static final String CACHE_TYPE = "cacheType";
+
+  public static final int VIEW_LIMIT_HEIGHT = WXViewUtils.getScreenHeight() /3*2;
+  public static final int VIEW_LIMIT_WIDTH = WXViewUtils.getScreenWidth() /3*2;
+  public static boolean TRACE_DATA = WXEnvironment.isApkDebugable();
+
+  /**
+   * No longer needed.
+   */
+  @Deprecated
+  public String bizType = "weex";
+
+  /**
+   * Use {@link #pageName} instead.
+   */
+  @Deprecated
+  public String templateUrl;
+
+  @RestrictTo(RestrictTo.Scope.LIBRARY_GROUP)
+  public String cacheType = "none";
+
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  public long renderTimeOrigin;
+
+  public long renderUnixTimeOrigin;
+
+  public long fsRenderTime;
+
+  public long callCreateFinishTime;
+
+  public long interactionTime;
+
+  public long interactionRealUnixTime;
+
+  public int interactionViewAddCount;
+
+  public int interactionViewAddLimitCount;
+
+  public long newFsRenderTime;
+
+  public int localInteractionViewAddCount;
+
+  /**
+   * Time used for
+   * {@link WXBridgeManager#createInstance(String, String, Map, String)}
+   */
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  public long callCreateInstanceTime;
+
+
+  public long fsCallJsTotalTime;
+
+  public int fsCallJsTotalNum;
+
+  public long fsCallNativeTotalTime;
+
+  public int fsCallNativeTotalNum;
+
+  public int fsRequestNum;
+
+  public int fsComponentCount;
+
+  public int fsComponentCreateTime;
+
+  public int cellExceedNum;
+
+  public int timerInvokeCount;
+
+  public int fsCallEventTotalNum;
+
+  public long avgFPS;
+  public double fluency = 100D;
+
+  public long backImproveMemory;
+
+
+  /**
+   * Time spent for reading, time unit is ms.
+   */
+  public double localReadTime;
+
+  /**
+   * Name of the page
+   */
+  public String pageName = DEFAULT;
+
+  /**
+   * Size of JavaScript framework, the unit is KB
+   */
+  public double JSLibSize;
+
+  /**
+   * Time of initial JavaScript library
+   */
+  public long JSLibInitTime;
+
+  /**
+   * Size of JavaScript template
+   */
+  public double JSTemplateSize;
+
+  public long templateLoadTime;
+
+  /**
+   * Use {@link #callCreateInstanceTime} instead.
+   */
+  @Deprecated
+  public long communicateTime;
+
+  /**
+   * Time spent when rendering first screen
+   */
+  public long screenRenderTime;
+
+  /**
+   * Call native Time spent when rendering first screen
+   */
+  public long callBridgeTime;
+
+  /**
+   * Create Instance Time spent when rendering first screen
+   */
+  public long firstScreenJSFExecuteTime;
+
+  /**
+   * Call native Time spent when rendering first screen
+   */
+  public long parseJsonTime;
+
+  /**
+   * CssLayout Time spent when rendering first screen
+   */
+  public long cssLayoutTime;
+
+  /**
+   * Time spent, the unit is micro second
+   */
+  public double totalTime;
+
+  /**
+   * load bundle js time, unite ms
+   */
+  public long networkTime;
+
+  /**
+   * pure network time;
+   */
+  public long pureNetworkTime;
+
+  public long actualNetworkTime;
+  public long packageSpendTime;
+  public long syncTaskTime;
+  /**
+   * view hierarchy
+   */
+  public int maxDeepViewLayer;
+
+  public int maxDeepVDomLayer;
+
+  public double wrongImgSizeCount;
+
+  /**
+   * 1:true
+   * 0:false
+   */
+  public int useScroller = 0;
+
+  /**
+   * component Count
+   */
+  public long componentCount;
+
+  public long componentCreateTime;
+  /**
+   * Version of JavaScript libraray
+   */
+  public String JSLibVersion = WXEnvironment.JS_LIB_SDK_VERSION;
+
+  /**
+   * Version of Weex SDK
+   */
+  public String WXSDKVersion = WXEnvironment.WXSDK_VERSION;
+
+  /**
+   * The detail message of render failure
+   */
+  public String renderFailedDetail;
+
+  /**
+   * Error code
+   */
+  public String errCode;
+
+  /**
+   * Error message
+   */
+  @Deprecated
+  public String errMsg;
+  private StringBuilder mErrMsgBuilder;
+
+  public String args="";
+
+  public String connectionType;
+  public String requestType="other";
+
+  public String zCacheInfo;
+
+  /**
+   *for network tracker
+   */
+
+  /**
+   * TODO These dimensions will be moved to elsewhere
+   */
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  @Deprecated
+  public String wxDims[] = new String[5];
+
+  /**
+   * TODO These dimensions will be moved to elsewhere
+   */
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  @Deprecated
+  public long measureTimes[] = new long[5];
+
+
+  /**
+   * RenderAction
+   */
+  public int mActionAddElementCount = 0;
+  public int mActionAddElementSumTime = 0;
+
+  private String mInstanceId;
+
+  public WXPerformance(String instanceId){
+    mErrMsgBuilder=new StringBuilder();
+    mInstanceId = instanceId;
+  }
+
+  public Map<String, Double> getMeasureMap() {
+    double fsRenderTime;
+    if (this.fsRenderTime != 0) {
+      fsRenderTime = this.fsRenderTime - renderTimeOrigin;
+    } else {
+      if (totalTime != 0) {
+        fsRenderTime = totalTime;
+      } else {
+        fsRenderTime = -1;
+      }
+    }
+    Map<String, Double> quotas = new HashMap<>();
+    quotas.put(Measure.JSLibSize.toString(), JSLibSize);
+    quotas.put(Measure.JSLibInitTime.toString(), (double) JSLibInitTime);
+    quotas.put(Measure.SDKInitTime.toString(), (double) WXEnvironment.sSDKInitTime);
+    quotas.put(Measure.SDKInitInvokeTime.toString(), (double) WXEnvironment.sSDKInitInvokeTime);
+    quotas.put(Measure.SDKInitExecuteTime.toString(), (double) WXEnvironment.sSDKInitExecuteTime);
+    quotas.put(Measure.JSTemplateSize.toString(), JSTemplateSize);
+    quotas.put(Measure.pureNetworkTime.toString(), (double) pureNetworkTime);
+    quotas.put(Measure.networkTime.toString(), (double) networkTime);
+    quotas.put(Measure.fsCreateInstanceTime.toString(), (double) callCreateInstanceTime);
+    quotas.put(Measure.fsCallJsTotalTime.toString(), (double) fsCallJsTotalTime);
+    quotas.put(Measure.fsCallJsTotalNum.toString(), (double) fsCallJsTotalNum);
+    quotas.put(Measure.fsCallNativeTotalTime.toString(), (double) fsCallNativeTotalTime);
+    quotas.put(Measure.fsCallNativeTotalNum.toString(), (double) fsCallNativeTotalNum);
+    quotas.put(Measure.fsComponentCount.toString(),(double)fsComponentCount);
+    quotas.put(Measure.fsComponentCreateTime.toString(),(double)fsComponentCreateTime);
+    quotas.put(Measure.fsRenderTime.toString(), fsRenderTime);
+    quotas.put(Measure.fsRequestNum.toString(), (double) fsRequestNum);
+    quotas.put(Measure.communicateTotalTime.toString(), totalTime);
+    quotas.put(Measure.maxDeepViewLayer.toString(), (double) maxDeepViewLayer);
+    quotas.put(Measure.maxDeepVDomLayer.toString(), (double) maxDeepVDomLayer);
+    quotas.put(Measure.componentCount.toString(), (double) componentCount);
+    quotas.put(Measure.componentCreateTime.toString(),(double)componentCreateTime);
+    quotas.put(Measure.cellExceedNum.toString(), (double) cellExceedNum);
+    quotas.put(Measure.timerCount.toString(), (double) timerInvokeCount);
+    quotas.put(Measure.avgFps.toString(), (double) avgFPS);
+    quotas.put(Measure.fluency.toString(), fluency);
+    quotas.put(Measure.MaxImproveMemory.toString(), 0D);
+    quotas.put(Measure.BackImproveMemory.toString(), (double) backImproveMemory);
+    quotas.put(Measure.PushImproveMemory.toString(), 0D);
+
+    quotas.put(Measure.fsCallEventTotalNum.toString(), (double) fsCallEventTotalNum);
+    quotas.put(Measure.callCreateFinishTime.toString(), (double) callCreateFinishTime);
+    quotas.put(Measure.imgSizeCount.toString(), wrongImgSizeCount);
+    quotas.put(Measure.interactionTime.toString(), (double) interactionTime);
+    quotas.put(Measure.interactionViewAddCount.toString(), (double) interactionViewAddCount);
+    quotas.put(Measure.interactionViewAddLimitCount.toString(), (double) interactionViewAddLimitCount);
+    quotas.put(Measure.newFsRenderTime.toString(), (double) newFsRenderTime);
+
+    quotas.put(Measure.callBridgeTime.toString(), (double) callBridgeTime);
+    quotas.put(Measure.cssLayoutTime.toString(), (double) cssLayoutTime);
+    quotas.put(Measure.parseJsonTime.toString(), (double) parseJsonTime);
+
+    // TODO the following attribute is no longer needed and will be deleted soon.
+    quotas.put(Measure.screenRenderTime.toString(), (double) screenRenderTime);
+    quotas.put(Measure.communicateTime.toString(), (double) communicateTime);
+    quotas.put(Measure.localReadTime.toString(), localReadTime);
+    quotas.put(Measure.templateLoadTime.toString(), (double) templateLoadTime);
+    quotas.put(Measure.firstScreenJSFExecuteTime.toString(), (double) firstScreenJSFExecuteTime);
+    quotas.put(Measure.actualNetworkTime.toString(), (double) actualNetworkTime);
+    quotas.put(Measure.syncTaskTime.toString(), (double) syncTaskTime);
+    quotas.put(Measure.packageSpendTime.toString(), (double) packageSpendTime);
+
+    // TODO These attribute will be moved to elsewhere
+    quotas.put(Measure.measureTime1.toString(), (double) measureTimes[0]);
+    quotas.put(Measure.measureTime2.toString(), (double) measureTimes[1]);
+    quotas.put(Measure.measureTime3.toString(), (double) measureTimes[2]);
+    quotas.put(Measure.measureTime4.toString(), (double) measureTimes[3]);
+    quotas.put(Measure.measureTime5.toString(), (double) measureTimes[4]);
+    return quotas;
+  }
+
+  public Map<String, String> getDimensionMap() {
+    Map<String, String> quotas = new HashMap<>();
+    quotas.put(Dimension.JSLibVersion.toString(), JSLibVersion);
+    quotas.put(Dimension.WXSDKVersion.toString(), WXSDKVersion);
+    quotas.put(Dimension.pageName.toString(), pageName);
+    quotas.put(Dimension.requestType.toString(), requestType);
+    quotas.put(Dimension.networkType.toString(), "unknown");
+    quotas.put(Dimension.connectionType.toString(), connectionType);
+    quotas.put(Dimension.zcacheInfo.toString(), zCacheInfo);
+    quotas.put(Dimension.cacheType.toString(), cacheType);
+    quotas.put(Dimension.useScroller.toString(), String.valueOf(useScroller));
+
+    WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
+    String keyActivity = WXInstanceApm.KEY_PAGE_PROPERTIES_CONTAINER_NAME;
+    quotas.put(keyActivity, null == sdkInstance? "unKnow" : sdkInstance.getContainerInfo().get(keyActivity));
+    String keyType = WXInstanceApm.KEY_PAGE_PROPERTIES_INSTANCE_TYPE;
+    quotas.put(keyType,sdkInstance == null ?"unKnow": sdkInstance.getContainerInfo().get(keyType));
+    String keyParentPae = WXInstanceApm.KEY_PAGE_PROPERTIES_PARENT_PAGE;
+    quotas.put(keyParentPae,null == sdkInstance ?"unKnow":sdkInstance.getContainerInfo().get(keyParentPae));
+
+    // TODO These attribute will be moved to elsewhere
+    // Extra Dimension for 3rd developers.
+    quotas.put(Dimension.wxdim1.toString(), wxDims[0]);
+    quotas.put(Dimension.wxdim2.toString(), wxDims[1]);
+    quotas.put(Dimension.wxdim3.toString(), wxDims[2]);
+    quotas.put(Dimension.wxdim4.toString(), wxDims[3]);
+    quotas.put(Dimension.wxdim5.toString(), wxDims[4]);
+
+    // TODO the following attribute is no longer needed and will be deleted soon.
+    quotas.put(Dimension.bizType.toString(), bizType);
+    quotas.put(Dimension.templateUrl.toString(), templateUrl);
+    return quotas;
+  }
+
+  public static String[] getDimensions() {
+    List<String> ret = new LinkedList<>();
+    for (Dimension dimension : Dimension.values()) {
+      ret.add(dimension.toString());
+    }
+    return ret.toArray(new String[ret.size()]);
+  }
+
+  public static String[] getMeasures() {
+    List<String> ret = new LinkedList<>();
+    for (Measure measure : Measure.values()) {
+      ret.add(measure.toString());
+    }
+    return ret.toArray(new String[ret.size()]);
+  }
+
+  @Override
+  public String toString() {
+    if (WXEnvironment.isApkDebugable()) {
+      return "bizType:" + bizType + ",pageName:" + pageName + ",templateLoadTime" + templateLoadTime
+              + ",localReadTime:" + localReadTime + ",JSLibInitTime:" + JSLibInitTime
+              + ",JSLibSize:" + JSLibSize + ",templateUrl" + templateUrl
+              + ",JSTemplateSize:" + JSTemplateSize + ",communicateTime:" + communicateTime
+              + ",screenRenderTime:" + screenRenderTime
+              + ",firstScreenJSFExecuteTime:" + firstScreenJSFExecuteTime
+              + ",componentCount:" + componentCount
+              + ",syncTaskTime:" + syncTaskTime
+              + ",pureNetworkTime:" + pureNetworkTime
+              + ",networkTime:" + networkTime
+              + ",actualNetworkTime:" + actualNetworkTime
+              + ",packageSpendTime:" + packageSpendTime
+              + ",connectionType:" + connectionType
+              + ",requestType:" + requestType
+              + ",initInvokeTime:" + WXEnvironment.sSDKInitInvokeTime + ",initExecuteTime:" + WXEnvironment.sSDKInitExecuteTime
+              + ",SDKInitTime:" + WXEnvironment.sSDKInitTime
+              + ",totalTime:" + totalTime + ",JSLibVersion:" + JSLibVersion + ",WXSDKVersion:" + WXSDKVersion
+              + ",errCode:" + errCode + ",renderFailedDetail:" + renderFailedDetail
+              + ",arg:" + args
+              + ",errMsg:" + getErrMsg();
+    }
+    return super.toString();
+  }
+
+  public String getPerfData() {
+    return "networkTime:" + networkTime
+            + " actualNetworkTime:" + actualNetworkTime
+            + " connectionType:" + connectionType
+            + " requestType:" + requestType
+            + " firstScreenRenderTime:" + screenRenderTime
+            + " firstScreenJSFExecuteTime:" + firstScreenJSFExecuteTime
+            + " componentCount:" + componentCount
+            + " JSTemplateSize:" + JSTemplateSize
+            + " SDKInitTime:" + WXEnvironment.sSDKInitTime
+            + " totalTime:" + totalTime
+            + " JSLibVersion:" + JSLibVersion
+            + " WXSDKVersion:" + WXSDKVersion
+            + " pageName:" + pageName
+            + " useScroller:" + useScroller;
+
+  }
+
+  public String getErrMsg() {
+    return mErrMsgBuilder.toString();
+  }
+
+  public void appendErrMsg(CharSequence msg) {
+    mErrMsgBuilder.append(msg);
+  }
+
+  public void beforeInstanceRender(String instanceId) {
+    renderTimeOrigin = System.currentTimeMillis();
+    renderUnixTimeOrigin = WXUtils.getFixUnixTime();
+  }
+
+  public void afterInstanceDestroy(String instanceId) {
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXRefreshData.java b/android/sdk/src/main/java/org/apache/weex/common/WXRefreshData.java
new file mode 100644
index 0000000..02d6696
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXRefreshData.java
@@ -0,0 +1,31 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public class WXRefreshData {
+
+  public String data;
+
+  public boolean isDirty;
+
+  public WXRefreshData(String data, boolean isDirty) {
+    this.data = data;
+    this.isDirty = isDirty;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXRenderStrategy.java b/android/sdk/src/main/java/org/apache/weex/common/WXRenderStrategy.java
new file mode 100644
index 0000000..2dcc5cd
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXRenderStrategy.java
@@ -0,0 +1,39 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public enum WXRenderStrategy {
+  APPEND_ASYNC("APPEND_ASYNC"),
+  APPEND_ONCE("APPEND_ONCE"),
+  DATA_RENDER("DATA_RENDER"),
+  DATA_RENDER_BINARY("DATA_RENDER_BINARY"),
+  JSON_RENDER("JSON_RENDER");
+
+
+  private String flag;
+
+  WXRenderStrategy(String flag) {
+    this.flag = flag;
+  }
+
+  public String getFlag() {
+    return flag;
+  }
+}
+
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXRequest.java b/android/sdk/src/main/java/org/apache/weex/common/WXRequest.java
new file mode 100644
index 0000000..d0aa52c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXRequest.java
@@ -0,0 +1,60 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import org.apache.weex.WXSDKInstance;
+
+import java.util.Map;
+
+public class WXRequest {
+
+  /**
+   * The request parameter
+   */
+  public Map<String, String> paramMap;
+
+  /**
+   * The request URL
+   */
+  public String url;
+  /**
+   * The request method
+   */
+  public String method;
+  /**
+   * The request body
+   */
+  public String body;
+
+  /**
+   * The request time out
+   */
+  public int timeoutMs = WXRequest.DEFAULT_TIMEOUT_MS;
+
+  /**
+   * The default timeout
+   */
+  public static final int DEFAULT_TIMEOUT_MS = 3000;
+
+  /**
+   * running weex instanceId
+   * @see WXSDKInstance#mInstanceId
+   */
+  public String instanceId;;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXRequestListener.java b/android/sdk/src/main/java/org/apache/weex/common/WXRequestListener.java
new file mode 100644
index 0000000..f261ac9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXRequestListener.java
@@ -0,0 +1,27 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+
+public interface WXRequestListener {
+
+  void onSuccess(int requestType, Object context, WXResponse response);
+
+  void onError(int requestType, Object context, WXResponse response);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXResponse.java b/android/sdk/src/main/java/org/apache/weex/common/WXResponse.java
new file mode 100644
index 0000000..4c209cc
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXResponse.java
@@ -0,0 +1,56 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import java.util.Map;
+
+public class WXResponse {
+
+  /**
+   * Status code
+   */
+  public String statusCode;
+
+  /**
+   * Byte stream fetched from the connection
+   */
+  public String data;
+
+  public byte[] originalData;
+
+  /**
+   * Server internal error
+   */
+  public String errorCode;
+
+  /**
+   * Server error message
+   */
+  public String errorMsg;
+
+  /**
+   * Message for toast
+   */
+  public String toastMsg;
+
+  /**
+   * Parameter for further extension.
+   */
+  public Map<String, Object> extendParams;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXRuntimeException.java b/android/sdk/src/main/java/org/apache/weex/common/WXRuntimeException.java
new file mode 100644
index 0000000..0673f8d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXRuntimeException.java
@@ -0,0 +1,28 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+public class WXRuntimeException extends RuntimeException {
+
+  private static final long serialVersionUID = 5732315311747521491L;
+
+  public WXRuntimeException(String e) {
+    super(e);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXThread.java b/android/sdk/src/main/java/org/apache/weex/common/WXThread.java
new file mode 100644
index 0000000..f9ee2f4
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXThread.java
@@ -0,0 +1,201 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import android.os.Handler;
+import android.os.Handler.Callback;
+import android.os.HandlerThread;
+import android.os.Message;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.tools.LogDetail;
+
+import java.lang.ref.WeakReference;
+import org.apache.weex.utils.tools.TimeCalculator;
+
+/**
+ * Thread used in weex
+ */
+public class WXThread extends HandlerThread {
+
+  private Handler mHandler;
+
+  static class SafeRunnable implements Runnable {
+
+    static final String TAG = "SafeRunnable";
+    private LogDetail mTimelineLog = null;
+    private WeakReference<WXSDKInstance> mInstance;
+    final Runnable mTask;
+    SafeRunnable(Runnable task){
+      this(task,null);
+    }
+
+    SafeRunnable(Runnable task, String taskName){
+      this(task,null, taskName);
+    }
+
+    SafeRunnable(Runnable runnable, WXSDKInstance instance, String taskName) {
+      mTask = runnable;
+      if(taskName != null) {
+        mTimelineLog = new LogDetail();
+        mTimelineLog.info.platform = TimeCalculator.PLATFORM_ANDROID;
+        mTimelineLog.name(taskName);
+        mInstance = new WeakReference<>(instance);
+      }
+    }
+
+    @Override
+    public void run() {
+      try {
+        if(mTask != null) {
+          if (mTimelineLog != null)
+            mTimelineLog.taskStart();
+          mTask.run();
+          if (mTimelineLog != null)
+            mTimelineLog.taskEnd();
+        }
+      }catch (Throwable e){
+        //catch everything may throw from exection.
+        if(WXEnvironment.isApkDebugable()){
+          WXLogUtils.e(TAG,"SafeRunnable run throw expection:"+e.getMessage());
+          throw e;
+        }
+        WXLogUtils.w(TAG, e);
+      }
+
+      if (mTimelineLog != null) {
+        if(mInstance != null) {
+          WXSDKInstance wxsdkInstance = mInstance.get();
+          if(wxsdkInstance != null) {
+            wxsdkInstance.mTimeCalculator.addLog(mTimelineLog);
+          }
+        }
+      }
+
+    }
+  }
+
+  static class SafeCallback implements Callback {
+    static final String TAG = "SafeCallback";
+
+    final Callback mCallback;
+    SafeCallback(Callback cb){
+      mCallback = cb;
+    }
+
+    @Override
+    public boolean handleMessage(Message msg) {
+      boolean result = false;
+      try{
+        if(mCallback != null){
+          result = mCallback.handleMessage(msg);
+        }
+      }catch (Throwable e){
+        //catch everything may throw from exection.
+        if(WXEnvironment.isApkDebugable()){
+          WXLogUtils.e(TAG,"SafeCallback handleMessage throw expection:"+e.getMessage());
+          throw e;
+        }
+      }
+      return result;
+    }
+  }
+
+  /**
+   * Secure Runnable to prevent throw during execution.
+   * NOTE: DO NOT use this method to wrap runnable that may be removed by {@link Handler#removeCallbacks(Runnable)}
+   * @param runnable
+   * @return
+   */
+  public static Runnable secure(Runnable runnable){
+    return secure(runnable, null, null);
+  }
+
+
+  public static Runnable secure(Runnable runnable, WXSDKInstance instance, String runnableName){
+    if(runnable == null || runnable instanceof SafeRunnable){
+      return runnable;
+    }
+    return new SafeRunnable(runnable,instance, runnableName);
+  }
+
+  public static Callback secure(Callback callback){
+    if(callback == null || callback instanceof SafeCallback){
+      return callback;
+    }
+
+    return new SafeCallback(callback);
+  }
+
+  /**
+   * @param name name of thread
+   */
+  public WXThread(String name) {
+    super(name);
+    start();
+    mHandler = new Handler(getLooper());
+  }
+
+
+  public WXThread(String name, Callback callback) {
+    super(name);
+    start();
+    mHandler = new Handler(getLooper(), secure(callback));
+  }
+
+  /**
+   * @param name name of thread
+   * @param priority The priority to run the thread at. The value supplied must be from
+   *                 {@link android.os.Process} and not from java.lang.Thread.
+   */
+  public WXThread(String name, int priority, Callback callback) {
+    super(name, priority);
+    start();
+    mHandler = new Handler(getLooper(), secure(callback));
+  }
+
+  /**
+   * @param name name of thread
+   * @param priority The priority to run the thread at. The value supplied must be from
+   *                 {@link android.os.Process} and not from java.lang.Thread.
+   */
+  public WXThread(String name, int priority) {
+    super(name, priority);
+    start();
+    mHandler = new Handler(getLooper());
+  }
+
+  public Handler getHandler() {
+    return mHandler;
+  }
+
+  public boolean isWXThreadAlive() {
+    return (mHandler != null && getLooper() != null && isAlive());
+  }
+
+  @Override
+  public boolean quit() {
+    if (mHandler != null) {
+      mHandler.removeCallbacksAndMessages(null);
+    }
+    return super.quit();
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/common/WXWorkThreadManager.java b/android/sdk/src/main/java/org/apache/weex/common/WXWorkThreadManager.java
new file mode 100644
index 0000000..8753ca9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/common/WXWorkThreadManager.java
@@ -0,0 +1,56 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.common;
+
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import java.util.concurrent.ExecutorService;
+import java.util.concurrent.Executors;
+
+/**
+ * Class for managing work thread.
+ *
+ * <p>
+ *  This class is for internal purpose,
+ *  please don't use it directly unless you know what you are doing.
+ * </p>
+ */
+@RestrictTo(Scope.LIBRARY_GROUP)
+public class WXWorkThreadManager {
+
+  private ExecutorService singleThreadExecutor;
+
+  public WXWorkThreadManager() {
+    singleThreadExecutor = Executors.newSingleThreadExecutor();
+  }
+
+  public void post(Runnable task) {
+    if (singleThreadExecutor != null)
+      singleThreadExecutor.execute(task);
+  }
+
+  /**
+   * Destroy current instance
+   */
+  public void destroy() {
+    if (singleThreadExecutor != null)
+      singleThreadExecutor.shutdown();
+    singleThreadExecutor = null;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/CSSConstants.java b/android/sdk/src/main/java/org/apache/weex/dom/CSSConstants.java
new file mode 100755
index 0000000..70a7a8c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/CSSConstants.java
@@ -0,0 +1,28 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.dom;
+
+public class CSSConstants {
+
+  public static final float UNDEFINED = Float.NaN;
+
+  public static boolean isUndefined(float value) {
+    return Float.compare(value, UNDEFINED) == 0;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/CSSShorthand.java b/android/sdk/src/main/java/org/apache/weex/dom/CSSShorthand.java
new file mode 100644
index 0000000..9c20d86
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/CSSShorthand.java
@@ -0,0 +1,120 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.dom;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.text.TextUtils;
+import org.apache.weex.dom.CSSShorthand.CSSProperty;
+import java.util.Arrays;
+
+public class CSSShorthand<T extends Enum<? extends CSSProperty>> implements Cloneable {
+
+  interface CSSProperty{
+  }
+
+  public static enum EDGE implements CSSProperty{
+    TOP, BOTTOM, LEFT, RIGHT, ALL;
+  }
+
+  public static enum CORNER implements CSSProperty{
+    BORDER_TOP_LEFT, BORDER_TOP_RIGHT,
+    BORDER_BOTTOM_RIGHT, BORDER_BOTTOM_LEFT, ALL;
+  }
+
+  public static enum TYPE {
+    MARGIN, PADDING, BORDER;
+  }
+
+  private float[] values;
+
+  public CSSShorthand(float []values){
+    replace(values);
+  }
+
+  public CSSShorthand() {
+    this(false);
+  }
+
+  CSSShorthand(boolean fillWithNaN) {
+    values = new float[Math.max(EDGE.values().length,CORNER.values().length)];
+    if (fillWithNaN) {
+      Arrays.fill(values, Float.NaN);
+    }
+  }
+
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  public void set(@NonNull EDGE edge, float value){
+    setInternal(edge, value);
+  }
+
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  public void set(@NonNull CORNER edge, float value) {
+    setInternal(edge, value);
+  }
+
+  /**
+   * {@link EDGE#ALL} is not supported, 0 will be returned.
+   * @throws IndexOutOfBoundsException
+   * @param edge
+   * @return
+   */
+  public float get(@NonNull EDGE edge){
+    return getInternal(edge);
+  }
+
+  /**
+   * {@link CORNER#ALL} is not supported, 0 will be returned.
+   * @throws IndexOutOfBoundsException
+   * @param edge
+   * @return
+   */
+  public float get(@NonNull CORNER edge) {
+    return getInternal(edge);
+  }
+
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  public final void replace(float []values){
+    this.values = values;
+  }
+
+  @Override
+  public CSSShorthand clone() throws CloneNotSupportedException {
+    return (CSSShorthand) super.clone();
+  }
+
+  private void setInternal(@NonNull Enum<? extends CSSProperty> edge, float value){
+    if (edge == EDGE.ALL || edge == CORNER.ALL) {
+      Arrays.fill(values, value);
+    } else {
+      values[edge.ordinal()] = value;
+    }
+  }
+
+  private float getInternal(@NonNull Enum<? extends CSSProperty> edge){
+    return (edge == EDGE.ALL || edge == CORNER.ALL) ? 0 : values[edge.ordinal()];
+  }
+
+  @Override
+  @RestrictTo(Scope.LIBRARY)
+  public String toString() {
+    return TextUtils.isEmpty(values.toString()) ? "" : Arrays.toString(values);
+  }
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/RenderContext.java b/android/sdk/src/main/java/org/apache/weex/dom/RenderContext.java
new file mode 100644
index 0000000..f54f12d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/RenderContext.java
@@ -0,0 +1,32 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.dom;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by sospartan on 23/02/2017.
+ */
+
+public interface RenderContext {
+  WXSDKInstance getInstance();
+  WXComponent getComponent(String ref);
+  WXComponent unregisterComponent(String ref);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/TextDecorationSpan.java b/android/sdk/src/main/java/org/apache/weex/dom/TextDecorationSpan.java
new file mode 100644
index 0000000..98be70a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/TextDecorationSpan.java
@@ -0,0 +1,55 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.dom;
+
+
+import android.support.annotation.NonNull;
+import android.text.TextPaint;
+import android.text.style.CharacterStyle;
+import android.text.style.UpdateAppearance;
+
+import org.apache.weex.ui.component.WXTextDecoration;
+
+public class TextDecorationSpan extends CharacterStyle
+    implements UpdateAppearance {
+
+  private final WXTextDecoration mTextDecoration;
+
+  public TextDecorationSpan(@NonNull WXTextDecoration wxTextDecoration) {
+    this.mTextDecoration = wxTextDecoration;
+  }
+
+  @Override
+  public void updateDrawState(TextPaint tp) {
+    switch (mTextDecoration) {
+      case LINETHROUGH:
+        tp.setUnderlineText(false);
+        tp.setStrikeThruText(true);
+        break;
+      case UNDERLINE:
+        tp.setUnderlineText(true);
+        tp.setStrikeThruText(false);
+        break;
+      case NONE:
+        tp.setUnderlineText(false);
+        tp.setStrikeThruText(false);
+        break;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/WXAttr.java b/android/sdk/src/main/java/org/apache/weex/dom/WXAttr.java
new file mode 100644
index 0000000..a04c70e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/WXAttr.java
@@ -0,0 +1,591 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.dom;
+
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Locale;
+import java.util.Map;
+import java.util.Set;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.UiThread;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.Constants.Name;
+import org.apache.weex.common.WXImageSharpen;
+import org.apache.weex.dom.binding.ELUtils;
+import org.apache.weex.dom.binding.WXStatement;
+import org.apache.weex.el.parse.Parser;
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import static org.apache.weex.dom.binding.ELUtils.COMPONENT_PROPS;
+import static org.apache.weex.dom.binding.ELUtils.EXCLUDES_BINDING;
+import static java.lang.Boolean.parseBoolean;
+
+/**
+ * store value of component attribute
+ *
+ */
+public class WXAttr implements Map<String, Object>,Cloneable {
+
+  private static final long serialVersionUID = -2619357510079360946L;
+
+  /**
+   * static attrs
+   * */
+  private @NonNull Map<String, Object> attr;
+  private Map<String, Object> writeAttr;
+
+  /**
+   * dynamic binding attrs, can be null, only weex use
+   * */
+  private ArrayMap<String, Object>  mBindingAttrs;
+
+  /**
+   * dynamic binding statement for match, can be null, only weex use
+   * */
+  private WXStatement mStatement;
+
+  public WXAttr(){
+    attr = new HashMap<>();
+  }
+
+  public WXAttr(@NonNull Map<String,Object> standardMap) {
+    attr = standardMap;
+  }
+
+  public WXAttr(@NonNull Map<String,Object> standardMap, int extra){
+    attr = standardMap;
+  }
+
+  public static String getPrefix(Map<String, Object> attr) {
+    if (attr == null) {
+      return null;
+    }
+    Object src = attr.get(Constants.Name.PREFIX);
+    if (src == null) {
+      return null;
+    }
+    return src.toString();
+  }
+
+  public static String getSuffix(Map<String, Object> attr) {
+    if (attr == null) {
+      return null;
+    }
+    Object src = attr.get(Constants.Name.SUFFIX);
+    if (src == null) {
+      return null;
+    }
+    return src.toString();
+  }
+
+  /**
+   * Compatible with value、content
+   *
+   * @return
+   */
+  public static String getValue(Map<String, Object> attr) {
+    if (attr == null) {
+      return null;
+    }
+    Object src = attr.get(Constants.Name.VALUE);
+    if (src == null) {
+      src = attr.get("content");
+      if (src == null) {
+        return null;
+      }
+    }
+    return src.toString();
+  }
+
+  public WXImageQuality getImageQuality() {
+    Object obj = containsKey(Name.QUALITY) ? get(Name.QUALITY) : get(Name.IMAGE_QUALITY);
+    WXImageQuality imageQuality = WXImageQuality.AUTO;
+    String value;
+    if (obj != null && !TextUtils.isEmpty(value = obj.toString())) {
+      try {
+        imageQuality = WXImageQuality.valueOf(value.toUpperCase(Locale.US));
+      }catch (IllegalArgumentException e){
+        WXLogUtils.e("Image", "Invalid value image quality. Only low, normal, high, original are valid");
+      }
+    }
+    return imageQuality;
+  }
+
+  public WXImageSharpen getImageSharpen() {
+    Object obj = get(Constants.Name.SHARPEN);
+    if (obj == null) {
+      obj = get(Constants.Name.IMAGE_SHARPEN);
+    }
+    if (obj == null) {
+      return WXImageSharpen.UNSHARPEN;
+    }
+    String imageSharpen = obj.toString();
+    WXImageSharpen waImageSharpen = WXImageSharpen.UNSHARPEN;
+    if (imageSharpen.equals("sharpen")) {
+      waImageSharpen = WXImageSharpen.SHARPEN;
+    }
+
+    return waImageSharpen;
+  }
+
+  public String getImageSrc() {
+    Object src = get(Constants.Name.SRC);
+    if (src == null) {
+      return null;
+    }
+    return src.toString();
+  }
+
+  public boolean canRecycled() {
+    Object obj = get(Constants.Name.RECYCLE);
+    if (obj == null) {
+      return true;
+    }
+    try {
+      return parseBoolean(String.valueOf(obj));
+    } catch (Exception e) {
+      WXLogUtils.e("[WXAttr] recycle:", e);
+    }
+    return true;
+  }
+
+  public boolean showIndicators() {
+    Object obj = get(Constants.Name.SHOW_INDICATORS);
+    if (obj == null) {
+      return true;
+    }
+
+    try {
+      return parseBoolean(String.valueOf(obj));
+    } catch (Exception e) {
+      WXLogUtils.e("[WXAttr] showIndicators:", e);
+    }
+    return true;
+  }
+
+  public boolean autoPlay() {
+    Object obj = get(Constants.Name.AUTO_PLAY);
+    if (obj == null) {
+      return false;
+    }
+
+    try {
+      return parseBoolean(String.valueOf(obj));
+    } catch (Exception e) {
+      WXLogUtils.e("[WXAttr] autoPlay:", e);
+    }
+    return false;
+  }
+
+  public String getScope() {
+    Object src = get(Constants.Name.SCOPE);
+    if (src == null) {
+      return null;
+    }
+    return src.toString();
+  }
+  public String getLoadMoreRetry() {
+    Object src = get(Constants.Name.LOADMORERETRY);
+    if (src == null) {
+      return null;
+    }
+    return src.toString();
+  }
+
+  public String getLoadMoreOffset() {
+    Object src = get(Constants.Name.LOADMOREOFFSET);
+    if (src == null) {
+      return null;
+    }
+    return src.toString();
+  }
+
+  public String optString(String key){
+    if(containsKey(key)){
+      Object value = get(key);
+      if (value instanceof String) {
+        return (String) value;
+      } else if (value != null) {
+        return String.valueOf(value);
+      }
+    }
+    return "";
+  }
+
+  public boolean getIsRecycleImage() {
+    Object obj = get(Constants.Name.RECYCLE_IMAGE);
+    if (obj == null) {
+      return true;
+    }
+
+    try {
+      return parseBoolean(String.valueOf(obj));
+    } catch (Exception e) {
+      WXLogUtils.e("[WXAttr] recycleImage:", e);
+    }
+    return false;
+  }
+  public String getScrollDirection() {
+    Object scrollDirection = get("scrollDirection");
+    if (scrollDirection == null) {
+      return "vertical";
+    }
+    return scrollDirection.toString();
+  }
+
+  public int getOrientation() {
+    String direction = getScrollDirection();
+    if(!TextUtils.isEmpty(direction)){
+      if(direction.equals(Constants.Value.HORIZONTAL)){
+        return Constants.Orientation.HORIZONTAL;
+      }
+    }
+    Object value = get(Name.ORIENTATION);
+    if(value != null && Constants.Value.HORIZONTAL.equals(value.toString())){
+      return Constants.Orientation.HORIZONTAL;
+    }
+    return Constants.Orientation.VERTICAL;
+  }
+
+  public float getElevation(int viewPortW) {
+    Object obj = get(Constants.Name.ELEVATION);
+    float ret = Float.NaN;
+    if (obj != null) {
+      String number = obj.toString();
+      if (!TextUtils.isEmpty(number)) {
+        ret = WXViewUtils.getRealSubPxByWidth(WXUtils.getFloat(number),viewPortW);
+      } else {
+        ret = 0;
+      }
+    }
+    return ret;
+  }
+
+  public float getColumnWidth(){
+
+    Object obj = get(Constants.Name.COLUMN_WIDTH);
+    if (obj == null) {
+      return Constants.Value.AUTO;
+    }
+
+    String value = String.valueOf(obj);
+    if(Constants.Name.AUTO.equals(value)){
+      return Constants.Value.AUTO;
+    }
+
+    try {
+      float columnWidth = Float.parseFloat(value);
+      return columnWidth > 0 ? columnWidth : 0;
+    } catch (Exception e) {
+      WXLogUtils.e("[WXAttr] getColumnWidth:", e);
+    }
+    return Constants.Value.AUTO;
+  }
+
+  public int getColumnCount() {
+
+    Object obj = get(Constants.Name.COLUMN_COUNT);
+    if (obj == null) {
+      return Constants.Value.AUTO;
+    }
+
+    String value = String.valueOf(obj);
+    if(Constants.Name.AUTO.equals(value)){
+      return Constants.Value.AUTO;
+    }
+
+    try {
+      int columnCount = Integer.parseInt(value);
+      return columnCount > 0 ? columnCount : Constants.Value.AUTO;
+    } catch (Exception e) {
+      WXLogUtils.e("[WXAttr] getColumnCount:", e);
+      return Constants.Value.AUTO;
+    }
+  }
+
+  public float getColumnGap() {
+
+    Object obj = get(Constants.Name.COLUMN_GAP);
+    if (obj == null) {
+      return Constants.Value.COLUMN_GAP_NORMAL;
+    }
+
+    String value = String.valueOf(obj);
+    if (Constants.Name.NORMAL.equals(value)) {
+      return Constants.Value.COLUMN_GAP_NORMAL;
+    }
+
+    try {
+      float columnGap = Float.parseFloat(value);
+      return columnGap >= 0 ? columnGap : Constants.Value.AUTO;
+    } catch (Exception e) {
+      WXLogUtils.e("[WXAttr] getColumnGap:", e);
+    }
+    return Constants.Value.COLUMN_GAP_NORMAL;
+  }
+
+  public int getLayoutType(){
+    Object obj = get(Constants.Name.LAYOUT);
+    if (obj == null) {
+      return WXRecyclerView.TYPE_LINEAR_LAYOUT;
+    }
+
+    try {
+      switch(String.valueOf(obj)){
+        case Constants.Value.MULTI_COLUMN :
+          return  WXRecyclerView.TYPE_STAGGERED_GRID_LAYOUT;
+        case Constants.Value.GRID :
+          return  WXRecyclerView.TYPE_GRID_LAYOUT;
+        default:
+          return WXRecyclerView.TYPE_LINEAR_LAYOUT;
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[WXAttr] getLayoutType:", e);
+    }
+    return WXRecyclerView.TYPE_LINEAR_LAYOUT;
+  }
+
+
+  @Override
+  public boolean equals(Object o) {
+    return attr.equals(o);
+  }
+
+  @Override
+  public int hashCode() {
+    return attr.hashCode();
+  }
+
+  @Override
+  public void clear() {
+    attr.clear();
+  }
+
+  @Override
+  public boolean containsKey(Object key) {
+    return attr.containsKey(key);
+  }
+
+  @Override
+  public boolean containsValue(Object value) {
+    return attr.containsValue(value);
+  }
+
+  @NonNull
+  @Override
+  public Set<Entry<String, Object>> entrySet() {
+    return attr.entrySet();
+  }
+
+  @Override
+  public Object get(Object key) {
+    Map<String, Object> temp = writeAttr;
+    if (null != temp) {
+      Object obj = temp.get(key);
+      if (null != obj) {
+        return obj;
+      }
+    }
+    return attr.get(key);
+  }
+
+  @Override
+  public boolean isEmpty() {
+    return attr.isEmpty();
+  }
+
+  @NonNull
+  @Override
+  public Set<String> keySet() {
+    return attr.keySet();
+  }
+
+  @Override
+  public Object put(String key, Object value) {
+    if(addBindingAttrIfStatement(key, value)){
+      return null;
+    }
+    return attr.put(key,value);
+  }
+
+  @Override
+  public void putAll(Map<? extends String, ?> map) {
+    //this.attr.putAll(map);
+    if (this.writeAttr == null) {
+      this.writeAttr = new ArrayMap<>();
+    }
+    this.writeAttr.putAll(map);
+  }
+
+  @Override
+  public Object remove(Object key) {
+    return attr.remove(key);
+  }
+
+  @Override
+  public int size() {
+    return attr.size();
+  }
+
+  @NonNull
+  @Override
+  public Collection<Object> values() {
+    return attr.values();
+  }
+
+  /**
+   * can by null, in most contion without template list, the value is null
+   * */
+  public ArrayMap<String, Object> getBindingAttrs() {
+    return mBindingAttrs;
+  }
+
+  /**
+   * can by null, in most contion without template list, the value is null
+   * */
+  public WXStatement getStatement() {
+    return mStatement;
+  }
+
+
+  public void setBindingAttrs(ArrayMap<String, Object> mBindingAttrs) {
+    this.mBindingAttrs = mBindingAttrs;
+  }
+
+  public void setStatement(WXStatement mStatement) {
+    this.mStatement = mStatement;
+  }
+
+  public void parseStatements(){
+    if(this.attr != null){
+       this.attr = filterStatementsFromAttrs(this.attr);
+    }
+  }
+
+  /**
+   * filter dynamic state ment
+   * */
+  private Map<String, Object> filterStatementsFromAttrs(Map attrs) {
+    if(attrs == null || attrs.size() == 0){
+      return attrs;
+    }
+    Set<Map.Entry<String,Object>> entries = attrs.entrySet();
+    Iterator<Entry<String,Object>> it =  entries.iterator();
+    while (it.hasNext()){
+      Map.Entry<String,Object> entry = it.next();
+      if(COMPONENT_PROPS.equals(entry.getKey())){
+        Object blockValue = ELUtils.bindingBlock(entry.getValue());
+        entry.setValue(blockValue);
+        continue;
+      }
+      if(addBindingAttrIfStatement(entry.getKey(), entry.getValue())){
+        it.remove();
+      }
+    }
+    return attrs;
+  }
+
+  /**
+   * filter dynamic attrs and statements
+   * */
+  private boolean addBindingAttrIfStatement(String key, Object value) {
+    for(String exclude : EXCLUDES_BINDING){
+      if(key.equals(exclude)){
+        return  false;
+      }
+    }
+    if(ELUtils.isBinding(value)){
+      if(mBindingAttrs == null){
+        mBindingAttrs = new ArrayMap<String, Object>();
+      }
+      value = ELUtils.bindingBlock(value);
+      mBindingAttrs.put(key, value);
+      return  true;
+    }
+    if(WXStatement.WX_IF.equals(key)){
+      if(mStatement == null){
+        mStatement = new WXStatement();
+      }
+      if(value != null) {
+        mStatement.put(key, Parser.parse(value.toString()));
+      }
+      return  true;
+    }
+
+    if(WXStatement.WX_FOR.equals(key)){
+      if(mStatement == null){
+        mStatement = new WXStatement();
+      }
+      value = ELUtils.vforBlock(value);
+      if(value != null) {
+        mStatement.put(key, value);
+        return  true;
+      }
+    }
+
+    if(WXStatement.WX_ONCE.equals(key)){
+      if(mStatement == null){
+        mStatement = new WXStatement();
+      }
+      mStatement.put(key, true);
+    }
+    return  false;
+  }
+
+  public void skipFilterPutAll(Map<String,Object> attrs){
+    this.attr.putAll(attrs);
+  }
+
+  @UiThread
+  public void mergeAttr() {
+    if (null != this.writeAttr) {
+      this.attr.putAll(this.writeAttr);
+      this.writeAttr = null;
+    }
+  }
+
+  @Override
+  public WXAttr clone() {
+    WXAttr wxAttr = new WXAttr();
+    wxAttr.skipFilterPutAll(attr);
+    if (mBindingAttrs != null) {
+      wxAttr.mBindingAttrs = new ArrayMap<>(mBindingAttrs);
+    }
+    if (mStatement != null){
+      wxAttr.mStatement = new WXStatement(mStatement);
+    }
+    return wxAttr;
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  @Override
+  public String toString() {
+    return attr.toString();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/WXCustomStyleSpan.java b/android/sdk/src/main/java/org/apache/weex/dom/WXCustomStyleSpan.java
new file mode 100644
index 0000000..f8834d6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/WXCustomStyleSpan.java
@@ -0,0 +1,68 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.dom;
+
+import android.graphics.Typeface;
+import android.text.TextPaint;
+import android.text.style.MetricAffectingSpan;
+import org.apache.weex.utils.TypefaceUtil;
+
+public class WXCustomStyleSpan extends MetricAffectingSpan {
+
+  private final int mStyle;
+  private final int mWeight;
+  private final String mFontFamily;
+
+  public WXCustomStyleSpan(int fontStyle, int fontWeight, String fontFamily) {
+    mStyle = fontStyle;
+    mWeight = fontWeight;
+    mFontFamily = fontFamily;
+  }
+
+  @Override
+  public void updateDrawState(TextPaint ds) {
+    TypefaceUtil.applyFontStyle(ds, mStyle, mWeight, mFontFamily);
+  }
+
+  @Override
+  public void updateMeasureState(TextPaint paint) {
+    TypefaceUtil.applyFontStyle(paint, mStyle, mWeight, mFontFamily);
+  }
+
+  /**
+   * Returns {@link Typeface#NORMAL} or {@link Typeface#ITALIC}.
+   */
+  public int getStyle() {
+    return (mStyle == WXStyle.UNSET ? 0 : mStyle);
+  }
+
+  /**
+   * Returns {@link Typeface#NORMAL} or {@link Typeface#BOLD}.
+   */
+  public int getWeight() {
+    return (mWeight == WXStyle.UNSET ? 0 : mWeight);
+  }
+
+  /**
+   * Returns the font family set for this StyleSpan.
+   */
+  public String getFontFamily() {
+    return mFontFamily;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/WXEvent.java b/android/sdk/src/main/java/org/apache/weex/dom/WXEvent.java
new file mode 100644
index 0000000..71277f1
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/WXEvent.java
@@ -0,0 +1,187 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.dom;
+
+import android.support.v4.util.ArrayMap;
+
+
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.dom.binding.ELUtils;
+import org.apache.weex.dom.binding.JSONUtils;
+
+import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Store value of component event
+ */
+public class WXEvent extends ArrayList<String> implements Serializable, Cloneable {
+
+  private static final long serialVersionUID = -8186587029452440107L;
+
+  /**
+   *  event data format
+   *  {
+   *  type: 'appear',
+   *  params: [
+   *  { '@binding': 'index' },
+   *   'static',
+   *   { '@binding': 'item.name' },
+   *  { '@binding': '$event' }
+   *  ]
+   *  }
+   * */
+  public static final String EVENT_KEY_TYPE = "type";
+  public static final String EVENT_KEY_ARGS = "params";
+
+
+  /**
+   * dynamic binding event args, can be null, only weex use
+   * */
+  private ArrayMap mEventBindingArgs;
+  private ArrayMap<String, List<Object>> mEventBindingArgsValues;
+
+
+  @Override
+  public void clear() {
+    if(mEventBindingArgs != null){
+      mEventBindingArgs.clear();
+    }
+    if(mEventBindingArgsValues != null){
+      mEventBindingArgsValues.clear();
+    }
+    super.clear();
+  }
+
+
+  public boolean remove(String o) {
+    if(mEventBindingArgs != null){
+      mEventBindingArgs.remove(o);
+    }
+    if(mEventBindingArgsValues != null){
+      mEventBindingArgsValues.remove(o);
+    }
+    return super.remove(o);
+  }
+
+  /**
+   * can by null
+   * */
+  public ArrayMap getEventBindingArgs() {
+    return mEventBindingArgs;
+  }
+
+
+  public ArrayMap<String, List<Object>> getEventBindingArgsValues() {
+    return mEventBindingArgsValues;
+  }
+
+
+  public void addEvent(Object event) {
+    if(event instanceof CharSequence){
+      if(JSONUtils.isJSON(event.toString())){
+        addEvent(JSONUtils.toJSON(event.toString()));
+        return;
+      }
+      String eventName = event.toString();
+      if(!contains(eventName)){
+        add(eventName);
+      }
+    }else if(event instanceof JSONObject){
+      JSONObject bindings = (JSONObject) event;
+      addBindingEvent(bindings);
+    }
+  }
+
+
+
+  public static String getEventName(Object event){
+    if(event instanceof CharSequence){
+      return event.toString();
+    }else if(event instanceof JSONObject){
+      JSONObject bindings = (JSONObject) event;
+      String eventName = bindings.getString(WXEvent.EVENT_KEY_TYPE);
+      return  eventName;
+    }
+    if(event == null){
+      return  null;
+    }
+    return  event.toString();
+  }
+
+
+  public void parseStatements() {
+     if(!isEmpty()){
+       for(int i=0; i<size(); i++){
+         String event =  get(i);
+         if(JSONUtils.isJSON(event)){
+           JSONObject object = JSONUtils.toJSON(event);
+           String eventName = addBindingEvent(object);
+           set(i, eventName);
+         }
+       }
+     }
+  }
+
+  private String addBindingEvent(JSONObject bindings){
+    String eventName = bindings.getString(WXEvent.EVENT_KEY_TYPE);
+    Object args = bindings.get(WXEvent.EVENT_KEY_ARGS);
+    if (eventName != null) {
+      addBindingArgsEvent(eventName, args);
+    }
+    return eventName;
+  }
+
+  private void addBindingArgsEvent(String eventName, Object args){
+    if(!contains(eventName)){
+      add(eventName);
+    }
+    if(args != null){
+      if(mEventBindingArgs == null){
+        mEventBindingArgs = new ArrayMap();
+      }
+      mEventBindingArgs.put(eventName, ELUtils.bindingBlock(args));
+    }
+  }
+
+  public void putEventBindingArgsValue(String event, List<Object> value){
+    if(mEventBindingArgsValues == null){
+      mEventBindingArgsValues = new ArrayMap();
+    }
+    if(value == null){
+      mEventBindingArgsValues.remove(event);
+    }else{
+      mEventBindingArgsValues.put(event, value);
+    }
+  }
+
+  @Override
+  public WXEvent clone() {
+    WXEvent event = new WXEvent();
+    event.addAll(this);
+    if(mEventBindingArgs != null) {
+      event.mEventBindingArgs = new ArrayMap(mEventBindingArgs);
+    }
+    event.mEventBindingArgsValues = null; //this should not be clone, it dynamic args
+    return  event;
+  }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/WXImageQuality.java b/android/sdk/src/main/java/org/apache/weex/dom/WXImageQuality.java
new file mode 100644
index 0000000..303ab2a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/WXImageQuality.java
@@ -0,0 +1,32 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.dom;
+
+public enum WXImageQuality {
+
+  ORIGINAL,
+
+  LOW,
+
+  NORMAL,
+
+  HIGH,
+
+  AUTO
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/WXLineHeightSpan.java b/android/sdk/src/main/java/org/apache/weex/dom/WXLineHeightSpan.java
new file mode 100644
index 0000000..8c7d279
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/WXLineHeightSpan.java
@@ -0,0 +1,46 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.dom;
+
+import android.graphics.Paint;
+import android.text.style.LineHeightSpan;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.utils.WXLogUtils;
+
+public class WXLineHeightSpan implements LineHeightSpan{
+
+  private int lineHeight;
+  public WXLineHeightSpan(int lineHeight){
+    this.lineHeight=lineHeight;
+  }
+
+  @Override
+  public void chooseHeight(CharSequence text, int start, int end, int spanstartv, int v, Paint.FontMetricsInt fm) {
+    if(WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("LineHeight", text + " ; start " + start + "; end " + end + "; spanstartv "
+              + spanstartv + "; v " + v + "; fm " + fm);
+    }
+    int halfLeading=(lineHeight-(fm.descent-fm.ascent))/2;
+    fm.top-=halfLeading;
+    fm.bottom+=halfLeading;
+    fm.ascent-=halfLeading;
+    fm.descent+=halfLeading;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/WXStyle.java b/android/sdk/src/main/java/org/apache/weex/dom/WXStyle.java
new file mode 100644
index 0000000..5a5fd38
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/WXStyle.java
@@ -0,0 +1,559 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.dom;
+
+import android.graphics.Typeface;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.support.v4.util.ArrayMap;
+import android.text.Layout;
+import android.text.TextUtils;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.binding.ELUtils;
+import org.apache.weex.ui.component.WXText;
+import org.apache.weex.ui.component.WXTextDecoration;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Store value of component style
+ *
+ */
+public class WXStyle implements Map<String, Object>,Cloneable {
+
+  private static final long serialVersionUID = 611132641365274134L;
+  public static final int UNSET = -1;
+
+  @NonNull
+  private Map<String,Object> mStyles;
+
+  @Nullable
+  private Map<String,Map<String,Object>> mPesudoStyleMap;// clz_group:{styleMap}
+
+  @Nullable
+  private Map<String,Object> mPesudoResetStyleMap;
+
+  /**
+   * dynamic binding attrs, can be null, only weex use
+   * */
+  private ArrayMap<String, Object>  mBindingStyle;
+
+  public WXStyle(){
+    mStyles = new ArrayMap<>();
+  }
+
+  public WXStyle(Map<String, Object> styles){
+    this.mStyles = styles;
+    processPesudoClasses(this.mStyles);
+  }
+
+  public WXStyle(Map<String, Object> mStyles, boolean byPesudo) {
+    this();
+    this.putAll(mStyles, byPesudo);
+  }
+
+  @Nullable
+  public String getBlur() {
+    if(get(Constants.Name.FILTER) == null) {
+      return null;
+    }
+    return get(Constants.Name.FILTER).toString().trim();
+  }
+
+  /*
+   * text-decoration
+   **/
+  public static WXTextDecoration getTextDecoration(Map<String, Object> style) {
+    Object obj;
+    WXTextDecoration ret;
+    if (style == null || (obj = style.get(Constants.Name.TEXT_DECORATION)) == null) {
+      ret = WXTextDecoration.NONE;
+    } else {
+      String textDecoration = obj.toString();
+      switch (textDecoration) {
+        case "underline":
+          ret = WXTextDecoration.UNDERLINE;
+          break;
+        case "line-through":
+          ret = WXTextDecoration.LINETHROUGH;
+          break;
+        case "none":
+          ret = WXTextDecoration.NONE;
+          break;
+        default:
+          ret = WXTextDecoration.INVALID;
+          break;
+      }
+    }
+    return ret;
+  }
+
+  public static String getTextColor(Map<String, Object> style) {
+    if (style == null) {
+      return "";
+    }
+    Object temp = style.get(Constants.Name.COLOR);
+    return temp == null ? "" : temp.toString();
+  }
+
+  public static int getFontWeight(Map<String, Object> style) {
+    int typeface = android.graphics.Typeface.NORMAL;
+    if (style != null) {
+      Object temp = style.get(Constants.Name.FONT_WEIGHT);
+      if (temp != null) {
+        String fontWeight = temp.toString();
+        switch (fontWeight){
+          case "600":
+          case "700":
+          case "800":
+          case "900":
+          case Constants.Value.BOLD:
+            typeface=Typeface.BOLD;
+            break;
+        }
+      }
+    }
+    return typeface;
+  }
+
+  public static int getFontStyle(Map<String, Object> style) {
+    int typeface = android.graphics.Typeface.NORMAL;
+    if (style == null) {
+      return typeface;
+    }
+    Object temp = style.get(Constants.Name.FONT_STYLE);
+    if (temp == null) {
+      return typeface;
+    }
+    String fontWeight = temp.toString();
+    if (fontWeight.equals(Constants.Value.ITALIC)) {
+      typeface = android.graphics.Typeface.ITALIC;
+    }
+    return typeface;
+  }
+
+  public static int getFontSize(Map<String, Object> style,int viewPortW) {
+    if (style == null) {
+      return (int) WXViewUtils.getRealPxByWidth(WXText.sDEFAULT_SIZE,viewPortW);
+    }
+    int fontSize = WXUtils.getInt(style.get(Constants.Name.FONT_SIZE));
+    if (fontSize <= 0) {
+      fontSize = WXText.sDEFAULT_SIZE;
+    }
+    return (int) WXViewUtils.getRealPxByWidth(fontSize,viewPortW);
+  }
+
+  public static String getFontFamily(Map<String, Object> style) {
+    String fontFamily = null;
+    if (style != null) {
+      Object temp;
+      temp = style.get(Constants.Name.FONT_FAMILY);
+      if (temp != null) {
+        fontFamily = temp.toString();
+      }
+    }
+    return fontFamily;
+  }
+
+  public static Layout.Alignment getTextAlignment(Map<String, Object> style){
+    return getTextAlignment(style, false);
+  }
+
+  public static Layout.Alignment getTextAlignment(Map<String, Object> style, boolean isRTL){
+    Layout.Alignment alignment= isRTL ? Layout.Alignment.ALIGN_OPPOSITE : Layout.Alignment.ALIGN_NORMAL;
+    String textAlign= (String) style.get(Constants.Name.TEXT_ALIGN);
+    if(TextUtils.equals(Constants.Value.LEFT,textAlign)){
+      alignment= Layout.Alignment.ALIGN_NORMAL;
+    }
+    else if(TextUtils.equals(Constants.Value.CENTER,textAlign)){
+      alignment= Layout.Alignment.ALIGN_CENTER;
+    }
+    else if(TextUtils.equals(Constants.Value.RIGHT,textAlign)){
+      alignment= Layout.Alignment.ALIGN_OPPOSITE;
+    }
+    return alignment;
+  }
+
+  public static TextUtils.TruncateAt getTextOverflow(Map<String, Object> style){
+    TextUtils.TruncateAt truncateAt=null;
+    String ellipse = (String) style.get(Constants.Name.TEXT_OVERFLOW);
+    if(TextUtils.equals(Constants.Name.ELLIPSIS,ellipse)){
+      truncateAt = TextUtils.TruncateAt.END;
+    }
+    return truncateAt;
+  }
+
+  public static int getLines(Map<String, Object> style) {
+    return WXUtils.getInt(style.get(Constants.Name.LINES));
+  }
+
+  public static int getLineHeight(Map<String, Object> style,int viewPortW){
+    if (style == null) {
+      return UNSET;
+    }
+    int lineHeight = WXUtils.getInt(style.get(Constants.Name.LINE_HEIGHT));
+    if (lineHeight <= 0) {
+      lineHeight = UNSET;
+      return lineHeight;
+    }
+    return (int) WXViewUtils.getRealPxByWidth(lineHeight,viewPortW);
+  }
+
+  public float getBorderRadius() {
+    float temp = WXUtils.getFloat(get(Constants.Name.BORDER_RADIUS));
+    if (WXUtils.isUndefined(temp)) {
+      return Float.NaN;
+    }
+    return temp;
+  }
+
+  public String getBorderColor() {
+    Object color = get(Constants.Name.BORDER_COLOR);
+    return color == null ? null : color.toString();
+  }
+
+  public String getBorderStyle() {
+    Object borderStyle = get(Constants.Name.BORDER_STYLE);
+    return borderStyle == null ? null : borderStyle.toString();
+  }
+
+  public boolean isSticky() {
+    Object position = get(Constants.Name.POSITION);
+    if (position == null) {
+      return false;
+    }
+    return position.toString().equals(Constants.Value.STICKY);
+  }
+
+  public boolean isFixed() {
+    Object position = get(Constants.Name.POSITION);
+    if (position == null) {
+      return false;
+    }
+    return position.toString().equals(Constants.Value.FIXED);
+  }
+
+  public float getLeft() {
+    float temp = WXUtils.getFloat(get(Constants.Name.LEFT));
+    if (WXUtils.isUndefined(temp)) {
+      return Float.NaN;
+    }
+    return temp;
+  }
+
+  public float getRight() {
+    float temp = WXUtils.getFloat(get(Constants.Name.RIGHT));
+    if (WXUtils.isUndefined(temp)) {
+      return Float.NaN;
+    }
+    return temp;
+  }
+
+  public float getTop() {
+    float temp = WXUtils.getFloat(get(Constants.Name.TOP));
+    if (WXUtils.isUndefined(temp)) {
+      return Float.NaN;
+    }
+    return temp;
+  }
+
+  public float getBottom() {
+    float temp = WXUtils.getFloat(get(Constants.Name.BOTTOM));
+    if (WXUtils.isUndefined(temp)) {
+      return Float.NaN;
+    }
+    return temp;
+  }
+
+  /*
+   * others
+   **/
+  public String getBackgroundColor() {
+    Object temp = get(Constants.Name.BACKGROUND_COLOR);
+    return temp == null ? "" : temp.toString();
+  }
+
+  public int getTimeFontSize() {
+    int fontSize = WXUtils.getInt(get("timeFontSize"));
+    if (fontSize <= 0) {
+      fontSize = WXText.sDEFAULT_SIZE;
+    }
+    return fontSize;
+  }
+
+  public float getOpacity() {
+    Object object = get(Constants.Name.OPACITY);
+    float opacity = 1;
+    if (object == null) {
+      return opacity;
+    }
+    return WXUtils.getFloat(object);
+  }
+
+  public String getOverflow() {
+    Object obj = get(Constants.Name.OVERFLOW);
+    return obj == null ? Constants.Value.VISIBLE : obj.toString();
+  }
+
+  @Override
+  public boolean equals(Object o) {
+    return mStyles.equals(o);
+  }
+
+  @Override
+  public int hashCode() {
+    return mStyles.hashCode();
+  }
+
+  @Override
+  public void clear() {
+    mStyles.clear();
+  }
+
+  @Override
+  public boolean containsKey(Object key) {
+    return mStyles.containsKey(key);
+  }
+
+  @Override
+  public boolean containsValue(Object value) {
+    return mStyles.containsValue(value);
+  }
+
+  @NonNull
+  @Override
+  public Set<Entry<String, Object>> entrySet() {
+    return mStyles.entrySet();
+  }
+
+  @Override
+  public Object get(Object key) {
+    return mStyles.get(key);
+  }
+
+  @Override
+  public boolean isEmpty() {
+    return mStyles.isEmpty();
+  }
+
+  @NonNull
+  @Override
+  public Set<String> keySet() {
+    return mStyles.keySet();
+  }
+
+  @Override
+  public Object put(String key, Object value) {
+    if(addBindingStyleIfStatement(key, value)){
+      return null;
+    }
+    return mStyles.put(key,value);
+  }
+
+  @Override
+  public void putAll(Map<? extends String, ?> map) {
+    this.mStyles.putAll(map);
+  }
+
+  /**
+   * Used by Dom Thread， new and update styles.
+   * @param map
+   * @param byPesudo
+   */
+  public void putAll(Map<? extends String, ?> map, boolean byPesudo) {
+    this.mStyles.putAll(map);
+    if (!byPesudo) {
+      processPesudoClasses(map);
+    }
+  }
+
+  public void updateStyle(Map<? extends String, ?> map, boolean byPesudo){
+      parseBindingStylesStatements(map);
+      putAll(map, byPesudo);
+  }
+
+
+  public Map<String, Object> getPesudoResetStyles() {
+    if(mPesudoResetStyleMap == null){
+      mPesudoResetStyleMap = new ArrayMap<>();
+    }
+    return mPesudoResetStyleMap;
+  }
+
+  public Map<String, Map<String, Object>> getPesudoStyles() {
+    if(mPesudoStyleMap == null){
+      mPesudoStyleMap = new ArrayMap<>();
+    }
+    return mPesudoStyleMap;
+  }
+
+  <T extends String, V> void processPesudoClasses(Map<T, V> styles) {
+    Map<String, Object> tempMap = null;
+    for(Map.Entry<T, V> entry:styles.entrySet()){
+      //Key Format: "style-prop:pesudo_clz1:pesudo_clz2"
+      String key = entry.getKey();
+      int i;
+      if ((i = key.indexOf(":")) > 0) {
+        initPesudoMapsIfNeed(styles);
+        String clzName = key.substring(i);
+        if (clzName.equals(Constants.PSEUDO.ENABLED)) {
+          //enabled, use as regular style
+          String styleKey = key.substring(0, i);
+          if(tempMap == null){
+            tempMap = new ArrayMap<>();
+          }
+          tempMap.put(styleKey, entry.getValue());
+          mPesudoResetStyleMap.put(styleKey, entry.getValue());
+          continue;
+        } else {
+          clzName = clzName.replace(Constants.PSEUDO.ENABLED, "");//remove ':enabled' which is ignored
+        }
+
+        Map<String, Object> stylesMap = mPesudoStyleMap.get(clzName);
+        if (stylesMap == null) {
+          stylesMap = new ArrayMap<>();
+          mPesudoStyleMap.put(clzName, stylesMap);
+        }
+        stylesMap.put(key.substring(0, i), entry.getValue());
+      }
+    }
+
+    if (tempMap != null && !tempMap.isEmpty()) {
+      this.mStyles.putAll(tempMap);
+    }
+  }
+
+  @Override
+  public Object remove(Object key) {
+    return mStyles.remove(key);
+  }
+
+  @Override
+  public int size() {
+    return mStyles.size();
+  }
+
+  @NonNull
+  @Override
+  public Collection<Object> values() {
+    return mStyles.values();
+  }
+
+
+
+  private void initPesudoMapsIfNeed(Map<? extends String, ?> styles){
+    if(mPesudoStyleMap == null){
+      mPesudoStyleMap = new ArrayMap<>();
+    }
+    if(mPesudoResetStyleMap == null){
+      mPesudoResetStyleMap = new ArrayMap<>();
+    }
+    if(mPesudoResetStyleMap.isEmpty()){
+      mPesudoResetStyleMap.putAll(styles);
+    }
+  }
+
+
+
+  public void  parseStatements(){
+    if(this.mStyles != null){
+      this.mStyles = parseBindingStylesStatements(this.mStyles);
+    }
+  }
+
+  /**
+   * filter dynamic state ment
+   * */
+  private Map<String, Object> parseBindingStylesStatements(Map styles) {
+    if(styles == null || styles.size() == 0){
+      return styles;
+    }
+    Set<Map.Entry<String,Object>> entries = styles.entrySet();
+    Iterator<Entry<String,Object>> it =  entries.iterator();
+    while (it.hasNext()){
+      Map.Entry<String,Object> entry = it.next();
+      if(addBindingStyleIfStatement(entry.getKey(), entry.getValue())){
+        if(mPesudoStyleMap != null){
+          mPesudoStyleMap.remove(entry.getKey());
+        }
+        if(mPesudoResetStyleMap != null){
+          mPesudoResetStyleMap.remove(entry.getKey());
+        }
+        it.remove();
+      }
+    }
+    return styles;
+  }
+
+  /**
+   * filter dynamic attrs and statements
+   * */
+  private boolean addBindingStyleIfStatement(String key, Object value) {
+    if(ELUtils.isBinding(value)){
+      if(mBindingStyle == null){
+        mBindingStyle = new ArrayMap<String, Object>();
+      }
+      value = ELUtils.bindingBlock(value);
+      mBindingStyle.put(key, value);
+      return  true;
+    }
+    return  false;
+  }
+
+  public ArrayMap<String, Object> getBindingStyle() {
+    return mBindingStyle;
+  }
+
+  @Override
+  public WXStyle clone(){
+    WXStyle style = new WXStyle();
+    style.mStyles.putAll(this.mStyles);
+    if(mBindingStyle != null){
+      style.mBindingStyle = new ArrayMap<>(mBindingStyle);
+    }
+    if(mPesudoStyleMap != null) {
+      style.mPesudoStyleMap = new ArrayMap<>();
+      for (Entry<String, Map<String, Object>> entry : this.mPesudoStyleMap.entrySet()) {
+        Map<String, Object> valueClone = new ArrayMap<>();
+        valueClone.putAll(entry.getValue());
+        style.mPesudoStyleMap.put(entry.getKey(), valueClone);
+      }
+    }
+
+    if(mPesudoResetStyleMap!=null) {
+      style.mPesudoResetStyleMap = new ArrayMap<>();
+      style.mPesudoResetStyleMap.putAll(this.mPesudoResetStyleMap);
+    }
+
+
+    return style;
+  }
+
+  @Override
+  @RestrictTo(Scope.LIBRARY)
+  public String toString() {
+    return mStyles.toString();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/binding/ELUtils.java b/android/sdk/src/main/java/org/apache/weex/dom/binding/ELUtils.java
new file mode 100644
index 0000000..482e8c8
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/binding/ELUtils.java
@@ -0,0 +1,127 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.dom.binding;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.el.parse.Parser;
+import org.apache.weex.el.parse.Token;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.Set;
+
+/**
+ * util's for binding and statment
+ * Created by jianbai.gbj on 2017/8/17.
+ */
+public class ELUtils {
+
+    public static final String BINDING = "@binding";
+    /**
+     * sub template
+     * */
+    public static final String IS_COMPONENT_ROOT = "@isComponentRoot";
+
+
+    public static final String COMPONENT_PROPS = "@componentProps";
+
+    public static final  String[] EXCLUDES_BINDING = {"clickEventParams"};
+
+    /**
+     * @param value check object is binding expression
+     * */
+    public static boolean isBinding(Object value){
+        if(value instanceof JSONObject){
+            JSONObject  object = (JSONObject) value;
+            if(object.containsKey(BINDING)){
+                return  true;
+            }
+        }else if(value instanceof JSONArray){
+            JSONArray array = (JSONArray) value;
+            for(int i=0; i<array.size(); i++){
+                if(isBinding(array.get(i))){
+                    return  true;
+                }
+            }
+        }else if(value instanceof String){
+            return ((String) value).indexOf(BINDING) >= 0;
+        }
+        return  false;
+    }
+
+    /**
+     * parse binding code to block, enable fast execute
+     * */
+    public static Object bindingBlock(Object value){
+        if(value instanceof JSONObject){
+            JSONObject  object = (JSONObject) value;
+            if(object.containsKey(BINDING)){
+                Object binding = object.get(BINDING);
+                if(!(binding instanceof Token)){
+                    object.put(BINDING, Parser.parse(binding.toString()));
+                }
+            }
+            Set<String> keys = object.keySet();
+            for(Object propsKey : keys){
+                if(object.get(propsKey) instanceof  JSONObject
+                        && ((JSONObject)object.get(propsKey)).containsKey(BINDING)){
+                    JSONObject propsValue = (JSONObject) object.get(propsKey);
+                    Object binding = propsValue.get(BINDING);
+                    if(!(binding instanceof Token)){
+                        propsValue.put(BINDING, Parser.parse(binding.toString()));
+                    }
+                }
+            }
+        }else if(value instanceof JSONArray){
+            JSONArray array = (JSONArray) value;
+            for(int i=0; i<array.size(); i++){
+                bindingBlock(array.get(i));
+            }
+        }else if(value instanceof String){
+            String json = value.toString();
+            if(json.startsWith("{")){
+                return bindingBlock(JSON.parseObject(json));
+            }else if(json.startsWith("[")){
+                return bindingBlock(JSON.parseArray(json));
+            }
+        }
+        return  value;
+    }
+
+    public static Object vforBlock(Object vfor){
+        if(vfor instanceof  JSONObject){
+            if(((JSONObject) vfor).containsKey(WXStatement.WX_FOR_LIST)){
+                Object list = ((JSONObject) vfor).get(WXStatement.WX_FOR_LIST);
+                if(!(list instanceof Token)){
+                    ((JSONObject) vfor).put(WXStatement.WX_FOR_LIST, Parser.parse(list.toString()));
+                }
+            }
+        }else if(vfor instanceof  String){
+            return vforBlock(JSONObject.parseObject(vfor.toString()));
+        }else{
+            if(WXEnvironment.isApkDebugable()){
+                WXLogUtils.e("weex", "weex vfor is illegal " + vfor);
+            }
+        }
+        return vfor;
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/binding/JSONUtils.java b/android/sdk/src/main/java/org/apache/weex/dom/binding/JSONUtils.java
new file mode 100644
index 0000000..8d54f14
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/binding/JSONUtils.java
@@ -0,0 +1,51 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.dom.binding;
+
+import com.alibaba.fastjson.JSONObject;
+
+/**
+ * Created by furture on 2018/5/8.
+ */
+
+public class JSONUtils {
+
+
+    public static boolean isJSON(Object json){
+        if(json instanceof JSONObject){
+            return true;
+        }
+        if(json instanceof String){
+            return ((String) json).startsWith("{");
+        }
+        return false;
+    }
+
+    public static JSONObject toJSON(Object json){
+        if(json instanceof JSONObject){
+            return (JSONObject) json;
+        }
+        return JSONObject.parseObject(json.toString());
+    }
+
+
+    public static boolean isJSON(String json){
+        return json.startsWith("{");
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/binding/WXStatement.java b/android/sdk/src/main/java/org/apache/weex/dom/binding/WXStatement.java
new file mode 100644
index 0000000..e58a583
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/binding/WXStatement.java
@@ -0,0 +1,83 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.dom.binding;
+
+import android.support.v4.util.ArrayMap;
+import android.support.v4.util.SimpleArrayMap;
+
+/**
+ * Created by furture on 2017/8/17.
+ * statement expression for template list, like v-if v-for
+ */
+public class WXStatement extends ArrayMap<String, Object> implements  Cloneable  {
+
+    /**
+     * v-for statement, like
+     * <code>
+     *     <div v-for="(item, i) in dataset.panels">
+     *     <text>{{i}}: {{item.name}}</text>
+     *     </div>
+     * </code>
+     * json command:
+     * <code>
+     *      attr: {
+     *          '[[repeat]]': {
+     *          '@expression': 'dataList',
+     *          '@index': 'index',
+     *          '@alias': 'item'
+     *         }
+     *      }
+     * </code>
+     * */
+    public static final String WX_FOR = "[[repeat]]";
+    public static final String WX_FOR_INDEX = "@index";
+    public static final String WX_FOR_ITEM = "@alias";
+    public static final String WX_FOR_LIST = "@expression";
+
+
+    /**
+     * v-if statement, like:
+     * <code>
+     *   <p v-if="male">Male</p>
+     * </code>
+     * json command
+     * attr: {
+     *      '[[match]]': 'condition'
+     *    }
+     * */
+    public static final String WX_IF = "[[match]]";
+
+
+    /**
+     * once statement
+     * */
+    public static final  String WX_ONCE = "[[once]]";
+
+    public WXStatement() {
+    }
+
+    public WXStatement(SimpleArrayMap map) {
+        super(map);
+    }
+
+    @Override
+    protected WXStatement clone(){
+        return new WXStatement(this);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/dom/transition/WXTransition.java b/android/sdk/src/main/java/org/apache/weex/dom/transition/WXTransition.java
new file mode 100644
index 0000000..577b2e0
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/dom/transition/WXTransition.java
@@ -0,0 +1,754 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.dom.transition;
+
+import android.animation.Animator;
+import android.animation.AnimatorListenerAdapter;
+import android.animation.ArgbEvaluator;
+import android.animation.ObjectAnimator;
+import android.animation.PropertyValuesHolder;
+import android.animation.ValueAnimator;
+import android.graphics.drawable.ColorDrawable;
+import android.os.Handler;
+import android.support.v4.util.ArrayMap;
+import android.support.v4.view.animation.PathInterpolatorCompat;
+import android.text.TextUtils;
+import android.util.Property;
+import android.view.View;
+import android.view.animation.Interpolator;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.ui.animation.BackgroundColorProperty;
+import org.apache.weex.ui.animation.TransformParser;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.SingleFunctionParser;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.ArrayList;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.atomic.AtomicInteger;
+import java.util.regex.Pattern;
+import org.apache.weex.common.Constants.TimeFunction;
+
+/**
+ *   transition on dom thread
+ *   transition-property: height;
+ *   transition-duration: .3s;
+ *   transition-delay: .05s;
+ *   transition-timing-function: ease-in-out;
+ *
+ *   Created by furture on 2017/10/18.
+ */
+public class WXTransition {
+
+    public static final  String TRANSITION_PROPERTY = "transitionProperty";
+    public static final  String TRANSITION_DURATION = "transitionDuration";
+    public static final  String TRANSITION_DELAY = "transitionDelay";
+    public static final  String TRANSITION_TIMING_FUNCTION = "transitionTimingFunction";
+
+    public static final  Pattern PROPERTY_SPLIT_PATTERN = Pattern.compile("\\||,");
+
+
+    /**
+     * layout animation property
+     * */
+    private static final Set<String> LAYOUT_PROPERTIES = new HashSet<>();
+    static {
+        LAYOUT_PROPERTIES.add(Constants.Name.WIDTH);
+        LAYOUT_PROPERTIES.add(Constants.Name.HEIGHT);
+        LAYOUT_PROPERTIES.add(Constants.Name.MARGIN_TOP);
+        LAYOUT_PROPERTIES.add(Constants.Name.MARGIN_BOTTOM);
+        LAYOUT_PROPERTIES.add(Constants.Name.MARGIN_LEFT);
+        LAYOUT_PROPERTIES.add(Constants.Name.MARGIN_RIGHT);
+        LAYOUT_PROPERTIES.add(Constants.Name.LEFT);
+        LAYOUT_PROPERTIES.add(Constants.Name.RIGHT);
+        LAYOUT_PROPERTIES.add(Constants.Name.TOP);
+        LAYOUT_PROPERTIES.add(Constants.Name.BOTTOM);
+        LAYOUT_PROPERTIES.add(Constants.Name.PADDING_LEFT);
+        LAYOUT_PROPERTIES.add(Constants.Name.PADDING_RIGHT);
+        LAYOUT_PROPERTIES.add(Constants.Name.PADDING_TOP);
+        LAYOUT_PROPERTIES.add(Constants.Name.PADDING_BOTTOM);
+    }
+
+    /**
+     * transform animation property, use android system animaton ability
+     * */
+    private static final Set<String> TRANSFORM_PROPERTIES = new HashSet<>();
+    static {
+        TRANSFORM_PROPERTIES.add(Constants.Name.OPACITY);
+        TRANSFORM_PROPERTIES.add(Constants.Name.BACKGROUND_COLOR);
+        TRANSFORM_PROPERTIES.add(Constants.Name.TRANSFORM);
+    }
+
+    private List<String> properties;
+    private Interpolator  interpolator;
+    private long  duration;
+    private long delay;
+    private WXComponent mWXComponent;
+    private Handler handler;
+    private ValueAnimator layoutValueAnimator;
+    private Map<String, Object> layoutPendingUpdates;
+    private ObjectAnimator transformAnimator;
+    private Map<String, Object> transformPendingUpdates;
+    private Runnable transitionEndEvent;
+    private Map<String, Object> targetStyles;
+    private Runnable animationRunnable;
+
+    private Runnable transformAnimationRunnable;
+    private volatile AtomicInteger lockToken = new AtomicInteger(0);
+
+
+    public WXTransition() {
+        this.properties = new ArrayList<>(4);
+        this.handler = new Handler();
+        this.layoutPendingUpdates = new ArrayMap<>();
+        this.transformPendingUpdates = new ArrayMap<>();
+        this.targetStyles = new ArrayMap<>();
+    }
+
+    /**
+     * create transition from map styles if style contains transitionProperty
+     * */
+    public static WXTransition fromMap(Map<String, Object> style, WXComponent component){
+        if(style.get(TRANSITION_PROPERTY) == null){
+            return  null;
+        }
+        String propertyString = WXUtils.getString(style.get(TRANSITION_PROPERTY), null);
+        if(propertyString == null){
+            return null;
+        }
+        WXTransition transition  = new WXTransition();
+        updateTransitionProperties(transition, propertyString);
+        if(transition.properties.isEmpty()){
+            return  null;
+        }
+        transition.duration = parseTimeMillis(style, TRANSITION_DURATION, 0);
+        transition.delay =  parseTimeMillis(style, TRANSITION_DELAY, 0);
+        transition.interpolator = createTimeInterpolator(WXUtils.getString(style.get(TRANSITION_TIMING_FUNCTION), null));
+        transition.mWXComponent = component;
+        return  transition;
+    }
+
+    /**
+     * check updates has transition property
+     * */
+    public boolean hasTransitionProperty(Map<String, Object> styles){
+        for(String property : properties){
+            if(styles.containsKey(property)){
+                return  true;
+            }
+        }
+        return false;
+    }
+
+    public void updateTranstionParams(Map<String, Object> updates){
+        if(updates.containsKey(TRANSITION_DELAY)){
+            mWXComponent.getStyles().put(TRANSITION_DELAY, updates.remove(TRANSITION_DELAY));
+            this.delay = parseTimeMillis(mWXComponent.getStyles(), TRANSITION_DELAY, 0);
+        }
+
+        if(updates.containsKey(TRANSITION_TIMING_FUNCTION) && updates.get(TRANSITION_TIMING_FUNCTION) != null){
+            mWXComponent.getStyles().put(TRANSITION_TIMING_FUNCTION, updates.remove(TRANSITION_TIMING_FUNCTION));
+            this.interpolator = createTimeInterpolator(mWXComponent.getStyles().get(TRANSITION_TIMING_FUNCTION).toString());
+        }
+
+        if(updates.containsKey(TRANSITION_DURATION)){
+            mWXComponent.getStyles().put(TRANSITION_DURATION, updates.remove(TRANSITION_DURATION));
+            this.duration = parseTimeMillis(mWXComponent.getStyles(), TRANSITION_DURATION, 0);
+        }
+
+        if(updates.containsKey(TRANSITION_PROPERTY)){
+            mWXComponent.getStyles().put(TRANSITION_PROPERTY, updates.remove(TRANSITION_PROPERTY));
+            updateTransitionProperties(this, WXUtils.getString(mWXComponent.getStyles().get(TRANSITION_PROPERTY), null));
+        }
+    }
+
+    /**
+     * start transition animation, updates maybe split two different updates,
+     * because javascript will send multi update on same transition, we assume that updates in 8ms is one transition
+     * */
+    public void  startTransition(Map<String, Object> updates){
+        synchronized (lockToken){
+            final View taregtView = getTargetView();
+            if(taregtView == null){
+                return;
+            }
+            final int token = lockToken.incrementAndGet();
+            for(String property : properties){
+                if(updates.containsKey(property)){
+                    Object targetValue = updates.remove(property);
+                    if(LAYOUT_PROPERTIES.contains(property)) {
+                        layoutPendingUpdates.put(property, targetValue);
+                    }else if(TRANSFORM_PROPERTIES.contains(property)){
+                        transformPendingUpdates.put(property, targetValue);
+                    }
+                }
+            }
+
+            int delay = WXUtils.getNumberInt(mWXComponent.getAttrs().get("actionDelay"), 16);
+            if(delay > duration){
+                delay = (int) duration;
+            }
+            if(animationRunnable != null) {
+                handler.removeCallbacks(animationRunnable);
+            }
+            animationRunnable = new Runnable() {
+                @Override
+                public void run() {
+                    if(token == lockToken.get()) {
+                        doTransitionAnimation(token);
+                    }
+                    animationRunnable = null;
+                }
+            };
+            if(delay > 0){
+                handler.postDelayed(animationRunnable, delay);
+            }else{
+                animationRunnable.run();
+            }
+        }
+    }
+
+    /**
+     * doTransitionAnimation include transform and layout animation.
+     * 1. put pre transition updates from target style to dom style
+     * 2. do transform animation and layout animation
+     * */
+    private void  doTransitionAnimation(final  int token){
+        final View taregtView = getTargetView();
+        if(taregtView == null){
+            return;
+        }
+        if(targetStyles.size() > 0){
+            for(String property : properties){
+                if(!(LAYOUT_PROPERTIES.contains(property) || TRANSFORM_PROPERTIES.contains(property))){
+                    continue;
+                }
+                if(layoutPendingUpdates.containsKey(property)){
+                    continue;
+                }
+                if(transformPendingUpdates.containsKey(property)){
+                    continue;
+                }
+                synchronized (targetStyles){
+                    if(targetStyles.containsKey(property)){
+                        //reset pre transition style
+                        Object targetValue = targetStyles.remove(property);
+                        mWXComponent.getStyles().put(property, targetValue);
+//                        domObject.getStyles().put(property, targetValue);
+//                        WXComponent component = getComponent();
+//                        if(component != null && component.getDomObject() != null){
+//                            component.getDomObject().getStyles().put(property, targetValue);
+//                        }
+                    }
+                }
+            }
+        }
+
+
+
+        if(transitionEndEvent != null){
+            taregtView.removeCallbacks(transitionEndEvent);
+        }
+        if(transitionEndEvent == null && duration > Float.MIN_NORMAL){
+            transitionEndEvent = new Runnable(){
+                @Override
+                public void run() {
+                    transitionEndEvent = null;
+                    if(duration < Float.MIN_NORMAL){
+                        return;
+                    }
+                    if(mWXComponent != null && mWXComponent.getEvents().contains(Constants.Event.ON_TRANSITION_END)){
+                        mWXComponent.fireEvent(Constants.Event.ON_TRANSITION_END);
+                    }
+                }
+            };
+        }
+        if(transformAnimationRunnable != null) {
+            taregtView.removeCallbacks(transformAnimationRunnable);
+        }
+        transformAnimationRunnable = new Runnable() {
+            @Override
+            public void run() {
+                synchronized (lockToken) {
+                    if(token == lockToken.get()) {
+                        doPendingTransformAnimation(token);
+                    }
+                }
+            }
+        };
+        taregtView.post(transformAnimationRunnable);
+        doPendingLayoutAnimation();
+    }
+
+
+    /**
+     *  transform, opacity, backgroundcolor which not effect layout use android system animation in main thread.
+     * */
+    private void doPendingTransformAnimation(int token) {
+        if(transformAnimator != null){
+            transformAnimator.cancel();
+            transformAnimator = null;
+        }
+        if(transformPendingUpdates.size() == 0){
+            return;
+        }
+        final View taregtView = getTargetView();
+        if(taregtView == null){
+            return;
+        }
+        List<PropertyValuesHolder> holders = new ArrayList<>(8);
+        String transform  = WXUtils.getString(transformPendingUpdates.remove(Constants.Name.TRANSFORM), null);
+        if(!TextUtils.isEmpty(transform)){
+            Map<Property<View,Float>, Float>  properties = TransformParser
+                .parseTransForm(mWXComponent.getInstanceId(), transform, (int)mWXComponent.getLayoutWidth(), (int)mWXComponent.getLayoutHeight(), mWXComponent.getViewPortWidth());
+            PropertyValuesHolder[]  transformHolders = TransformParser.toHolders(properties);
+            for(PropertyValuesHolder holder : transformHolders){
+                holders.add(holder);
+            }
+            synchronized (targetStyles) {
+                targetStyles.put(Constants.Name.TRANSFORM, transform);
+            }
+        }
+
+        for(String property : properties){
+            if(!TRANSFORM_PROPERTIES.contains(property)){
+                continue;
+            }
+            if(!transformPendingUpdates.containsKey(property)){
+                continue;
+            }
+            Object value = transformPendingUpdates.remove(property);
+            synchronized (targetStyles) {
+                targetStyles.put(property, value);
+            }
+            switch (property){
+                case Constants.Name.OPACITY:{
+                    holders.add(PropertyValuesHolder.ofFloat(View.ALPHA, taregtView.getAlpha(), WXUtils.getFloat(value, 1.0f)));
+                    taregtView.setLayerType(View.LAYER_TYPE_SOFTWARE, null); //hardware or none has bug on some platform
+                }
+                break;
+                case Constants.Name.BACKGROUND_COLOR:{
+                    int fromColor = WXResourceUtils.getColor(WXUtils.getString(mWXComponent.getStyles().getBackgroundColor(), null), 0);
+                    int toColor = WXResourceUtils.getColor(WXUtils.getString(value, null), 0);
+                    if(WXViewUtils.getBorderDrawable(taregtView) != null){
+                        fromColor = WXViewUtils.getBorderDrawable(taregtView).getColor();
+                    }else if (taregtView.getBackground() instanceof ColorDrawable) {
+                        fromColor = ((ColorDrawable) taregtView.getBackground()).getColor();
+                    }
+                    holders.add(PropertyValuesHolder.ofObject(new BackgroundColorProperty(), new ArgbEvaluator(), fromColor,toColor));
+                }
+                break;
+                default:break;
+            }
+        }
+
+        if(token == lockToken.get()) {
+            transformPendingUpdates.clear();
+        }
+        transformAnimator =  ObjectAnimator.ofPropertyValuesHolder(taregtView, holders.toArray(new PropertyValuesHolder[holders.size()]));
+        transformAnimator.setDuration((long) duration);
+        if((long) delay > 0) {
+            transformAnimator.setStartDelay((long) delay);
+        }
+        if(interpolator != null) {
+            transformAnimator.setInterpolator(interpolator);
+        }
+        transformAnimator.addListener(new AnimatorListenerAdapter() {
+            boolean  hasCancel = false;
+            @Override
+            public void onAnimationCancel(Animator animation) {
+                super.onAnimationCancel(animation);
+                hasCancel = true;
+            }
+
+            @Override
+            public void onAnimationEnd(Animator animation) {
+                if(hasCancel){
+                    return;
+                }
+                super.onAnimationEnd(animation);
+                WXTransition.this.onTransitionAnimationEnd();
+            }
+        });
+        transformAnimator.start();
+    }
+
+
+    public void doPendingLayoutAnimation(){
+        if(layoutValueAnimator != null){
+            layoutValueAnimator.cancel();
+            layoutValueAnimator = null;
+        }
+        if(layoutPendingUpdates.size() == 0){
+            return;
+        }
+        PropertyValuesHolder[] holders = new PropertyValuesHolder[layoutPendingUpdates.size()];
+        int index = 0;
+        for(String property : properties){
+            if(!LAYOUT_PROPERTIES.contains(property)){
+                continue;
+            }
+            if(layoutPendingUpdates.containsKey(property)){
+                Object targetValue = layoutPendingUpdates.remove(property);
+                synchronized (targetStyles) {
+                    targetStyles.put(property, targetValue);
+                }
+                holders[index] = createLayoutPropertyValueHolder(property, targetValue);
+                index++;
+            }
+        }
+        layoutPendingUpdates.clear();
+        doLayoutPropertyValuesHolderAnimation(holders);
+    }
+
+
+    private PropertyValuesHolder createLayoutPropertyValueHolder(String property, Object value){
+        PropertyValuesHolder holder = null;
+        switch (property){
+            case Constants.Name.WIDTH:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.WIDTH, mWXComponent.getLayoutWidth(),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloat(value, 0.0f), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.HEIGHT:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.HEIGHT, mWXComponent.getLayoutHeight(),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloat(value, 0.0f), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.MARGIN_TOP:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.MARGIN_TOP,  mWXComponent.getMargin().get(
+                    CSSShorthand.EDGE.TOP),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.MARGIN_LEFT:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.MARGIN_LEFT,  mWXComponent.getMargin().get(CSSShorthand.EDGE.LEFT),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.MARGIN_RIGHT:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.MARGIN_RIGHT,  mWXComponent.getMargin().get(CSSShorthand.EDGE.RIGHT),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.MARGIN_BOTTOM:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.MARGIN_BOTTOM,  mWXComponent.getMargin().get(CSSShorthand.EDGE.BOTTOM),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.LEFT:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.LEFT,  mWXComponent.getLayoutPosition().getLeft(),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.RIGHT:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.RIGHT,  mWXComponent.getLayoutPosition().getRight(),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.BOTTOM:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.BOTTOM,  mWXComponent.getLayoutPosition().getBottom(),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.TOP:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.TOP,  mWXComponent.getLayoutPosition().getTop(),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.PADDING_TOP:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.PADDING_TOP,  mWXComponent.getPadding().get(CSSShorthand.EDGE.TOP),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.PADDING_BOTTOM:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.PADDING_BOTTOM,  mWXComponent.getPadding().get(CSSShorthand.EDGE.BOTTOM),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.PADDING_LEFT:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.PADDING_LEFT,  mWXComponent.getPadding().get(CSSShorthand.EDGE.LEFT),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            case Constants.Name.PADDING_RIGHT:{
+                holder = PropertyValuesHolder.ofFloat(Constants.Name.PADDING_RIGHT,  mWXComponent.getPadding().get(CSSShorthand.EDGE.RIGHT),
+                        WXViewUtils.getRealPxByWidth(WXUtils.getFloatByViewport(value, mWXComponent.getViewPortWidth()), mWXComponent.getViewPortWidth()));
+            }
+            break;
+            default:
+                break;
+        }
+        if(holder == null){
+            holder  = PropertyValuesHolder.ofFloat(property, 1, 1);
+        }
+        return  holder;
+    }
+
+    private void doLayoutPropertyValuesHolderAnimation(PropertyValuesHolder[] holders){
+        layoutValueAnimator = ValueAnimator.ofPropertyValuesHolder(holders);
+        layoutValueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
+            @Override
+            public void onAnimationUpdate(final ValueAnimator animation) {
+                PropertyValuesHolder holders[] = animation.getValues();
+                for(PropertyValuesHolder holder : holders){
+
+                    final String property =  holder.getPropertyName();
+                    asynchronouslyUpdateLayout(mWXComponent, property, (Float) animation.getAnimatedValue(property));
+                }
+//                WXBridgeManager.getInstance().calculateLayoutPostToJSThread(mWXComponent.getInstanceId(), mWXComponent.getRef(), false);
+            }
+        });
+        layoutValueAnimator.addListener(new AnimatorListenerAdapter() {
+
+            boolean  hasCancel = false;
+            @Override
+            public void onAnimationCancel(Animator animation) {
+                super.onAnimationCancel(animation);
+                hasCancel = true;
+            }
+
+            @Override
+            public void onAnimationEnd(Animator animation) {
+                if(hasCancel){
+                    return;
+                }
+                super.onAnimationEnd(animation);
+                WXTransition.this.onTransitionAnimationEnd();
+            }
+        });
+        if(interpolator != null) {
+            layoutValueAnimator.setInterpolator(interpolator);
+        }
+        layoutValueAnimator.setStartDelay((long) (delay));
+        layoutValueAnimator.setDuration((long) (duration));
+        layoutValueAnimator.start();
+    }
+
+    @SuppressWarnings("unused")
+    public static void asynchronouslyUpdateLayout(WXComponent component, final String propertyName, final float propertyValue) {
+        if(component == null) {
+            return;
+        }
+        final String ref = component.getRef();
+        final String instanceId = component.getInstanceId();
+        if(TextUtils.isEmpty(ref) || TextUtils.isEmpty(instanceId)) {
+            return;
+        }
+
+        WXSDKManager.getInstance().getWXBridgeManager().post(new Runnable() {
+            @Override
+            public void run() {
+                switch (propertyName){
+                    case Constants.Name.WIDTH:{
+                        WXBridgeManager.getInstance().setStyleWidth(instanceId, ref, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.HEIGHT:{
+                        WXBridgeManager.getInstance().setStyleHeight(instanceId, ref, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.MARGIN_TOP:{
+                        WXBridgeManager.getInstance().setMargin(instanceId, ref, CSSShorthand.EDGE.TOP, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.MARGIN_LEFT:{
+                        WXBridgeManager.getInstance().setMargin(instanceId, ref, CSSShorthand.EDGE.LEFT, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.MARGIN_RIGHT:{
+                        WXBridgeManager.getInstance().setMargin(instanceId, ref, CSSShorthand.EDGE.RIGHT, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.MARGIN_BOTTOM:{
+                        WXBridgeManager.getInstance().setMargin(instanceId, ref, CSSShorthand.EDGE.BOTTOM, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.LEFT:{
+                        WXBridgeManager.getInstance().setPosition(instanceId, ref, CSSShorthand.EDGE.LEFT, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.RIGHT:{
+                        WXBridgeManager.getInstance().setPosition(instanceId, ref, CSSShorthand.EDGE.RIGHT, (propertyValue));
+                    }
+                    break;
+                    case Constants.Name.BOTTOM:{
+                        WXBridgeManager.getInstance().setPosition(instanceId, ref, CSSShorthand.EDGE.BOTTOM, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.TOP:{
+                        WXBridgeManager.getInstance().setPosition(instanceId, ref, CSSShorthand.EDGE.TOP, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.PADDING_TOP:{
+                        WXBridgeManager.getInstance().setPadding(instanceId, ref, CSSShorthand.EDGE.TOP, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.PADDING_BOTTOM:{
+                        WXBridgeManager.getInstance().setPadding(instanceId, ref, CSSShorthand.EDGE.BOTTOM, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.PADDING_LEFT:{
+                        WXBridgeManager.getInstance().setPadding(instanceId, ref, CSSShorthand.EDGE.LEFT, propertyValue);
+                    }
+                    break;
+                    case Constants.Name.PADDING_RIGHT:{
+                        WXBridgeManager.getInstance().setPadding(instanceId, ref, CSSShorthand.EDGE.RIGHT, propertyValue);
+                    }
+                    break;
+                    default:
+                        break;
+                }
+            }
+        });
+    }
+
+    private synchronized void onTransitionAnimationEnd(){
+        if(duration > 0){
+            if(transitionEndEvent != null){
+                View view = getTargetView();
+                if(view != null &&  transitionEndEvent != null){
+                    view.post(transitionEndEvent);
+                }
+                transitionEndEvent = null;
+            }
+        }
+        synchronized (targetStyles){
+            if(targetStyles.size() > 0){
+                for(String property : properties) {
+                    if(targetStyles.containsKey(property)){
+                        Object targetValue = targetStyles.remove(property);
+                        mWXComponent.getStyles().put(property, targetValue);
+                    }
+                }
+                targetStyles.clear();
+            }
+        }
+    }
+
+    private View getTargetView(){
+        return null != mWXComponent ? mWXComponent.getHostView() : null;
+    }
+
+
+    /**
+     * get time millis
+     * */
+    private static long parseTimeMillis(Map<String, Object> style, String key, long defaultValue){
+        String  duration = WXUtils.getString(style.get(key), null);
+        if(duration != null){
+            duration = duration.replaceAll("ms", "");
+        }
+        if(duration != null){
+            if(WXEnvironment.isApkDebugable()){
+                if(duration.contains("px")){
+                    WXLogUtils.w("Transition Duration Unit Only Support ms, " + duration + " is not ms Unit");
+                }
+            }
+            duration = duration.replaceAll("px", "");
+        }
+        if(TextUtils.isEmpty(duration)){
+            return  defaultValue;
+        }
+        try{
+            return (long)Float.parseFloat(duration);
+        }catch (NumberFormatException e){
+            return  defaultValue;
+        }
+    }
+
+    /**
+     * create interpolcator same with web
+     * http://www.w3school.com.cn/cssref/pr_transition-timing-function.asp
+     * */
+    private static Interpolator createTimeInterpolator(String interpolator) {
+        if (!TextUtils.isEmpty(interpolator)) {
+            switch (interpolator) {
+                case TimeFunction.EASE_IN:
+                    return PathInterpolatorCompat.create(0.42f,0f, 1f,1f);
+                case TimeFunction.EASE_OUT:
+                    return PathInterpolatorCompat.create(0f,0f, 0.58f,1f);
+                case TimeFunction.EASE_IN_OUT:
+                    return PathInterpolatorCompat.create(0.42f,0f, 0.58f,1f);
+                case TimeFunction.EASE:
+                    return PathInterpolatorCompat.create(0.25f,0.1f, 0.25f,1f);
+                case TimeFunction.LINEAR:
+                    return PathInterpolatorCompat.create(0.0f,0f, 1f,1f);
+                default:
+                    try {
+                        //Parse cubic-bezier
+                        SingleFunctionParser<Float> parser = new SingleFunctionParser<>(
+                                interpolator,
+                                new SingleFunctionParser.FlatMapper<Float>() {
+                                    @Override
+                                    public Float map(String raw) {
+                                        return Float.parseFloat(raw);
+                                    }
+                                });
+                        List<Float> params = parser.parse(TimeFunction.CUBIC_BEZIER);
+                        if (params != null && params.size() == 4) {
+                            return PathInterpolatorCompat.create(
+                                    params.get(0), params.get(1), params.get(2), params.get(3));
+                        }
+                    } catch (RuntimeException e) {
+                        if(WXEnvironment.isApkDebugable()) {
+                            WXLogUtils.e("WXTransition", e);
+                        }
+                    }
+            }
+        }
+        return PathInterpolatorCompat.create(0.25f,0.1f, 0.25f,1f);
+    }
+
+    private static  void  updateTransitionProperties(WXTransition transition, String transtionProperty){
+        if(transtionProperty == null){
+            return;
+        }
+        transition.properties.clear();
+        String[] propertiesArray = PROPERTY_SPLIT_PATTERN.split(transtionProperty);
+        for(String property : propertiesArray){
+            String trim = property.trim();
+            if(TextUtils.isEmpty(trim)){
+                continue;
+            }
+            if(!(LAYOUT_PROPERTIES.contains(trim) || TRANSFORM_PROPERTIES.contains(trim))){
+                if(WXEnvironment.isApkDebugable()){
+                    WXLogUtils.e("WXTransition Property Not Supported" + trim + " in " + transtionProperty);
+                }
+                continue;
+            }
+            transition.properties.add(trim);
+        }
+    }
+
+    public List<String> getProperties() {
+        return properties;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/el/parse/ArrayStack.java b/android/sdk/src/main/java/org/apache/weex/el/parse/ArrayStack.java
new file mode 100644
index 0000000..b492d53
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/el/parse/ArrayStack.java
@@ -0,0 +1,72 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.el.parse;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * stack for parse and execute code
+ * Created by jianbai.gbj on 2017/9/1.
+ */
+public class ArrayStack<T> {
+
+    private ArrayList<T> stack;
+
+    public ArrayStack() {
+        this.stack = new ArrayList<T>(4);
+    }
+
+    public int size() {
+        return stack.size();
+    }
+
+    public T pop() {
+        return stack.remove(stack.size()-1);
+    }
+
+    public void push(T token) {
+        stack.add(token);
+    }
+
+
+    public T peek() {
+        return stack.get(stack.size()-1);
+    }
+
+    public T get(int i) {
+        return stack.get(i);
+    }
+
+    public T remove(int i) {
+        return stack.remove(i);
+    }
+
+    public void add(int i, T t) {
+        stack.add(i, t);
+    }
+
+    public boolean isEmpty() {
+        return   stack.isEmpty();
+    }
+
+    public List<T> getList(){
+        return stack;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/el/parse/Block.java b/android/sdk/src/main/java/org/apache/weex/el/parse/Block.java
new file mode 100644
index 0000000..d593a01
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/el/parse/Block.java
@@ -0,0 +1,71 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.el.parse;
+
+import com.alibaba.fastjson.JSONArray;
+
+import java.util.List;
+
+/**
+ * block, has more than one tokens, but only first will be execute.
+ * Created by jianbai.gbj on 2017/8/28.
+ */
+class Block extends Token {
+    private List<Token> tokens;
+    public Block(List<Token> tokens,  int type) {
+        super("", type);
+        this.tokens = tokens;
+    }
+
+    @Override
+    public Object execute(Object context){
+        if(getType() == TYPE_ARRAY){
+            if(tokens == null || tokens.size() == 0){
+                return  new JSONArray(4);
+            }
+            JSONArray arrayList = new JSONArray(tokens.size());
+            for(int i=0; i<tokens.size(); i++){
+                Token token = tokens.get(i);
+                if(token == null){
+                    arrayList.add(null);
+                }else{
+                    arrayList.add(token.execute(context));
+                }
+            }
+            return arrayList;
+        }
+        if(tokens == null || tokens.size() == 0){
+            return  null;
+        }
+        Token token = tokens.get(0);
+        return token.execute(context);
+    }
+
+    @Override
+    public String toString() {
+        if(getType() == TYPE_ARRAY){
+            return "" + tokens + "";
+        }else {
+            if(tokens != null && tokens.size() == 1){
+                return "{" + tokens.get(0) + '}';
+            }
+            return "{" + tokens + '}';
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/el/parse/Operator.java b/android/sdk/src/main/java/org/apache/weex/el/parse/Operator.java
new file mode 100644
index 0000000..839d541
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/el/parse/Operator.java
@@ -0,0 +1,106 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.el.parse;
+
+
+/**
+ * Created by jianbai.gbj on 2017/8/28.
+ * one operator, two operator, and three operator
+ */
+class Operator extends Token {
+    public Token self;
+    public Token first;
+    public Token second;
+
+    public Operator(String operator, int type) {
+        super(operator, type);
+    }
+
+
+    @Override
+    public Object execute(Object context){
+        String op = getToken();
+        switch (op){
+            case  Operators.DOT_STR:
+            case  Operators.ARRAY_START_STR:{
+                return  Operators.dot(first, second, context);
+            }
+            case  Operators.EQUAL:
+            case  Operators.EQUAL2:{
+                return Operators.isEquals(first, second, context);
+            }
+            case  Operators.NOT_EQUAL:
+            case  Operators.NOT_EQUAL2:{
+                return !Operators.isEquals(first, second, context);
+            }
+            case  Operators.CONDITION_IF_STRING:{
+                return Operators.condition(self, first, second, context);
+            }
+            case  Operators.AND_NOT:{
+                return  !Operators.tokenTrue(self, context);
+            }
+            case  Operators.AND:{
+                return  Operators.tokenTrue(first, context) && Operators.tokenTrue(second, context);
+            }
+            case  Operators.OR:{
+                return  Operators.tokenTrue(first, context) || Operators.tokenTrue(second, context);
+            }
+            case  Operators.G:{
+                return  Operators.tokenNumber(first, context) > Operators.tokenNumber(second, context);
+            }
+            case  Operators.GE:{
+                return  Operators.tokenNumber(first, context) >= Operators.tokenNumber(second, context);
+            }
+            case  Operators.L:{
+                return  Operators.tokenNumber(first, context) < Operators.tokenNumber(second, context);
+            }
+            case  Operators.LE:{
+                return  Operators.tokenNumber(first, context) <= Operators.tokenNumber(second, context);
+            }
+            case  Operators.PLUS:{
+                return  Operators.plus(first, second, context);
+            }
+            case  Operators.SUB:{
+                return  Operators.sub(first, second, context);
+            }
+            case  Operators.MUL:{
+                return  Operators.mul(first, second, context);
+            }
+            case  Operators.DIV:{
+                return  Operators.div(first, second, context);
+            }
+            case  Operators.MOD:{
+                return  Operators.mod(first, second, context);
+            }
+            default:
+                throw new IllegalArgumentException(op + " operator is not supported");
+        }
+    }
+
+    @Override
+    public String toString() {
+        if(Operators.AND_NOT.equals(getToken())){
+            return "{!" +  self + "}";
+        }
+        if(self == null){
+            return "{" + first +  getToken() + second + "}";
+        }
+        return "{" + self + getToken() + first + ":" + second + "}";
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/el/parse/Operators.java b/android/sdk/src/main/java/org/apache/weex/el/parse/Operators.java
new file mode 100644
index 0000000..61d1842
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/el/parse/Operators.java
@@ -0,0 +1,502 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.el.parse;
+
+import java.lang.reflect.Array;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Stack;
+
+/**
+ * Created by furture on 2017/8/28.
+ */
+public class Operators {
+
+
+    public static Object dot(Token left, Token right, Object context){
+        if(left == null || right == null){
+            return null;
+        }
+        Object leftValue = left.execute(context);
+        if(leftValue == null){
+            return null;
+        }
+        Object value =  null;
+        if(right.getType() != Token.TYPE_IDENTIFIER){
+            Object identifter = right.execute(context);
+            if(identifter instanceof Double){
+                identifter = ((Double) identifter).intValue();
+            }
+            String key = identifter == null ? "" : identifter.toString().trim();
+            value = Operators.el(leftValue, key);
+        }else{
+            value = right.execute(leftValue);
+        }
+        if(value != null){
+            return value;
+        }
+        return  specialKey(leftValue, right.getToken());
+    }
+
+    /**
+     * get key's value on object
+     * */
+    public static  Object el(Object context, String key){
+        if(context == null){
+            return  null;
+        }
+        // TODO
+//        if(context instanceof CellRenderContext){
+//            if(WXEnvironment.isApkDebugable()){
+//                throw new IllegalArgumentException("rong context CellRenderContext, you should pass it's stack");
+//            }
+//            context = ((CellRenderContext) context).stack;
+//        }
+        if(context instanceof ArrayStack){
+            ArrayStack stack = (ArrayStack) context;
+            for(int index=stack.size()-1; index >= 0; index--){
+                Object value = stack.get(index);
+                if(value instanceof  Map){
+                    Map map = (Map) value;
+                    if(map.containsKey(key)){
+                        return map.get(key);
+                    }
+                }
+            }
+        }
+        if(context instanceof Stack){
+            Stack stack = (Stack) context;
+            for(int index=stack.size()-1; index >= 0; index--){
+                Object value = stack.get(index);
+                if(value instanceof  Map){
+                    Map map = (Map) value;
+                    if(map.containsKey(key)){
+                        return map.get(key);
+                    }
+                }
+            }
+        }
+
+        if(context instanceof  Map){
+            return ((Map) context).get(key);
+        }
+
+        if(context instanceof List){
+            List list = (List) context;
+            try{
+                return list.get(Integer.parseInt(key));
+            }catch (Exception e){}
+        }
+        if(context.getClass().isArray()){
+            try{
+                return Array.get(context, Integer.parseInt(key));
+            }catch (Exception e){}
+        }
+        return  null;
+    }
+
+    public static  Object specialKey(Object leftValue, String key){
+        if("length".equals(key)){
+            if(leftValue instanceof  CharSequence){
+                return ((CharSequence) leftValue).length();
+            }
+            if(leftValue instanceof  Map){
+                return  ((Map) leftValue).size();
+            }
+            if(leftValue instanceof  Map){
+                return  ((Map) leftValue).size();
+            }
+            if(leftValue instanceof  List){
+                return  ((List) leftValue).size();
+            }
+            if(leftValue.getClass().isArray()){
+                return Array.getLength(leftValue);
+            }
+        }
+        return null;
+    }
+
+    public static Object plus(Token left, Token right, Object context){
+        Object leftValue = null;
+        Object rightValue = null;
+        if(left != null){
+            leftValue = left.execute(context);
+        }
+        if(right  != null){
+            rightValue = right.execute(context);
+        }
+        if(leftValue instanceof  CharSequence || rightValue instanceof  CharSequence){
+            if(leftValue == null){
+                return  rightValue;
+            }
+            return leftValue.toString() + (rightValue == null ? "" : rightValue.toString());
+        }
+        if(leftValue instanceof  Number || rightValue instanceof Number){
+            return getNumber(leftValue) + getNumber(rightValue);
+        }
+        if(leftValue == null && rightValue == null){
+            return  null;
+        }
+        if(leftValue == null){
+            return  rightValue.toString();
+        }
+        return leftValue.toString() + (rightValue == null ? "" : rightValue.toString());
+    }
+
+
+    public static Object sub(Token left, Token right, Object context){
+        Object leftValue = null;
+        Object rightValue = null;
+        if(left != null){
+            leftValue = left.execute(context);
+        }
+        if(right  != null){
+            rightValue = right.execute(context);
+        }
+        return getNumber(leftValue) - getNumber(rightValue);
+    }
+
+    public static Object div(Token left, Token right, Object context){
+        Object leftValue = null;
+        Object rightValue = null;
+        if(left != null){
+            leftValue = left.execute(context);
+        }
+        if(right  != null){
+            rightValue = right.execute(context);
+        }
+        return getNumber(leftValue)/getNumber(rightValue);
+    }
+
+    public static Object mul(Token left, Token right, Object context){
+        Object leftValue = null;
+        Object rightValue = null;
+        if(left != null){
+            leftValue = left.execute(context);
+        }
+        if(right  != null){
+            rightValue = right.execute(context);
+        }
+        return getNumber(leftValue)*getNumber(rightValue);
+    }
+
+    public static Object mod(Token left, Token right, Object context){
+        Object leftValue = null;
+        Object rightValue = null;
+        if(left != null){
+            leftValue = left.execute(context);
+        }
+        if(right  != null){
+            rightValue = right.execute(context);
+        }
+        return (getNumber(leftValue))%(getNumber(rightValue));
+    }
+
+    /**
+     * condition expression
+     * */
+    public static Object condition(Token selfs, Token first, Token second, Object context){
+        boolean value = false;
+        if(selfs != null){
+            value = isTrue(selfs.execute(context));
+        }
+        if(value){
+            if(first != null){
+                return  first.execute(context);
+            }
+        }else{
+            if(second != null){
+                return  second.execute(context);
+            }
+        }
+        return null;
+    }
+
+
+    /**
+     * is token value is true
+     * */
+    public static boolean tokenTrue(Token selfs, Object context) {
+        if(selfs == null){
+            return false;
+        }
+        Object value = selfs.execute(context);
+        return  isTrue(value);
+    }
+
+    /**
+     * get token number
+     * */
+    public static double tokenNumber(Token self,  Object context) {
+        if(self == null){
+            return  0;
+        }
+        Object value = self.execute(context);
+        return  getNumber(value);
+    }
+
+
+
+    /**
+     * isEquls operation
+     * */
+    public static boolean isEquals(Token left, Token right, Object context){
+        if(left == null && right == null){
+            return  true;
+        }
+        Object leftValue =  null;
+        if(left != null){
+            leftValue  = left.execute(context);
+        }
+        Object rightValue = null;
+        if(right != null) {
+            rightValue = right.execute(context);
+        }
+        if(leftValue == null){
+            if(rightValue == null){
+                return  true;
+            }
+            if(rightValue instanceof  CharSequence){
+                if(isEmpty(rightValue.toString())){
+                    return  true;
+                }
+            }
+            return  false;
+        }
+        if(rightValue == null){
+            if(isEmpty(leftValue.toString())){
+                return  true;
+            }
+            return  false;
+        }
+        if(leftValue instanceof  Number){
+            if(rightValue instanceof  Number){
+                return  ((Number) leftValue).doubleValue() == ((Number) rightValue).doubleValue();
+            }
+            return ((Number) leftValue).doubleValue() == getNumber(rightValue);
+        }
+        if(rightValue instanceof  Number){
+            return getNumber(leftValue) == ((Number) rightValue).doubleValue();
+        }
+        if(leftValue instanceof CharSequence
+                ||  rightValue instanceof CharSequence){
+            return  leftValue.toString().trim().equals(rightValue.toString().trim());
+        }
+        return  leftValue.equals(rightValue);
+    }
+
+
+    /**
+     * check whether value is true
+     * */
+    public static boolean isTrue(Object value){
+        if(value == null){
+            return  false;
+        }
+        if(value instanceof  Number){
+            return ((Number) value).doubleValue() != 0;
+        }
+        String bool = value.toString().trim();
+        if("false".equals(bool)
+                || "undefined".equals(bool)
+                || "null".equals(bool)){
+            return  false;
+        }
+        if(isEmpty(bool)){
+            return  false;
+        }
+        return  true;
+    }
+
+    /**
+     * check String value is empty
+     * */
+    public static boolean isEmpty(String value){
+        if (value == null){
+            return  true;
+        }
+        for(int i=0; i<value.length(); i++){
+            if(value.charAt(i) != ' '){
+                return  false;
+            }
+        }
+        return true;
+    }
+
+
+    /**
+     * get number
+     * */
+    public static double getNumber(Object value){
+        if(value == null){
+            return  0;
+        }
+        if(value instanceof  Number){
+            return  ((Number) value).doubleValue();
+        }
+        try{
+            return Double.parseDouble(value.toString());
+        }catch (Exception e){return  0;}
+    }
+
+    public static boolean isOpEnd(String op){
+        return isOpEnd(op.charAt(0));
+    }
+    /**
+     * op end, has none operation, should not enter operator stack.
+     * */
+    public static boolean isOpEnd(char op){
+        if(op == BRACKET_END
+                || op == ARRAY_END
+                || op == SPACE
+                || op == ARRAY_SEPRATOR){
+            return true;
+        }
+        return  false;
+    }
+
+    /**
+     * is not
+     * */
+    public static boolean isDot(String opStr){
+        char op = opStr.charAt(0);
+        return  op == DOT || op == ARRAY_START;
+    }
+
+
+
+
+    public static final char BRACKET_END = ')';
+    public static final String BRACKET_END_STR = ")";
+    public static final char BRACKET_START = '(';
+    public static final String BRACKET_START_STR = "(";
+    public static final char QUOTE = '"';
+    public static final char SINGLE_QUOTE = '\'';
+    public static final char DOT = '.';
+    public static final String DOT_STR = ".";
+    public static final char ARRAY_START = '[';
+    public static final String ARRAY_START_STR = "[";
+    public static final char ARRAY_SEPRATOR = ',';
+    public static final String ARRAY_SEPRATOR_STR = ",";
+    public static final char ARRAY_END = ']';
+    public static final String ARRAY_END_STR = "]";
+    public static final String SPACE_STR = " ";
+    public static final char SPACE = ' ';
+    public static final char BLOCK_START = '{';
+    public static final String BLOCK_START_STR = "{";
+    public static final char BLOCK_END = '}';
+    public static final String BLOCK_END_STR = "}";
+    public static final char DOLLAR = '$';
+    public static final String DOLLAR_STR = "$";
+
+    /**
+     * condition
+     * */
+    public static final char  CONDITION_IF = '?';
+    public static final String  CONDITION_IF_STRING = "?";
+    public static final char  CONDITION_IF_MIDDLE = ':';
+
+
+
+    /**
+     * match
+     * */
+    public static final String PLUS ="+";
+    public static final String SUB = "-";
+    public static final String MUL = "*";
+    public static final String DIV = "/";
+    public static final String MOD = "%";
+
+
+
+    public static final String AND  = "&&";
+    public static final String OR  = "||";
+    /**
+     * and operator
+     * */
+    public static final String EQUAL = "===";
+    public static final String EQUAL2 = "==";
+    public static final String NOT_EQUAL = "!==";
+    public static final String NOT_EQUAL2 = "!=";
+    public static final String AND_NOT = "!";
+
+
+    public static final String G = ">";
+    public static final String GE = ">=";
+    public static final String LE = "<=";
+    public static final String L = "<";
+
+
+
+
+
+    /**
+     * https://github.com/jquery/esprima/blob/master/src/parser.ts
+     * */
+    public static Map<String, Integer> OPERATORS_PRIORITY = new HashMap<>();
+    static {
+        OPERATORS_PRIORITY.put(BLOCK_END_STR, 0);
+        OPERATORS_PRIORITY.put(BRACKET_END_STR, 0);
+        OPERATORS_PRIORITY.put(SPACE_STR, 0);
+        OPERATORS_PRIORITY.put(ARRAY_SEPRATOR_STR, 0);
+        OPERATORS_PRIORITY.put(ARRAY_END_STR, 0);
+
+
+        OPERATORS_PRIORITY.put(OR, 1);
+        OPERATORS_PRIORITY.put(AND, 1);
+
+        OPERATORS_PRIORITY.put(EQUAL, 2);
+        OPERATORS_PRIORITY.put(EQUAL2, 2);
+        OPERATORS_PRIORITY.put(NOT_EQUAL, 2);
+        OPERATORS_PRIORITY.put(NOT_EQUAL2, 2);
+
+        OPERATORS_PRIORITY.put(G, 7);
+        OPERATORS_PRIORITY.put(GE, 7);
+        OPERATORS_PRIORITY.put(L, 7);
+        OPERATORS_PRIORITY.put(LE, 8);
+
+        OPERATORS_PRIORITY.put(PLUS, 9);
+        OPERATORS_PRIORITY.put(SUB, 9);
+        OPERATORS_PRIORITY.put(MUL, 10);
+        OPERATORS_PRIORITY.put(DIV, 10);
+        OPERATORS_PRIORITY.put(MOD, 10);
+        OPERATORS_PRIORITY.put(AND_NOT, 11);
+
+        OPERATORS_PRIORITY.put(DOT_STR, 15);
+        
+        OPERATORS_PRIORITY.put(ARRAY_START_STR, 16);
+
+
+        OPERATORS_PRIORITY.put(BRACKET_START_STR, 17);
+        OPERATORS_PRIORITY.put(BLOCK_START_STR, 17);
+
+
+    }
+
+
+    public static final Map<String,Object> KEYWORDS = new HashMap<>();
+    static {
+        KEYWORDS.put("null", null);
+        KEYWORDS.put("true", Boolean.TRUE);
+        KEYWORDS.put("false", Boolean.FALSE);
+        KEYWORDS.put("undefined", null);
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/el/parse/Parser.java b/android/sdk/src/main/java/org/apache/weex/el/parse/Parser.java
new file mode 100644
index 0000000..ea85032
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/el/parse/Parser.java
@@ -0,0 +1,486 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.el.parse;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.ArrayList;
+import java.util.List;
+
+
+/**
+ * Created by furture on 2017/8/28.
+ * simple expression parse, less ast node and save memory
+ */
+public class Parser {
+
+    private String code;
+    private int position;
+    private ArrayStack<Token> stacks;
+    private ArrayStack<Symbol> operators;
+
+    public Parser(String code){
+        this.code = code;
+        this.position = 0;
+        this.stacks = new ArrayStack<>();
+        this.operators = new ArrayStack<>();
+    }
+
+
+    public final Token parse(){
+        while (hasNextToken()){
+            scanNextToken();
+        }
+        while (!operators.isEmpty()){
+            Symbol op = operators.pop();
+            doOperator(op);
+        }
+        if(stacks.size() == 1){
+            return  stacks.pop();
+        }
+        Block block = new Block(stacks.getList(), Token.TYPE_BLOCK);
+        return block;
+    }
+
+
+    /**
+     * parse code to ast block.
+     * */
+    public static Token parse(String code){
+        try{
+            Parser parser = new Parser(code);
+            return parser.parse();
+        }catch (Exception e){
+            if(WXEnvironment.isApkDebugable()){
+                WXLogUtils.e("code " + code, e);
+            }
+            return new Block(null, Token.TYPE_BLOCK);
+        }
+    }
+
+
+    final char scanNextToken(){
+        char ch = nextToken();
+        if(ch == Operators.DOLLAR){
+            position++;
+            return ch;
+        }else if(Character.isJavaIdentifierStart(ch)){
+            scanIdentifier();
+        }else if (ch == Operators.BRACKET_START || ch == Operators.BLOCK_START) {
+            scanBracket();
+        }else if (ch == Operators.ARRAY_START) {
+            scanArray();
+        }else if (ch ==  Operators.QUOTE || ch == Operators.SINGLE_QUOTE) {
+            scanString();
+        }else if((ch == Operators.DOT && Character.isDigit(code.charAt(position + 1)))
+                || Character.isDigit(ch)){ //number .00 .00e6
+            scanNumber();
+        }else if(ch ==  Operators.CONDITION_IF){
+            scanIf();
+        }else if(ch ==  Operators.CONDITION_IF_MIDDLE
+                || ch ==  Operators.BRACKET_END
+                || ch == Operators.BLOCK_END
+                || ch == Operators.SPACE
+                || ch == Operators.ARRAY_END){
+            position++;
+            return ch;
+        }else{
+            scanOperator();
+        }
+        return ch;
+    }
+
+
+    final void  scanArray(){
+        int stackSize = stacks.size();
+        int opSize = operators.size();
+        int type = Token.TYPE_IDENTIFIER;
+        if(position - 1 < 0 || !Character.isJavaIdentifierPart(code.charAt(position - 1))){
+            type = Token.TYPE_ARRAY;
+        }
+        operators.push(new Symbol(Operators.ARRAY_START_STR, stacks.size()));
+        position++;
+        while (hasNextToken()){
+            char token = scanNextToken();
+            if(token == Operators.ARRAY_END){
+                break;
+            }
+        }
+
+        if(stacks.size() <= stackSize){ // empty bracket, none need, save memory
+            while (operators.size() > opSize){
+                operators.pop();
+            }
+            return;
+        }
+
+        while (operators.size() > opSize){
+            Symbol op = operators.pop();
+            if(stacks.size() > stackSize){
+                doOperator(op);
+            }
+        }
+        List<Token> tokens = new ArrayList<>(4);
+        for(int i=stackSize; i<stacks.size(); i++){
+            tokens.add(stacks.get(i));
+        }
+        while (stacks.size() > stackSize){
+            stacks.pop();
+        }
+        if(type == Token.TYPE_ARRAY || stacks.size() == 0){
+            Block block = new Block(tokens, Token.TYPE_ARRAY);
+            stacks.push(block);
+            return;
+        }
+
+        Token identifer = stacks.pop();
+        Token second = null;
+        if(tokens.size() == 1){
+            second = tokens.get(0);
+        }else{
+            second = new Block(tokens, Token.TYPE_BLOCK);
+        }
+        Operator operator = new Operator(Operators.DOT_STR, type);
+        operator.first = identifer;
+        operator.second = second;
+        stacks.push(operator);
+    }
+
+    void  scanBracket(){
+        int stackSize = stacks.size();
+        int opSize = operators.size();
+        if(code.charAt(position) == Operators.BLOCK_START){
+            operators.push(new Symbol(Operators.BLOCK_START_STR, stacks.size()));
+            position++;
+            while (hasNextToken()){
+                if(scanNextToken() == Operators.BLOCK_END){
+                    break;
+                }
+            }
+        }else{
+            operators.push(new Symbol(Operators.BRACKET_START_STR, stacks.size()));
+            position++;
+            while (hasNextToken()){
+                if(scanNextToken() == Operators.BRACKET_END){
+                    break;
+                }
+            }
+        }
+        if(stacks.size() <= stackSize){ // empty bracket, none need, save memory
+            while (operators.size() > opSize){
+                operators.pop();
+            }
+            return;
+        }
+        while (operators.size() > opSize){
+            Symbol op = operators.pop();
+            if(stacks.size() > stackSize){
+                doOperator(op);
+            }
+        }
+        List<Token> tokens = new ArrayList<>(4);
+        for(int i=stackSize; i<stacks.size(); i++){
+            tokens.add(stacks.get(i));
+        }
+        while (stacks.size() > stackSize){
+            stacks.pop();
+        }
+        if(tokens.size() == 1){
+            stacks.push(tokens.get(0));
+        }else{
+            Block block = new Block(tokens, Token.TYPE_BLOCK);
+            stacks.push(block);
+        }
+    }
+
+    /**
+     * 1  === (1 + 3) &&  1
+     * scan operator
+     * */
+    void scanOperator(){
+        int start = position;
+        int length = Math.min(position + 3, code.length());
+        String operator = code.substring(position, length);
+        if(operator.length() >= 3){
+            if(!Operators.OPERATORS_PRIORITY.containsKey(operator)){
+                operator = operator.substring(0, 2);
+            }
+        }
+        if(operator.length() >= 2){
+            if(!Operators.OPERATORS_PRIORITY.containsKey(operator)){
+                operator = operator.substring(0, 1);
+            }
+        }
+        if(!Operators.OPERATORS_PRIORITY.containsKey(operator)){
+            //just skip illegal character
+            int illegalChar = Math.min(start + 1, code.length());
+            WXLogUtils.e("weex", new IllegalArgumentException(code.substring(0, illegalChar) + " illegal code operator" + operator));
+            position += operator.length();
+            return;
+        }
+        if((!operators.isEmpty() && operators.peek() != null)){
+            String preOp = operators.peek().op;
+            if(Operators.OPERATORS_PRIORITY.get(preOp) >= Operators.OPERATORS_PRIORITY.get(operator)){
+                Symbol op = operators.pop();
+                doOperator(op);
+            }
+        }
+        if(!Operators.isOpEnd(operator)){
+            operators.push(new Symbol(operator, stacks.size()));
+        }
+        position += operator.length();
+    }
+
+
+
+    void doOperator(Symbol symbol){
+        String op = symbol.op;
+        if(Operators.BRACKET_START_STR.equals(symbol.op)
+                || Operators.BLOCK_START_STR.equals(symbol.op)
+                || Operators.ARRAY_START_STR.equals(symbol.op)
+                || Operators.DOLLAR_STR.equals(symbol.op)){
+            return;
+        }
+        if(Operators.BLOCK_START_STR.equals(symbol.op)){
+            return;
+        }
+        int second = symbol.pos;
+        int first  = Math.max(symbol.pos - 1, 0);
+        if(!operators.isEmpty()){
+            first = Math.max(first, operators.peek().pos);
+        }
+
+        Operator operator = new Operator(op, Token.TYPE_OPERATOR);
+        if(Operators.AND_NOT.equals(op)){
+            if(stacks.size() > second) {
+                Token token = stacks.remove(second);
+                operator.self = token;
+                stacks.add(second, operator);
+                return;
+            }
+            return; //invalid
+        }
+        if(stacks.size() > second) {
+            operator.second = stacks.remove(second);
+        }else{
+            return;
+        }
+        if(stacks.size() > first) {
+            operator.first = stacks.remove(first);
+        }else{
+            if(operator.second == null){
+                return;
+            }
+        }
+        stacks.add(first, operator);
+    }
+
+    /**
+     * condition if
+     * */
+    void scanIf(){
+        Operator operator = new Operator(Operators.CONDITION_IF_STRING, Token.TYPE_OPERATOR);
+        int selfIndex = 0;
+        doStackOperators(0);
+        if(operators.size() > 0){
+            selfIndex = Math.max(operators.peek().pos, selfIndex);
+        }
+        if(stacks.size() > selfIndex){
+            operator.self = stacks.pop();
+        }
+
+        int stackSize = stacks.size();
+        int leftOperatorSize = operators.size();
+        position++;
+        while (hasNextToken()){
+            if(scanNextToken() == Operators.CONDITION_IF_MIDDLE){
+                break;
+            }
+        }
+        while (operators.size() > leftOperatorSize){
+            Symbol symbol = operators.pop();
+            doOperator(symbol);
+        }
+
+        while (stacks.size() > stackSize){
+            operator.first = stacks.pop();
+        }
+        int rightOperatorsSize = operators.size();
+        while (hasNextToken()){
+            scanNextToken();
+            if(hasNextToken()){
+                scanNextToken();
+            }
+            if(operators.size() <= rightOperatorsSize){
+                break;
+            }
+        }
+        doStackOperators(rightOperatorsSize);
+        while (stacks.size() > stackSize){
+            operator.second = stacks.pop();
+        }
+        stacks.push(operator);
+    }
+
+    private final void doStackOperators(int operatorSize){
+        while (operators.size() > operatorSize){
+            Symbol symbol = operators.pop();
+            doOperator(symbol);
+        }
+    }
+
+    /**
+     * 1+e6
+     * .00
+     * .00e6
+     * 100
+     * 199e5
+     * */
+    final void scanNumber(){
+        boolean isInt = true;
+        int start = position;
+        if(code.charAt(position) == 'e' || code.charAt(position) == '.'){
+            isInt = false;
+        }
+        position++;
+        while (hasNext()){
+            char ch = code.charAt(position);
+            if(Character.isDigit(ch)
+                    || ch == '.'
+                    || ch =='e'){
+                if(ch == 'e'
+                        || ch == '.'){
+                    isInt = false;
+                }
+                position++;
+            }else{
+                break;
+            }
+        }
+        String number = code.substring(start, position);
+        if(".".equals(number)){
+            return;
+        }
+        Token stack = null;
+        if(isInt){
+            stack = new Token(number, Token.TYPE_INT);
+        }else{
+            stack = new Token(number, Token.TYPE_DOUBLE);
+        }
+        stacks.push(stack);
+    }
+
+
+    final void  scanString(){
+        int start = position;
+        ArrayStack operator = new ArrayStack();
+        char quote = code.charAt(start);
+        operator.push(quote);
+        StringBuilder builder = new StringBuilder();
+        for(position= start + 1; position<code.length(); position++){
+            char ch = code.charAt(position);
+            if(ch == quote){
+                if(code.charAt(position -1) != '\\'){
+                    operator.pop();
+                    if(operator.size() == 0){
+                       position++;
+                       break;
+                    }
+                }else{
+                    builder.deleteCharAt(builder.length()-1);
+                    builder.append(ch);
+                }
+            }else{
+                builder.append(ch);
+            }
+        }
+        String string =  builder.toString();
+        Token token = new Token(string, Token.TYPE_STRING);
+        stacks.push(token);
+    }
+
+
+
+    /**
+     * scan el expression.
+     * item.ddd
+     * ${item.dd}
+     * $item.dd
+     * */
+    final void scanIdentifier(){
+        int start = position;
+        position++;
+        while (hasNext()){
+            char ch = code.charAt(position);
+            if(Character.isJavaIdentifierPart(ch)){
+               position++;
+            }else{
+                break;
+            }
+            //2.true
+        }
+        String el = code.substring(start, position);
+        if(el.startsWith(Operators.DOLLAR_STR)){
+            if(el.length() == Operators.DOLLAR_STR.length()){
+                return;
+            }
+            el = el.substring(Operators.DOLLAR_STR.length());
+        }
+        int type = Token.TYPE_IDENTIFIER;
+        if(Operators.KEYWORDS.containsKey(el)){
+            if(!(!operators.isEmpty() && Operators.isDot(operators.peek().op))){
+                type = Token.TYPE_KEYWORD;
+            }
+        }
+        Token token = new Token(el, type);
+        stacks.push(token);
+    }
+
+
+    final boolean hasNext(){
+        return position < code.length();
+    }
+
+
+
+    final boolean hasNextToken(){
+        while (hasNext()){
+            char ch = code.charAt(position);
+            if(ch == ' '){
+                position++;
+                continue;
+            }
+            return  true;
+        }
+        return false;
+    }
+
+    final char nextToken(){
+        char ch = code.charAt(position);
+        while (ch == ' '){
+            position ++;
+            if(code.length() <= position){
+                break;
+            }
+            ch = code.charAt(position);
+        }
+        return ch;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/el/parse/Symbol.java b/android/sdk/src/main/java/org/apache/weex/el/parse/Symbol.java
new file mode 100644
index 0000000..2136633
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/el/parse/Symbol.java
@@ -0,0 +1,38 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.el.parse;
+
+/**
+ * Created by furture on 2017/8/29.
+ */
+
+public class Symbol {
+    public final String op;
+    public final int pos;
+    public Symbol(String op, int pos) {
+        this.op = op;
+        this.pos = pos;
+    }
+
+    /**
+    @Override
+    public String toString() {
+        return op;
+    }*/
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/el/parse/Token.java b/android/sdk/src/main/java/org/apache/weex/el/parse/Token.java
new file mode 100644
index 0000000..f0d6186
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/el/parse/Token.java
@@ -0,0 +1,89 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.el.parse;
+
+/**
+ * Created by furture on 2017/8/28.
+ */
+public class Token {
+
+    /**
+     * token's type
+     * */
+    public static final int TYPE_IDENTIFIER = 0;
+    public static final int TYPE_INT = 1;
+    public static final int TYPE_DOUBLE = 2;
+    public static final int TYPE_STRING = 3;
+    public static final int TYPE_KEYWORD = 4;
+    public static final int TYPE_OPERATOR = 5;
+    public static final int TYPE_BLOCK = 6;
+
+    public static final int TYPE_ARRAY = 7;
+
+
+
+    private String token;
+    private int type;
+
+    public Token(String token, int type){
+        this.token = token;
+        this.type = type;
+    }
+
+
+    /**
+     * stack should use array stack.
+     * execute token in context, and return value.
+     * */
+    public Object execute(Object context){
+        if(type == TYPE_IDENTIFIER){
+            return Operators.el(context, token);
+        }else if(type == TYPE_STRING){
+            return  token;
+        }else if(type == TYPE_INT){
+            try{
+                return  Integer.parseInt(token);
+            }catch (Exception e){
+                return 0;
+            }
+        }else if(type == TYPE_DOUBLE){
+            try{
+                return  Double.parseDouble(token);
+            }catch (Exception e){
+                return 0;
+            }
+        }else if(type == TYPE_KEYWORD){
+            return  Operators.KEYWORDS.get(token);
+        }
+        throw new IllegalArgumentException("unhandled token type " + type);
+    }
+
+    @Override
+    public String toString() {
+        return "{" + token + "," + type + '}';
+    }
+
+    public String getToken() {
+        return token;
+    }
+
+    public int getType() {
+        return type;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/font/FontAdapter.java b/android/sdk/src/main/java/org/apache/weex/font/FontAdapter.java
new file mode 100644
index 0000000..9140e60
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/font/FontAdapter.java
@@ -0,0 +1,56 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.font;
+
+import java.util.List;
+import java.util.concurrent.CopyOnWriteArrayList;
+
+public class FontAdapter {
+
+
+    private List<FontListener> mFontListener;
+
+    public FontAdapter(){
+        mFontListener = new CopyOnWriteArrayList<>();
+    }
+
+    public void addFontListener(FontListener fontListener){
+        mFontListener.add(fontListener);
+    }
+
+    public void removeFontListener(FontListener fontListener){
+        mFontListener.remove(fontListener);
+    }
+
+    public void onAddFontRule(String pageId, String fontFamily, String fontUrl){
+        synchronized (this){
+            for(FontListener fontListener : mFontListener){
+                fontListener.onAddFontRule(pageId, fontFamily, fontUrl);
+            }
+        }
+    }
+
+    public void onFontLoad(String fontFaimly, String fontUrl, String filePath){
+        synchronized (this) {
+            for (FontListener fontListener : mFontListener) {
+                fontListener.onFontLoad(fontFaimly, fontUrl, filePath);
+            }
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/font/FontListener.java b/android/sdk/src/main/java/org/apache/weex/font/FontListener.java
new file mode 100644
index 0000000..50cd1b9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/font/FontListener.java
@@ -0,0 +1,26 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.font;
+
+public interface FontListener {
+
+    public void onAddFontRule(String pageId, String fontFamily, String fontUrl);
+
+    public void onFontLoad(String fontFamily, String fontUrl, String filePath);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/http/Options.java b/android/sdk/src/main/java/org/apache/weex/http/Options.java
new file mode 100644
index 0000000..9a82f6b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/http/Options.java
@@ -0,0 +1,139 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.http;
+
+import java.util.HashMap;
+import java.util.Map;
+import org.apache.weex.common.*;
+import org.apache.weex.common.WXRequest;
+
+/**
+ * Created by sospartan on 5/19/16.
+ */
+class Options {
+  private String method;
+  private String url;
+  private Map<String, String> headers;
+  private String body;
+  private Type type = Type.text;
+  private int timeout = WXRequest.DEFAULT_TIMEOUT_MS;
+
+  private Options(String method,
+                  String url,
+                  Map<String, String> headers,
+                  String body,
+                  Type type,
+                  int timeout) {
+    this.method = method;
+    this.url = url;
+    this.headers = headers;
+    this.body = body;
+    this.type = type;
+    if (timeout == 0) {
+      timeout = WXRequest.DEFAULT_TIMEOUT_MS;
+    }
+    this.timeout = timeout;
+  }
+
+  public String getMethod() {
+    return method;
+  }
+
+  public String getUrl() {
+    return url;
+  }
+
+  public Map<String, String> getHeaders() {
+    return headers;
+  }
+
+  public String getBody() {
+    return body;
+  }
+
+  public Type getType() {
+    return type;
+  }
+
+  public int getTimeout() { return timeout; }
+
+  public enum Type {
+    json, text,jsonp
+  }
+
+  public static class Builder {
+    private String method;
+    private String url;
+    private Map<String, String> headers = new HashMap<>();
+    private String body;
+    private Type type;
+    private int timeout;
+
+    public Builder setMethod(String method) {
+      this.method = method;
+      return this;
+    }
+
+    public Builder setUrl(String url) {
+      this.url = url;
+      return this;
+    }
+
+    public Builder putHeader(String key,String value){
+      this.headers.put(key,value);
+      return this;
+    }
+
+    public Builder setBody(String body) {
+      this.body = body;
+      return this;
+    }
+
+    /**
+     * default text
+     * json = jsonp
+     * @param type
+     * @return
+       */
+    public Builder setType(String type) {
+      if(Type.json.name().equals(type)){
+        this.type = Type.json;
+      }else if(Type.jsonp.name().equals(type)){
+        this.type = Type.jsonp;
+      }else{
+        this.type = Type.text;
+      }
+      return this;
+    }
+
+    public Builder setType(Type type) {
+      this.type = type;
+      return this;
+    }
+
+    public Builder setTimeout(int timeout) {
+      this.timeout = timeout;
+      return this;
+    }
+
+    public Options createOptions() {
+      return new Options(method, url, headers, body, type, timeout);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/http/Status.java b/android/sdk/src/main/java/org/apache/weex/http/Status.java
new file mode 100644
index 0000000..69b3892
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/http/Status.java
@@ -0,0 +1,94 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.http;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Created by sospartan on 5/26/16.
+ */
+public class Status {
+  public static final String UNKNOWN_STATUS = "unknown status";
+  public static final String ERR_INVALID_REQUEST = "ERR_INVALID_REQUEST";
+  public static final String ERR_CONNECT_FAILED = "ERR_CONNECT_FAILED";
+
+  private static Map<String,String> statusMap = new HashMap<>();
+
+  static {
+    statusMap.put("100","Continue");
+    statusMap.put("101","Switching Protocol");
+    statusMap.put("200","OK");
+    statusMap.put("201","Created");
+    statusMap.put("202","Accepted");
+    statusMap.put("203","Non-Authoritative Information");
+    statusMap.put("204","No Content");
+    statusMap.put("205","Reset Content");
+    statusMap.put("206","Partial Content");
+    statusMap.put("300","Multiple Choice");
+    statusMap.put("301","Moved Permanently");
+    statusMap.put("302","Found");
+    statusMap.put("303","See Other");
+    statusMap.put("304","Not Modified");
+    statusMap.put("305","Use Proxy");
+    statusMap.put("306","unused");
+    statusMap.put("307","Temporary Redirect");
+    statusMap.put("308","Permanent Redirect");
+    statusMap.put("400","Bad Request");
+    statusMap.put("401","Unauthorized");
+    statusMap.put("402","Payment Required");
+    statusMap.put("403","Forbidden");
+    statusMap.put("404","Not Found");
+    statusMap.put("405","Method Not Allowed");
+    statusMap.put("406","Not Acceptable");
+    statusMap.put("407","Proxy Authentication Required");
+    statusMap.put("408","Request Timeout");
+    statusMap.put("409","Conflict");
+    statusMap.put("410","Gone");
+    statusMap.put("411","Length Required");
+    statusMap.put("412","Precondition Failed");
+    statusMap.put("413","Payload Too Large");
+    statusMap.put("414","URI Too Long");
+    statusMap.put("415","Unsupported Media Type");
+    statusMap.put("416","Requested Range Not Satisfiable");
+    statusMap.put("417","Expectation Failed");
+    statusMap.put("418","I'm a teapot");
+    statusMap.put("421","Misdirected Request");
+    statusMap.put("426","Upgrade Required");
+    statusMap.put("428","Precondition Required");
+    statusMap.put("429","Too Many Requests");
+    statusMap.put("431","Request Header Fields Too Large");
+    statusMap.put("500","Internal Server Error");
+    statusMap.put("501","Not Implemented");
+    statusMap.put("502","Bad Gateway");
+    statusMap.put("503","Service Unavailable");
+    statusMap.put("504","Gateway Timeout");
+    statusMap.put("505","HTTP Version Not Supported");
+    statusMap.put("506","Variant Also Negotiates");
+    statusMap.put("507","Variant Also Negotiates");
+    statusMap.put("511","Network Authentication Required");
+  }
+
+  public static String getStatusText(String code){
+    if(!statusMap.containsKey(code))
+      return UNKNOWN_STATUS;
+    return statusMap.get(code);
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/http/WXHttpUtil.java b/android/sdk/src/main/java/org/apache/weex/http/WXHttpUtil.java
new file mode 100644
index 0000000..d8f2577
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/http/WXHttpUtil.java
@@ -0,0 +1,67 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.http;
+
+import android.content.Context;
+import android.text.TextUtils;
+
+import org.apache.weex.common.WXConfig;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.Map;
+
+/**
+ * Created by lixinke on 16/4/6.
+ */
+public class WXHttpUtil {
+
+  private static String sDefaultUA = null;
+
+  public static final String KEY_USER_AGENT = "user-agent";
+
+  public static String assembleUserAgent(Context ctx,Map<String, String> config) {
+    if (TextUtils.isEmpty(sDefaultUA)) {
+      StringBuilder builder = new StringBuilder();
+      builder.append(config.get(WXConfig.sysModel))
+          .append("(Android/")
+          .append(config.get(WXConfig.sysVersion))
+          .append(")")
+          .append(" ")
+
+          .append(TextUtils.isEmpty(config.get(WXConfig.appGroup)) ? "" : config.get(WXConfig.appGroup))
+          .append("(")
+          .append(TextUtils.isEmpty(config.get(WXConfig.appName)) ? "" : config.get(WXConfig.appName))
+          .append("/")
+          .append(config.get(WXConfig.appVersion))
+          .append(")")
+          .append(" ")
+
+          .append("Weex/")
+          .append(config.get(WXConfig.weexVersion))
+          .append(" ")
+
+          .append(TextUtils.isEmpty(config.get(WXConfig.externalUserAgent)) ? "" : config.get(WXConfig.externalUserAgent))
+          .append(TextUtils.isEmpty(config.get(WXConfig.externalUserAgent)) ? "" : " ")
+
+          .append(WXViewUtils.getScreenWidth(ctx) + "x" + WXViewUtils.getScreenHeight(ctx));
+      sDefaultUA = builder.toString();
+    }
+    return sDefaultUA;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/http/WXStreamModule.java b/android/sdk/src/main/java/org/apache/weex/http/WXStreamModule.java
new file mode 100644
index 0000000..ba3844b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/http/WXStreamModule.java
@@ -0,0 +1,383 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.http;
+
+import static org.apache.weex.http.WXHttpUtil.KEY_USER_AGENT;
+
+import android.net.Uri;
+import android.text.TextUtils;
+
+import com.alibaba.fastjson.JSONException;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXHttpAdapter;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.common.WXRequest;
+import org.apache.weex.common.WXResponse;
+import org.apache.weex.performance.WXStateRecord;
+import org.apache.weex.utils.WXLogUtils;
+import java.io.UnsupportedEncodingException;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+public class WXStreamModule extends WXModule {
+
+  public static final String STATUS_TEXT = "statusText";
+  public static final String STATUS = "status";
+  final IWXHttpAdapter mAdapter;
+  static final Pattern CHARSET_PATTERN = Pattern.compile("charset=([a-z0-9-]+)");
+
+  public WXStreamModule(){
+    this(null);
+  }
+  public WXStreamModule(IWXHttpAdapter adapter){
+    mAdapter = adapter;
+  }
+
+  /**
+   * send HTTP request
+   *
+   * @param params   {method:POST/GET/PUT/DELETE/HEAD/PATCH,url:http://xxx,header:{key:value},
+   *                 body:{key:value}}
+   * @param callback formate：handler(err, response)
+   */
+  @Deprecated
+  @JSMethod(uiThread = false)
+  public void sendHttp(JSONObject paramsObj, final String callback) {
+
+    String method = paramsObj.getString("method");
+    String url = paramsObj.getString("url");
+    JSONObject headers = paramsObj.getJSONObject("header");
+    String body = paramsObj.getString("body");
+    int timeout = paramsObj.getIntValue("timeout");
+
+    if (method != null) method = method.toUpperCase(Locale.ROOT);
+    Options.Builder builder = new Options.Builder()
+            .setMethod(!"GET".equals(method)
+                    &&!"POST".equals(method)
+                    &&!"PUT".equals(method)
+                    &&!"DELETE".equals(method)
+                    &&!"HEAD".equals(method)
+                    &&!"PATCH".equals(method)?"GET":method)
+            .setUrl(url)
+            .setBody(body)
+            .setTimeout(timeout);
+
+    extractHeaders(headers,builder);
+    sendRequest(builder.createOptions(), new ResponseCallback() {
+      @Override
+      public void onResponse(WXResponse response, Map<String, String> headers) {
+        if(callback != null && mWXSDKInstance != null)
+          WXBridgeManager.getInstance().callback(mWXSDKInstance.getInstanceId(), callback,
+                  (response == null || response.originalData == null) ? "{}" :
+                          readAsString(response.originalData,
+                                  headers!=null?getHeader(headers,"Content-Type"):""
+                          ));
+      }
+    }, null, mWXSDKInstance.getInstanceId(), mWXSDKInstance.getBundleUrl());
+  }
+
+  /**
+   *
+   * @param optionsStr request options include:
+   *  method: GET 、POST、PUT、DELETE、HEAD、PATCH
+   *  headers：object，request header
+   *  url:
+   *  body: "Any body that you want to add to your request"
+   *  type: json、text、jsonp（json）
+   * @param callback finished callback,response object:
+   *  status：status code
+   *  ok：boolean is success，http status200～299
+   *  statusText： statusText
+   *  data:  option type is json，data is object，not data is string
+   *  headers: headers
+   *
+   * @param progressCallback in progress callback,for download progress and request state,response object:
+   *  readyState: number connection status 1 OPENED 2 HEADERS_RECEIVED 3 LOADING
+   *  status：status code
+   *  length：headers Content-Length
+   *  statusText：statusText
+   *  headers: headers
+   */
+  @JSMethod(uiThread = false)
+  public void fetch(JSONObject optionsObj , final JSCallback callback, JSCallback progressCallback){
+    fetch(optionsObj, callback, progressCallback, mWXSDKInstance.getInstanceId(), mWXSDKInstance.getBundleUrl());
+  }
+
+  public void fetch(JSONObject optionsObj , final JSCallback callback, JSCallback progressCallback, final String instanceId, String bundleURL){
+    boolean invaildOption = optionsObj==null || optionsObj.getString("url")==null;
+    if(invaildOption){
+      if(callback != null) {
+        Map<String, Object> resp = new HashMap<>();
+        resp.put("ok", false);
+        resp.put(STATUS_TEXT, Status.ERR_INVALID_REQUEST);
+        callback.invoke(resp);
+      }
+      return;
+    }
+    String method = optionsObj.getString("method");
+    String url = optionsObj.getString("url");
+    JSONObject headers = optionsObj.getJSONObject("headers");
+    String body = optionsObj.getString("body");
+    String type = optionsObj.getString("type");
+    int timeout = optionsObj.getIntValue("timeout");
+
+    WXSDKInstance wxsdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (wxsdkInstance != null) {
+      if (wxsdkInstance.getStreamNetworkHandler() != null) {
+        String localUrl = wxsdkInstance.getStreamNetworkHandler().fetchLocal(url);
+        if (!TextUtils.isEmpty(localUrl)) {
+          url = localUrl;
+        }
+      }
+    }
+
+    if (method != null) method = method.toUpperCase(Locale.ROOT);
+    Options.Builder builder = new Options.Builder()
+        .setMethod(!"GET".equals(method)
+            &&!"POST".equals(method)
+            &&!"PUT".equals(method)
+            &&!"DELETE".equals(method)
+            &&!"HEAD".equals(method)
+            &&!"PATCH".equals(method)?"GET":method)
+        .setUrl(url)
+        .setBody(body)
+        .setType(type)
+        .setTimeout(timeout);
+
+    extractHeaders(headers,builder);
+    final Options options = builder.createOptions();
+    sendRequest(options, new ResponseCallback() {
+      @Override
+      public void onResponse(WXResponse response, Map<String, String> headers) {
+        if(callback != null) {
+          Map<String, Object> resp = new HashMap<>();
+          if(response == null|| "-1".equals(response.statusCode)){
+            resp.put(STATUS,-1);
+            resp.put(STATUS_TEXT,Status.ERR_CONNECT_FAILED);
+          }else {
+            int code = Integer.parseInt(response.statusCode);
+            resp.put(STATUS, code);
+            resp.put("ok", (code >= 200 && code <= 299));
+            if (response.originalData == null) {
+              resp.put("data", null);
+            } else {
+              String respData = readAsString(response.originalData,
+                  headers != null ? getHeader(headers, "Content-Type") : ""
+              );
+              try {
+                resp.put("data", parseData(respData, options.getType()));
+              } catch (JSONException exception) {
+                WXLogUtils.e("", exception);
+                resp.put("ok", false);
+                resp.put("data","{'err':'Data parse failed!'}");
+              }
+            }
+            resp.put(STATUS_TEXT, Status.getStatusText(response.statusCode));
+          }
+          resp.put("headers", headers);
+          WXStateRecord
+              .getInstance().recordAction(instanceId,"stream response code:"+(null!= response?response.statusCode:"null"));
+          callback.invoke(resp);
+        }
+      }
+    }, progressCallback, instanceId, bundleURL);
+  }
+
+  Object parseData(String data, Options.Type type) throws JSONException{
+    if( type == Options.Type.json){
+      return JSONObject.parse(data);
+    }else if( type == Options.Type.jsonp){
+      if(data == null || data.isEmpty()) {
+        return new JSONObject();
+      }
+      int b = data.indexOf("(")+1;
+      int e = data.lastIndexOf(")");
+      if(b ==0 || b >= e || e <= 0){
+        return new JSONObject();
+      }
+
+      data = data.substring(b,e);
+      return JSONObject.parse(data);
+    }else {
+      return data;
+    }
+  }
+
+  static String getHeader(Map<String,String> headers,String key){
+    if(headers == null||key == null){
+      return null;
+    }
+    if(headers.containsKey(key)){
+      return headers.get(key);
+    }else{
+      return headers.get(key.toLowerCase(Locale.ROOT));
+    }
+  }
+
+
+
+  static String readAsString(byte[] data,String cType){
+    String charset = "utf-8";
+    if(cType != null){
+      Matcher matcher = CHARSET_PATTERN.matcher(cType.toLowerCase(Locale.ROOT));
+      if(matcher.find()){
+        charset = matcher.group(1);
+      }
+    }
+    try {
+      return new String(data,charset);
+    } catch (UnsupportedEncodingException e) {
+      WXLogUtils.e("", e);
+      return new String(data);
+    }
+  }
+
+
+  private void extractHeaders(JSONObject headers, Options.Builder builder){
+    //set user-agent
+    String UA = WXHttpUtil.assembleUserAgent(WXEnvironment.getApplication(),WXEnvironment.getConfig());
+    if(headers != null){
+      for (String key : headers.keySet()) {
+        if (key.equals(KEY_USER_AGENT)) {
+          UA = headers.getString(key);
+          continue;
+        }
+        builder.putHeader(key, headers.getString(key));
+      }
+    }
+    builder.putHeader(KEY_USER_AGENT,UA);
+  }
+
+
+  private void sendRequest(Options options,ResponseCallback callback,JSCallback progressCallback,String instanceId, String bundleURL){
+    WXRequest wxRequest = new WXRequest();
+    wxRequest.method = options.getMethod();
+    wxRequest.url = WXSDKManager.getInstance().getURIAdapter().rewrite(bundleURL, URIAdapter.REQUEST,Uri.parse(options.getUrl())).toString();
+    wxRequest.body = options.getBody();
+    wxRequest.timeoutMs = options.getTimeout();
+    wxRequest.instanceId = instanceId;
+
+    if(options.getHeaders()!=null) {
+      if (wxRequest.paramMap == null) {
+        wxRequest.paramMap = options.getHeaders();
+      } else {
+        wxRequest.paramMap.putAll(options.getHeaders());
+      }
+    }
+
+    IWXHttpAdapter adapter = ( mAdapter==null) ? WXSDKManager.getInstance().getIWXHttpAdapter() : mAdapter;
+    if (adapter != null) {
+      adapter.sendRequest(wxRequest, new StreamHttpListener(callback,progressCallback));
+    }else{
+      WXLogUtils.e("WXStreamModule","No HttpAdapter found,request failed.");
+    }
+  }
+
+  private interface ResponseCallback{
+    void onResponse(WXResponse response, Map<String, String> headers);
+  }
+
+  private static class StreamHttpListener implements IWXHttpAdapter.OnHttpListener {
+    private ResponseCallback mCallback;
+    private JSCallback mProgressCallback;
+    private Map<String,Object> mResponse = new HashMap<>();
+    private Map<String,String> mRespHeaders;
+
+    private StreamHttpListener(ResponseCallback callback,JSCallback progressCallback) {
+      mCallback = callback;
+      mProgressCallback = progressCallback;
+    }
+
+
+    @Override
+    public void onHttpStart() {
+      if(mProgressCallback !=null) {
+        mResponse.put("readyState",1);//readyState: number 1 OPENED 2 HEADERS_RECEIVED 3 LOADING
+        mResponse.put("length",0);
+        mProgressCallback.invokeAndKeepAlive(new HashMap<>(mResponse));
+      }
+    }
+
+    @Override
+    public void onHttpUploadProgress(int uploadProgress) {
+
+    }
+
+    @Override
+    public void onHeadersReceived(int statusCode,Map<String,List<String>> headers) {
+      mResponse.put("readyState", 2);
+      mResponse.put("status", statusCode);
+
+      Map<String, String> simpleHeaders = new HashMap<>();
+      if (headers != null) {
+        Iterator<Map.Entry<String, List<String>>> it = headers.entrySet().iterator();
+        while (it.hasNext()) {
+          Map.Entry<String, List<String>> entry = it.next();
+          if (entry.getValue().size() == 0) {
+            continue;
+          } else if (entry.getValue().size() == 1)
+            simpleHeaders.put(entry.getKey() == null ? "_" : entry.getKey(), entry.getValue().get(0));
+          else {
+            simpleHeaders.put(entry.getKey() == null ? "_" : entry.getKey(), entry.getValue().toString());
+          }
+        }
+      }
+
+      mResponse.put("headers", simpleHeaders);
+      mRespHeaders = simpleHeaders;
+      if (mProgressCallback != null) {
+        mProgressCallback.invokeAndKeepAlive(new HashMap<>(mResponse));
+      }
+    }
+
+    @Override
+    public void onHttpResponseProgress(int loadedLength) {
+      mResponse.put("length",loadedLength);
+      if(mProgressCallback!=null){
+        mProgressCallback.invokeAndKeepAlive(new HashMap<>(mResponse));
+      }
+
+    }
+
+    @Override
+    public void onHttpFinish(final WXResponse response) {
+      //compatible with old sendhttp
+      if(mCallback!=null){
+        mCallback.onResponse(response, mRespHeaders);
+      }
+
+      if(WXEnvironment.isApkDebugable()){
+        WXLogUtils.d("WXStreamModule",response!=null && response.originalData!=null?new String(response.originalData):"response data is NUll!");
+      }
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/instance/InstanceOnFireEventInterceptor.java b/android/sdk/src/main/java/org/apache/weex/instance/InstanceOnFireEventInterceptor.java
new file mode 100644
index 0000000..dd5915d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/instance/InstanceOnFireEventInterceptor.java
@@ -0,0 +1,57 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.instance;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Created by furture on 2018/8/23.
+ */
+
+public abstract  class InstanceOnFireEventInterceptor {
+
+    private List<String> listenEvents;
+
+    public InstanceOnFireEventInterceptor() {
+        this.listenEvents = new ArrayList<>();
+    }
+
+    public void addInterceptEvent(String event){
+        if(!listenEvents.contains(event)){
+            this.listenEvents.add(event);
+        }
+    }
+
+    public List<String> getListenEvents() {
+        return listenEvents;
+    }
+
+    public void onInterceptFireEvent(String instanceId, String elementRef, String type, Map<String, Object> params, Map<String, Object> domChanges){
+        if(params == null){
+            return;
+        }
+        if(this.listenEvents.contains(type)){
+            onFireEvent(instanceId, elementRef, type, params, domChanges);
+        }
+    }
+
+    public  abstract void onFireEvent(String instanceId, String elementRef,String type, Map<String, Object> params, Map<String, Object> domChanges);
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/jsEngine/CallBackCode.java b/android/sdk/src/main/java/org/apache/weex/jsEngine/CallBackCode.java
new file mode 100644
index 0000000..428c66c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/jsEngine/CallBackCode.java
@@ -0,0 +1,32 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.jsEngine;
+
+public class CallBackCode {
+
+    public static final CallBackCode ERROR_JSENGINE_CRASHED = new CallBackCode(-1, "js engine Crashed");
+    public static final CallBackCode JSENGINE_INIT_FINISH = new CallBackCode(1, "js Engine init finished");
+    public int code;
+    public String msg;
+
+    private CallBackCode(int code, String msg) {
+        this.code = code;
+        this.msg = msg;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/jsEngine/EnvCallback.java b/android/sdk/src/main/java/org/apache/weex/jsEngine/EnvCallback.java
new file mode 100644
index 0000000..37287ec
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/jsEngine/EnvCallback.java
@@ -0,0 +1,23 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.jsEngine;
+
+public interface EnvCallback {
+    void error(CallBackCode code);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/jsEngine/JSBiz.java b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSBiz.java
new file mode 100644
index 0000000..c0195c4
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSBiz.java
@@ -0,0 +1,29 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.jsEngine;
+
+public class JSBiz {
+    private String bizName;
+    private String bizId;
+
+    public JSBiz(String id, String name) {
+        this.bizId = id;
+        this.bizName = name;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/jsEngine/JSContext.java b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSContext.java
new file mode 100644
index 0000000..e2324d9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSContext.java
@@ -0,0 +1,122 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.jsEngine;
+
+import org.apache.weex.base.CalledByNative;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.io.Serializable;
+import java.util.concurrent.ConcurrentHashMap;
+
+import static org.apache.weex.jsEngine.JSEngine.mCreatedJSContext;
+
+public class JSContext implements Serializable {
+    private ConcurrentHashMap<String, JSFunction> funcMap = new ConcurrentHashMap<>();
+    //JSEnginePtrContainer
+    private long mNativeContextPtr = 0;
+
+    private JSException mExceptionTransfer = null;
+
+    protected JSContext() {
+        WXBridgeManager.getInstance().post(new Runnable() {
+            @Override
+            public void run() {
+                mNativeContextPtr = nativeCreateContext();
+                mCreatedJSContext.put(mNativeContextPtr, JSContext.this);
+            }
+        });
+    }
+
+    public void registerException(JSException e) {
+        mExceptionTransfer = e;
+    }
+
+    public void destroy() {
+        mCreatedJSContext.remove(mNativeContextPtr);
+        mExceptionTransfer = null;
+        WXBridgeManager.getInstance().post(new Runnable() {
+            @Override
+            public void run() {
+                if (mNativeContextPtr != 0) {
+                    long tmp = mNativeContextPtr;
+                    mNativeContextPtr = 0;
+                    nativeDestroyContext(tmp);
+                }
+            }
+        });
+    }
+
+    public void bindFunction(final String name, final JSFunction function) {
+        WXBridgeManager.getInstance().post(new Runnable() {
+            @Override
+            public void run() {
+                funcMap.put(name, function);
+                nativeBindFunc(mNativeContextPtr, name);
+            }
+        });
+    }
+
+    public void unBindFunction(final String name) {
+        WXBridgeManager.getInstance().post(new Runnable() {
+            @Override
+            public void run() {
+                funcMap.remove(name);
+                nativeUnBindFunc(mNativeContextPtr, name);
+            }
+        });
+    }
+
+    public void Eval(final String script) {
+        WXBridgeManager.getInstance().post(new Runnable() {
+            @Override
+            public void run() {
+                nativeExecJS(mNativeContextPtr, script);
+            }
+        });
+    }
+
+
+    @CalledByNative
+    public String Invoke(String name, String args) {
+        JSFunction jsFunction = funcMap.get(name);
+        if (jsFunction != null) {
+            WXLogUtils.d("jsEngine invoke " + name + " arg:" + args);
+            return jsFunction.invoke(args);
+        }
+        return "";
+    }
+
+    @CalledByNative
+    public void Exception(String exception) {
+        if (exception != null && mExceptionTransfer != null) {
+            this.mExceptionTransfer.exception(exception);
+        }
+    }
+
+    private native long nativeCreateContext();
+
+    private native void nativeDestroyContext(long ctxPtr);
+
+    private native void nativeBindFunc(long ctxPtr, String name);
+
+    private native void nativeUnBindFunc(long ctxPtr, String name);
+
+    private native void nativeExecJS(long ctxPtr, String script);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/jsEngine/JSEngine.java b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSEngine.java
new file mode 100644
index 0000000..86b8d63
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSEngine.java
@@ -0,0 +1,99 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.jsEngine;
+
+import android.support.annotation.Nullable;
+import android.util.Log;
+
+import org.apache.weex.WXSDKEngine;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.io.Serializable;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+import static org.apache.weex.jsEngine.CallBackCode.ERROR_JSENGINE_CRASHED;
+import static org.apache.weex.jsEngine.CallBackCode.JSENGINE_INIT_FINISH;
+
+public class JSEngine implements Serializable {
+    private static JSEngine mJsEngine = null;
+
+    public static final ConcurrentHashMap<Long, JSContext> mCreatedJSContext = new ConcurrentHashMap<>();
+
+    private static final ConcurrentHashMap<JSBiz, EnvCallback> mEnvCallbacks = new ConcurrentHashMap<>();
+
+    private JSEngine() {
+    }
+
+    public static JSEngine getInstance() {
+        if (mJsEngine == null) {
+            synchronized (JSEngine.class) {
+                if (mJsEngine == null) {
+                    mJsEngine = new JSEngine();
+                }
+            }
+        }
+        return mJsEngine;
+    }
+
+    public void registerEnvCallback(JSBiz biz, EnvCallback e) {
+        if (biz == null || e == null) {
+            return;
+        }
+        mEnvCallbacks.put(biz, e);
+    }
+
+    public void unRegisterEnvCallback(JSBiz biz) {
+        if (biz == null) {
+            return;
+        }
+        mEnvCallbacks.remove(biz);
+    }
+
+
+    @Nullable
+    public JSContext createJSContext() {
+        if (!WXSDKEngine.isInitialized()) {
+            WXLogUtils.e("Create JSContext Failed because of weex has not been initialized");
+            return null;
+        }
+        return new JSContext();
+    }
+
+    public void engineInitFinished() {
+        for (Map.Entry<JSBiz, EnvCallback> next : mEnvCallbacks.entrySet()) {
+            next.getValue().error(JSENGINE_INIT_FINISH);
+        }
+    }
+
+    public void engineCrashed() {
+        for (Map.Entry<JSBiz, EnvCallback> next : mEnvCallbacks.entrySet()) {
+            next.getValue().error(ERROR_JSENGINE_CRASHED);
+        }
+
+        HashMap<Long, JSContext> map = new HashMap<>(mCreatedJSContext);
+        mCreatedJSContext.clear();
+        for (Map.Entry<Long, JSContext> next : map.entrySet()) {
+            JSContext value = next.getValue();
+            value.destroy();
+        }
+        map.clear();
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/jsEngine/JSException.java b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSException.java
new file mode 100644
index 0000000..cefa998
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSException.java
@@ -0,0 +1,23 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.jsEngine;
+
+public interface JSException {
+    void exception(String exception);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/jsEngine/JSFunction.java b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSFunction.java
new file mode 100644
index 0000000..ea71105
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/jsEngine/JSFunction.java
@@ -0,0 +1,23 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.jsEngine;
+
+public interface JSFunction {
+    String invoke(String args);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/layout/ContentBoxMeasurement.java b/android/sdk/src/main/java/org/apache/weex/layout/ContentBoxMeasurement.java
new file mode 100644
index 0000000..309c2bf
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/layout/ContentBoxMeasurement.java
@@ -0,0 +1,77 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.layout;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import org.apache.weex.base.CalledByNative;
+import org.apache.weex.common.Destroyable;
+import org.apache.weex.ui.component.WXComponent;
+
+import java.io.Serializable;
+
+public abstract class ContentBoxMeasurement implements Serializable, Destroyable {
+
+  @Nullable
+  protected WXComponent mComponent;
+
+  protected float mMeasureWidth;
+
+  protected float mMeasureHeight;
+
+  public ContentBoxMeasurement() {
+    mComponent = null;
+  }
+
+  public ContentBoxMeasurement(@NonNull WXComponent component) {
+    this.mComponent = component;
+  }
+
+  /** uiThread = false **/
+  @CalledByNative
+  public final void measure(float width, float height, int widthMeasureMode, int heightMeasureMode) {
+    measureInternal(width, height, widthMeasureMode, heightMeasureMode);
+  }
+
+  /** uiThread = false **/
+  public abstract void measureInternal(float width, float height, int widthMeasureMode, int heightMeasureMode);
+
+  /** uiThread = false **/
+  @CalledByNative
+  public abstract void layoutBefore();
+
+  /** uiThread = false **/
+  @CalledByNative
+  public abstract void layoutAfter(float computedWidth, float computedHeight);
+
+  @CalledByNative
+  public float getWidth() {
+    return mMeasureWidth;
+  }
+
+  @CalledByNative
+  public float getHeight() {
+    return mMeasureHeight;
+  }
+
+  @Override
+  public void destroy() {
+    mComponent = null;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/layout/MeasureMode.java b/android/sdk/src/main/java/org/apache/weex/layout/MeasureMode.java
new file mode 100644
index 0000000..c44b49b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/layout/MeasureMode.java
@@ -0,0 +1,29 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.layout;
+
+import java.io.Serializable;
+
+public class MeasureMode implements Serializable {
+
+  public static int EXACTLY = 1;
+
+  public static int UNSPECIFIED = 0;
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/layout/MeasureSize.java b/android/sdk/src/main/java/org/apache/weex/layout/MeasureSize.java
new file mode 100644
index 0000000..476027e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/layout/MeasureSize.java
@@ -0,0 +1,42 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.layout;
+
+import java.io.Serializable;
+
+public class MeasureSize implements Serializable{
+  private float width;
+  private float height;
+
+  public float getWidth() {
+    return width;
+  }
+
+  public void setWidth(float width) {
+    this.width = width;
+  }
+
+  public float getHeight() {
+    return height;
+  }
+
+  public void setHeight(float height) {
+    this.height = height;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/layout/measurefunc/TextContentBoxMeasurement.java b/android/sdk/src/main/java/org/apache/weex/layout/measurefunc/TextContentBoxMeasurement.java
new file mode 100755
index 0000000..dca61a0
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/layout/measurefunc/TextContentBoxMeasurement.java
@@ -0,0 +1,493 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.layout.measurefunc;
+
+import android.graphics.Canvas;
+import android.os.Build;
+import android.os.Looper;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.text.Editable;
+import android.text.Layout;
+import android.text.Spannable;
+import android.text.SpannableString;
+import android.text.SpannableStringBuilder;
+import android.text.Spanned;
+import android.text.SpannedString;
+import android.text.StaticLayout;
+import android.text.TextPaint;
+import android.text.TextUtils;
+import android.text.style.AlignmentSpan;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.support.annotation.WorkerThread;
+
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.TextDecorationSpan;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.dom.WXCustomStyleSpan;
+import org.apache.weex.dom.WXLineHeightSpan;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.layout.ContentBoxMeasurement;
+import org.apache.weex.layout.MeasureMode;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXText;
+import org.apache.weex.ui.component.WXTextDecoration;
+import org.apache.weex.utils.WXDomUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXResourceUtils;
+
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicReference;
+
+import static org.apache.weex.dom.WXStyle.UNSET;
+import static org.apache.weex.utils.WXUtils.isUndefined;
+
+/**
+ * Created by miomin on 2018/3/9.
+ */
+
+public class TextContentBoxMeasurement extends ContentBoxMeasurement {
+
+  private static final Canvas DUMMY_CANVAS = new Canvas();
+
+  public TextContentBoxMeasurement(WXComponent component) {
+    super(component);
+  }
+
+  class SetSpanOperation {
+
+    protected final int start, end, flag;
+    protected final Object what;
+
+    SetSpanOperation(int start, int end, Object what) {
+      this(start, end, what, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
+    }
+
+    SetSpanOperation(int start, int end, Object what, int flag) {
+      this.start = start;
+      this.end = end;
+      this.what = what;
+      this.flag = flag;
+    }
+
+    public void execute(Spannable sb) {
+      sb.setSpan(what, start, end, flag);
+    }
+  }
+
+  private static final String ELLIPSIS = "\u2026";
+  private boolean mIsColorSet = false;
+  private boolean hasBeenMeasured = false;
+  private int mColor;
+  private int mFontStyle = UNSET;
+  private int mFontWeight = UNSET;
+  private int mNumberOfLines = UNSET;
+  private int mFontSize = UNSET;
+  private int mLineHeight = UNSET;
+  private float previousWidth = Float.NaN;
+  private String mFontFamily = null;
+  private String mText = null;
+  private TextUtils.TruncateAt textOverflow;
+  private Layout.Alignment mAlignment;
+  private WXTextDecoration mTextDecoration = WXTextDecoration.NONE;
+  private TextPaint mTextPaint;
+  private @Nullable
+  Spanned spanned;
+  private @Nullable
+  Layout layout;
+  private AtomicReference<Layout> atomicReference = new AtomicReference<>();
+
+  /**
+   * uiThread = false
+   **/
+  @Override
+  public void layoutBefore() {
+    mTextPaint = new TextPaint(TextPaint.ANTI_ALIAS_FLAG);
+    hasBeenMeasured = false;
+    updateStyleAndText();
+    spanned = createSpanned(mText);
+  }
+
+  /**
+   * uiThread = false
+   **/
+  @Override
+  public void measureInternal(float width, float height, int widthMeasureMode, int heightMeasureMode) {
+    float measureWidth = width, measureHeight = height;
+    hasBeenMeasured = true;
+    float textWidth = getTextWidth(mTextPaint, width, widthMeasureMode == MeasureMode.EXACTLY);
+
+    if (textWidth > 0 && spanned != null) {
+      layout = createLayout(textWidth,null);
+      previousWidth = layout.getWidth();
+      if (Float.isNaN(width)) {
+        measureWidth = layout.getWidth();
+      } else {
+        measureWidth = Math.min(layout.getWidth(), measureWidth);
+      }
+
+      if (Float.isNaN(height)) {
+        measureHeight = layout.getHeight();
+      }
+    } else {
+      if (widthMeasureMode == MeasureMode.UNSPECIFIED) {
+        measureWidth = 0;
+      }
+      if (heightMeasureMode == MeasureMode.UNSPECIFIED) {
+        measureHeight = 0;
+      }
+    }
+    mMeasureWidth = measureWidth;
+    mMeasureHeight = measureHeight;
+  }
+
+  /**
+   * uiThread = false
+   **/
+  @Override
+  public void layoutAfter(float computedWidth, float computedHeight) {
+    if(mComponent!=null) {
+      if (hasBeenMeasured) {
+        if (layout != null &&
+            WXDomUtils
+                .getContentWidth(mComponent.getPadding(), mComponent.getBorder(), computedWidth)
+                != previousWidth) {
+          recalculateLayout(computedWidth);
+        }
+      } else {
+        updateStyleAndText();
+        recalculateLayout(computedWidth);
+      }
+      hasBeenMeasured = false;
+      if (layout != null && !layout.equals(atomicReference.get()) &&
+          Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
+        if (Thread.currentThread() != Looper.getMainLooper().getThread()) {
+          warmUpTextLayoutCache(layout);
+        }
+      }
+      swap();
+      WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(new Runnable() {
+        @Override
+        public void run() {
+          if(mComponent!=null) {
+            mComponent.updateExtra(atomicReference.get());
+          }
+        }
+      }, mComponent.getInstanceId());
+    }
+  }
+
+  private void updateStyleAndText() {
+    updateStyleImp(mComponent.getStyles());
+    mText = WXAttr.getValue(mComponent.getAttrs());
+  }
+
+  /**
+   * Force relayout the text, the text must layout before invoke this method.
+   *
+   * Internal method, do not invoke unless you what what you are doing
+   * @param isRTL
+   */
+  @RestrictTo(Scope.LIBRARY)
+  @WorkerThread
+  public void forceRelayout(){
+    //Generate Spans
+    layoutBefore();
+
+    //Measure
+    measure(previousWidth, Float.NaN, MeasureMode.EXACTLY, MeasureMode.UNSPECIFIED);
+
+    //Swap text layout to UI Thread
+    layoutAfter(previousWidth, Float.NaN);
+  }
+
+  /**
+   * Record the property according to the given style
+   *
+   * @param style the give style.
+   */
+  private void updateStyleImp(Map<String, Object> style) {
+    if (style != null) {
+      if (style.containsKey(Constants.Name.LINES)) {
+        int lines = WXStyle.getLines(style);
+        mNumberOfLines = lines > 0 ? lines : UNSET;
+      }
+      if (style.containsKey(Constants.Name.FONT_SIZE)) {
+        mFontSize = WXStyle.getFontSize(style, mComponent.getViewPortWidth());
+      }
+      if (style.containsKey(Constants.Name.FONT_WEIGHT)) {
+        mFontWeight = WXStyle.getFontWeight(style);
+      }
+      if (style.containsKey(Constants.Name.FONT_STYLE)) {
+        mFontStyle = WXStyle.getFontStyle(style);
+      }
+      if (style.containsKey(Constants.Name.COLOR)) {
+        mColor = WXResourceUtils.getColor(WXStyle.getTextColor(style));
+        mIsColorSet = mColor != Integer.MIN_VALUE;
+      }
+      if (style.containsKey(Constants.Name.TEXT_DECORATION)) {
+        mTextDecoration = WXStyle.getTextDecoration(style);
+      }
+      if (style.containsKey(Constants.Name.FONT_FAMILY)) {
+        mFontFamily = WXStyle.getFontFamily(style);
+      }
+      mAlignment = WXStyle.getTextAlignment(style, mComponent.isLayoutRTL());
+      textOverflow = WXStyle.getTextOverflow(style);
+      int lineHeight = WXStyle.getLineHeight(style, mComponent.getViewPortWidth());
+      if (lineHeight != UNSET) {
+        mLineHeight = lineHeight;
+      }
+    }
+  }
+
+  /**
+   * Update {@link #spanned} according to the give charSequence and styles
+   *
+   * @param text the give raw text.
+   * @return an Spanned contains text and spans
+   */
+  protected
+  @NonNull
+  Spanned createSpanned(String text) {
+    if (!TextUtils.isEmpty(text)) {
+      SpannableString spannable = new SpannableString(text);
+      updateSpannable(spannable, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
+      return spannable;
+    }
+    return new SpannableString("");
+  }
+
+  protected void updateSpannable(Spannable spannable, int spanFlag) {
+    int end = spannable.length();
+    if (mFontSize == UNSET) {
+      mTextPaint.setTextSize(WXText.sDEFAULT_SIZE);
+    }
+    else{
+      mTextPaint.setTextSize(mFontSize);
+    }
+
+    if (mLineHeight != UNSET) {
+      setSpan(spannable, new WXLineHeightSpan(mLineHeight), 0, end, spanFlag);
+    }
+
+    setSpan(spannable, new AlignmentSpan.Standard(mAlignment), 0, end, spanFlag);
+
+    if (mFontStyle != UNSET || mFontWeight != UNSET || mFontFamily != null) {
+      setSpan(spannable, new WXCustomStyleSpan(mFontStyle, mFontWeight, mFontFamily), 0, end, spanFlag);
+    }
+
+    if (mIsColorSet) {
+      mTextPaint.setColor(mColor);
+    }
+
+    if (mTextDecoration == WXTextDecoration.UNDERLINE || mTextDecoration == WXTextDecoration.LINETHROUGH) {
+      setSpan(spannable, new TextDecorationSpan(mTextDecoration), 0, end, spanFlag);
+    }
+  }
+
+  private void setSpan(Spannable spannable, Object what, int start, int end, int spanFlag){
+    spannable.setSpan(what, start, end, spanFlag);
+  }
+
+  /**
+   * Get text width according to constrain of outerWidth with and forceToDesired
+   *
+   * @param textPaint      paint used to measure text
+   * @param outerWidth     the width that css-layout desired.
+   * @param forceToDesired if set true, the return value will be outerWidth, no matter what the width
+   *                       of text is.
+   * @return if forceToDesired is false, it will be the minimum value of the width of text and
+   * outerWidth in case of outerWidth is defined, in other case, it will be outer width.
+   */
+  private float getTextWidth(TextPaint textPaint, float outerWidth, boolean forceToDesired) {
+    if (mText == null) {
+      if (forceToDesired) {
+        return outerWidth;
+      }
+      return 0;
+    }
+    else {
+      float textWidth;
+      if (forceToDesired) {
+        textWidth = outerWidth;
+      } else {
+        float desiredWidth = Layout.getDesiredWidth(spanned, textPaint);
+        if (isUndefined(outerWidth) || desiredWidth < outerWidth) {
+          textWidth = desiredWidth;
+        } else {
+          textWidth = outerWidth;
+        }
+      }
+      return textWidth;
+    }
+  }
+
+  /**
+   * Update layout according to {@link #mText} and span
+   *
+   * @param width          the specified width.
+   * @param forceWidth     If true, force the text width to the specified width, otherwise, text width
+   *                       may equals to or be smaller than the specified width.
+   * @param previousLayout the result of previous layout, could be null.
+   */
+  private
+  @NonNull
+  Layout createLayout(final float textWidth, @Nullable Layout previousLayout) {
+    Layout layout;
+    if (previousWidth != textWidth || previousLayout == null) {
+      layout = new StaticLayout(spanned, mTextPaint, (int) Math.ceil(textWidth),
+              Layout.Alignment.ALIGN_NORMAL, 1, 0, false);
+    } else {
+      layout = previousLayout;
+    }
+    if (mNumberOfLines != UNSET && mNumberOfLines > 0 && mNumberOfLines < layout.getLineCount()) {
+      int lastLineStart, lastLineEnd;
+      lastLineStart = layout.getLineStart(mNumberOfLines - 1);
+      lastLineEnd = layout.getLineEnd(mNumberOfLines - 1);
+      if (lastLineStart < lastLineEnd) {
+        SpannableStringBuilder builder = null;
+        if (lastLineStart > 0) {
+          builder = new SpannableStringBuilder(spanned.subSequence(0, lastLineStart));
+        } else {
+          builder = new SpannableStringBuilder();
+        }
+        Editable lastLine = new SpannableStringBuilder(spanned.subSequence(lastLineStart, lastLineEnd));
+        builder.append(truncate(lastLine, mTextPaint, (int) Math.ceil(textWidth), textOverflow));
+        adjustSpansRange(spanned, builder);
+        spanned = builder;
+        return new StaticLayout(spanned, mTextPaint, (int) Math.ceil(textWidth),
+                Layout.Alignment.ALIGN_NORMAL, 1, 0, false);
+      }
+    }
+    return layout;
+  }
+
+  /**
+   * Truncate the source span to the specified lines.
+   * Caller of this method must ensure that the lines of text is <strong>greater than desired lines and need truncate</strong>.
+   * Otherwise, unexpected behavior may happen.
+   *
+   * @param source     The source span.
+   * @param paint      the textPaint
+   * @param desired    specified lines.
+   * @param truncateAt truncate method, null value means clipping overflow text directly, non-null value means using ellipsis strategy to clip
+   * @return The spans after clipped.
+   */
+  private
+  @NonNull
+  Spanned truncate(@Nullable Editable source, @NonNull TextPaint paint,
+                   int desired, @Nullable TextUtils.TruncateAt truncateAt) {
+    Spanned ret = new SpannedString("");
+    if (!TextUtils.isEmpty(source) && source.length() > 0) {
+      if (truncateAt != null) {
+        source.append(ELLIPSIS);
+        Object[] spans = source.getSpans(0, source.length(), Object.class);
+        for (Object span : spans) {
+          int start = source.getSpanStart(span);
+          int end = source.getSpanEnd(span);
+          if (start == 0 && end == source.length() - 1) {
+            source.removeSpan(span);
+            source.setSpan(span, 0, source.length(), source.getSpanFlags(span));
+          }
+        }
+      }
+
+      StaticLayout layout;
+      int startOffset;
+
+      while (source.length() > 1) {
+        startOffset = source.length() - 1;
+        if (truncateAt != null) {
+          startOffset -= 1;
+        }
+        source.delete(startOffset, startOffset + 1);
+        layout = new StaticLayout(source, paint, desired, Layout.Alignment.ALIGN_NORMAL, 1, 0, false);
+        if (layout.getLineCount() <= 1) {
+          ret = source;
+          break;
+        }
+      }
+    }
+    return ret;
+  }
+
+  /**
+   * Adjust span range after truncate due to the wrong span range during span copy and slicing.
+   *
+   * @param beforeTruncate The span before truncate
+   * @param afterTruncate  The span after truncate
+   */
+  private void adjustSpansRange(@NonNull Spanned beforeTruncate, @NonNull Spannable afterTruncate) {
+    Object[] spans = beforeTruncate.getSpans(0, beforeTruncate.length(), Object.class);
+    for (Object span : spans) {
+      int start = beforeTruncate.getSpanStart(span);
+      int end = beforeTruncate.getSpanEnd(span);
+      if (start == 0 && end == beforeTruncate.length()) {
+        afterTruncate.removeSpan(span);
+        afterTruncate.setSpan(span, 0, afterTruncate.length(), beforeTruncate.getSpanFlags(span));
+      }
+    }
+  }
+
+  private void recalculateLayout(float computedWidth) {
+    float contentWidth = WXDomUtils.getContentWidth(mComponent.getPadding(), mComponent.getBorder(), computedWidth);
+    if (contentWidth > 0) {
+      spanned = createSpanned(mText);
+      if (spanned != null) {
+        layout = createLayout(contentWidth, layout);
+        previousWidth = layout.getWidth();
+      } else {
+        previousWidth = 0;
+      }
+    }
+  }
+
+  /**
+   * As warming up TextLayoutCache done in the DOM thread may manipulate UI operation,
+   * there may be some exception, in which case the exception is ignored. After all,
+   * this is just a warm up operation.
+   *
+   * @return false for warm up failure, otherwise returns true.
+   */
+  private boolean warmUpTextLayoutCache(Layout layout) {
+    boolean result;
+    try {
+      layout.draw(DUMMY_CANVAS);
+      result = true;
+    } catch (Exception e) {
+      WXLogUtils.eTag("TextWarmUp", e);
+      result = false;
+    }
+    return result;
+  }
+
+  /**
+   * Move the reference of current layout to the {@link AtomicReference} for further use,
+   * then clear current layout.
+   */
+  private void swap() {
+    if (layout != null) {
+      atomicReference.set(layout);
+      layout = null;
+    }
+    hasBeenMeasured = false;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/performance/IApmGenerator.java b/android/sdk/src/main/java/org/apache/weex/performance/IApmGenerator.java
new file mode 100644
index 0000000..45fb7bd
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/performance/IApmGenerator.java
@@ -0,0 +1,27 @@
+/**
+ * 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
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.performance;
+
+public interface IApmGenerator {
+    /**
+     * @param type apm type
+     * @return impl
+     */
+    IWXApmMonitorAdapter generateApmInstance(String type);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/performance/IWXAnalyzer.java b/android/sdk/src/main/java/org/apache/weex/performance/IWXAnalyzer.java
new file mode 100644
index 0000000..5015f01
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/performance/IWXAnalyzer.java
@@ -0,0 +1,35 @@
+/**
+ * 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
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 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.
+ */
+package org.apache.weex.performance;
+
+
+/**
+ * @author zhongcang
+ * @date 2018/2/28
+ */
+
+public interface IWXAnalyzer {
+
+  /**
+   *
+   * @param group   dataGroup
+   * @param module  dataModule in group
+   * @param type    dataType
+   * @param data   data (json)
+   */
+  void transfer(String group, String module, String type, String data);
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/performance/IWXApmMonitorAdapter.java b/android/sdk/src/main/java/org/apache/weex/performance/IWXApmMonitorAdapter.java
new file mode 100644
index 0000000..de1c56f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/performance/IWXApmMonitorAdapter.java
@@ -0,0 +1,82 @@
+/**
+ * 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
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.performance;
+
+public interface IWXApmMonitorAdapter {
+
+    /**
+     * start record
+     *
+     * @param instanceId instanceId
+     */
+    void onStart(String instanceId);
+
+    /**
+     * end record
+     */
+    void onEnd();
+
+    /**
+     * record event
+     */
+    void onEvent(String name, Object value);
+
+    /**
+     * record stage
+     */
+    void onStage(String name, long timestamp);
+
+    /**
+     * record property
+     */
+    void addProperty(String key, Object value);
+
+    /**
+     * record statistic
+     */
+    void addStats(String key, double value);
+
+    /**
+     * record subProcedure stage
+     */
+
+    void onSubProcedureStage(String procedureName, String stageName);
+
+    /**
+     * record SubProcedure event
+     */
+
+    void onSubProcedureEvent(String procedureName, String eventName);
+
+    /**
+     * record subProcedure stats
+     */
+    void setSubProcedureStats(String procedureName, String name, double value);
+
+    /**
+     * record subProcedure properties
+     */
+    void setSubProcedureProperties(String procedureName, String name, Object value);
+
+    void onAppear();
+
+    void onDisappear();
+
+    String parseReportUrl(String originUrl);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/performance/WXAnalyzerDataTransfer.java b/android/sdk/src/main/java/org/apache/weex/performance/WXAnalyzerDataTransfer.java
new file mode 100644
index 0000000..17e069c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/performance/WXAnalyzerDataTransfer.java
@@ -0,0 +1,167 @@
+/**
+ * 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
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * 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.
+ */
+package org.apache.weex.performance;
+
+import java.util.Iterator;
+import java.util.List;
+
+import android.util.Log;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXJSExceptionInfo;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.WXUtils;
+import org.json.JSONObject;
+
+/**
+ * @author zhongcang
+ * @date 2018/2/28
+ */
+
+public class WXAnalyzerDataTransfer {
+
+  private static final String GROUP = "WXAnalyzer";
+  private static final String MODULE_ERROR = "WXError";
+  private static final String MODULE_WX_APM = "wxapm";
+  public static boolean isOpenPerformance = false;
+  public static final String INTERACTION_TAG = "wxInteractionAnalyzer";
+  private static boolean sOpenInteractionLog;
+
+
+  public static void transferPerformance(String instanceId,String type,String key,Object value)
+  {
+      if (!isOpenPerformance){
+          return;
+      }
+      if (sOpenInteractionLog && "stage".equals(type)){
+          Log.d(INTERACTION_TAG, "[client][stage]"+instanceId+","+key+","+value);
+      }
+      List<IWXAnalyzer> transferList = WXSDKManager.getInstance().getWXAnalyzerList();
+      if (null == transferList || transferList.size() == 0) {
+          return;
+      }
+
+      WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
+      if (null == instance){
+          return;
+      }
+
+      String data;
+      try {
+        data = new JSONObject().put(key,value).toString();
+      }catch (Exception e){
+        e.printStackTrace();
+        return;
+      }
+
+      Iterator<IWXAnalyzer> itr = transferList.iterator();
+      while (itr.hasNext()){
+          IWXAnalyzer item = itr.next();
+          item.transfer(MODULE_WX_APM, instance.getInstanceId(), type, data);
+      }
+  }
+
+  public static void transferInteractionInfo(WXComponent targetComponent){
+    if (!isOpenPerformance){
+      return;
+    }
+
+    List<IWXAnalyzer> transferList = WXSDKManager.getInstance().getWXAnalyzerList();
+    if (null == transferList || transferList.size() == 0) {
+      return;
+    }
+    long renderOriginDiffTime = WXUtils.getFixUnixTime() - targetComponent.getInstance().getWXPerformance().renderUnixTimeOrigin;
+    String data;
+    try{
+      data = new JSONObject()
+          .put("renderOriginDiffTime",renderOriginDiffTime)
+          .put("type",targetComponent.getComponentType())
+          .put("ref",targetComponent.getRef())
+          .put("style",targetComponent.getStyles())
+          .put("attrs",targetComponent.getAttrs())
+          .toString();
+    }catch (Exception e){
+      e.printStackTrace();
+      return;
+    }
+    for (IWXAnalyzer transfer : transferList) {
+      transfer.transfer(MODULE_WX_APM, targetComponent.getInstanceId(), "wxinteraction", data);
+    }
+  }
+
+
+  public static void transferError(WXJSExceptionInfo exceptionInfo, String instanceId) {
+    if (!WXEnvironment.isApkDebugable()) {
+      return;
+    }
+    List<IWXAnalyzer> transferList = WXSDKManager.getInstance().getWXAnalyzerList();
+    if (null == transferList || transferList.size() == 0) {
+      return;
+    }
+
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (null == instance) {
+      return;
+    }
+    WXErrorCode errorCode = exceptionInfo.getErrCode();
+    String data = "";
+    try {
+      data = new JSONObject()
+              .put("instanceId", instanceId)
+              .put("url", instance.getBundleUrl())
+              .put("errorCode", errorCode.getErrorCode())
+              .put("errorMsg", errorCode.getErrorMsg())
+              .put("errorGroup", errorCode.getErrorGroup())
+              .toString();
+    } catch (Exception e) {
+      e.printStackTrace();
+    }
+    for (IWXAnalyzer transfer : transferList) {
+      transfer.transfer(GROUP, MODULE_ERROR, errorCode.getErrorType().toString(), data);
+    }
+  }
+
+  public static void switchInteractionLog(final boolean isOpen){
+      if ( sOpenInteractionLog == isOpen || !WXEnvironment.JsFrameworkInit){
+          return;
+      }
+      sOpenInteractionLog = isOpen;
+      //for jsfm && jsengin
+      //TODO wait for JSFramework
+//      WXBridgeManager.getInstance().post(new Runnable() {
+//          @Override
+//          public void run() {
+//              WXJSObject[] args = {new WXJSObject(isOpen?1:0)};
+//              WXBridgeManager.getInstance().invokeExecJS(
+//                  "",
+//                  null,
+//                  "switchInteractionLog",
+//                  args,
+//                  false);
+//          }
+//      });
+      //for weex_core
+      WXBridgeManager.getInstance().registerCoreEnv("switchInteractionLog",String.valueOf(isOpen));
+  }
+
+  public static boolean isInteractionLogOpen(){
+     return sOpenInteractionLog;
+  }
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/performance/WXInstanceApm.java b/android/sdk/src/main/java/org/apache/weex/performance/WXInstanceApm.java
new file mode 100644
index 0000000..39d9019
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/performance/WXInstanceApm.java
@@ -0,0 +1,683 @@
+/**
+ * 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
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.performance;
+
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.CopyOnWriteArraySet;
+
+import android.graphics.Rect;
+import android.os.Handler;
+import android.os.Looper;
+import android.text.TextUtils;
+import android.util.Log;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXPerformance;
+import org.apache.weex.common.WXRenderStrategy;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+
+public class WXInstanceApm {
+
+    public static final String WEEX_PAGE_TOPIC = "weex_page";
+
+    /************** properties *****************/
+    public static final String KEY_PROPERTIES_ERROR_CODE = "wxErrorCode";
+    //public static final String KEY_PAGE_PROPERTIES_LAUNCH_ID = "wxLaunchId";
+    public static final String KEY_PAGE_PROPERTIES_BIZ_ID = "wxBizID";
+    public static final String KEY_PAGE_PROPERTIES_BUBDLE_URL = "wxBundleUrl";
+    public static final String KEY_PAGE_PROPERTIES_JSLIB_VERSION = "wxJSLibVersion";
+    public static final String KEY_PAGE_PROPERTIES_WEEX_VERSION = "wxSDKVersion";
+    public static final String KEY_PAGE_PROPERTIES_REQUEST_TYPE = "wxRequestType";
+    public static final String KEY_PAGE_PROPERTIES_CACHE_TYPE = "wxCacheType";
+    public static final String KEY_PAGE_PROPERTIES_CACHE_INFO = "wxZCacheInfo";
+    public static final String KEY_PAGE_PROPERTIES_JS_FM_INI = "wxJsFrameworkInit";
+    public static final String KEY_PAGE_PROPERTIES_CONTAINER_NAME = "wxContainerName";
+    public static final String KEY_PAGE_PROPERTIES_INSTANCE_TYPE = "wxInstanceType";
+    public static final String KEY_PAGE_PROPERTIES_PARENT_PAGE = "wxParentPage";
+    public static final String KEY_PAGE_PROPERTIES_BUNDLE_TYPE = "wxBundleType";
+    public static final String KEY_PAGE_PROPERTIES_RENDER_TYPE = "wxRenderType";
+    public static final String KEY_PAGE_PROPERTIES_UIKIT_TYPE = "wxUIKitType";
+
+    /************** stages *****************/
+    public static final String KEY_PAGE_STAGES_CONTAINER_READY = "wxContainerReady";
+    public static final String KEY_PAGE_STAGES_DOWN_BUNDLE_START = "wxStartDownLoadBundle";
+    public static final String KEY_PAGE_STAGES_DOWN_BUNDLE_END = "wxEndDownLoadBundle";
+    public static final String KEY_PAGE_STAGES_RENDER_ORGIGIN = "wxRenderTimeOrigin";
+    public static final String KEY_PAGE_STAGES_LOAD_BUNDLE_START = "wxStartLoadBundle";
+    public static final String KEY_PAGE_STAGES_LOAD_BUNDLE_END = "wxEndLoadBundle";
+    public static final String KEY_PAGE_STAGES_FIRST_INTERACTION_VIEW = "wxFirstInteractionView";
+    public static final String KEY_PAGE_STAGES_CREATE_FINISH= "wxJSBundleCreateFinish";
+    public static final String KEY_PAGE_STAGES_FSRENDER = "wxFsRender";
+    public static final String KEY_PAGE_STAGES_NEW_FSRENDER = "wxNewFsRender";
+    public static final String KEY_PAGE_STAGES_END_EXCUTE_BUNDLE = "wxEndExecuteBundle";
+    public static final String KEY_PAGE_STAGES_INTERACTION = "wxInteraction";
+    public static final String KEY_PAGE_STAGES_DESTROY = "wxDestroy";
+
+    //Custom preprocessing start, called when activity created or other time. Called by other activity
+    public static final String KEY_PAGE_STAGES_CUSTOM_PREPROCESS_START = "wxCustomPreprocessStart";
+    //Custom preprocessing end, called when you'are able to start weex render. Called by other activity
+    public static final String KEY_PAGE_STAGES_CUSTOM_PREPROCESS_END = "wxCustomPreprocessEnd";
+
+    /************** stats *****************/
+    public static final String KEY_PAGE_STATS_BUNDLE_SIZE = "wxBundleSize";
+    public static final String KEY_PAGE_STATS_FS_CALL_JS_TIME = "wxFSCallJsTotalTime";
+    public static final String KEY_PAGE_STATS_FS_CALL_JS_NUM = "wxFSCallJsTotalNum";
+    public static final String KEY_PAGE_STATS_FS_TIMER_NUM = "wxFSTimerCount";
+    public static final String KEY_PAGE_STATS_FS_CALL_NATIVE_TIME = "wxFSCallNativeTotalTime";
+    public static final String KEY_PAGE_STATS_FS_CALL_NATIVE_NUM = "wxFSCallNativeTotalNum";
+    public static final String KEY_PAGE_STATS_FS_CALL_EVENT_NUM = "wxFSCallEventTotalNum";
+    public static final String KEY_PAGE_STATS_FS_REQUEST_NUM = "wxFSRequestNum";
+    public static final String KEY_PAGE_STATS_CELL_EXCEED_NUM = "wxCellExceedNum";
+    public static final String KEY_PAGE_STATS_MAX_DEEP_VIEW = "wxMaxDeepViewLayer";
+    public static final String KEY_PAGE_STATS_MAX_DEEP_DOM = "wxMaxDeepVDomLayer";
+    public static final String KEY_PAGE_STATS_MAX_COMPONENT_NUM = "wxMaxComponentCount";
+    public static final String KEY_PAGE_STATS_WRONG_IMG_SIZE_COUNT = "wxWrongImgSizeCount";
+    public static final String KEY_PAGE_STATS_EMBED_COUNT = "wxEmbedCount";
+    public static final String KEY_PAGE_STATS_LARGE_IMG_COUNT = "wxLargeImgMaxCount";
+    public static final String KEY_PAGE_STATS_BODY_RATIO = "wxBodyRatio";
+    public static final String KEY_PAGE_STATS_SCROLLER_NUM = "wxScrollerCount";
+    public static final String KEY_PAGE_STATS_CELL_DATA_UN_RECYCLE_NUM = "wxCellDataUnRecycleCount";
+    public static final String KEY_PAGE_STATS_CELL_UN_RE_USE_NUM = "wxCellUnReUseCount";
+    public static final String KEY_PAGE_STATS_IMG_UN_RECYCLE_NUM = "wxImgUnRecycleCount";
+
+    public static final String KEY_PAGE_STATS_I_SCREEN_VIEW_COUNT = "wxInteractionScreenViewCount";
+    public static final String KEY_PAGE_STATS_I_ALL_VIEW_COUNT = "wxInteractionAllViewCount";
+    public static final String KEY_PAGE_STATS_I_COMPONENT_CREATE_COUNT = "wxInteractionComponentCreateCount";
+    public static final String KEY_PAGE_ANIM_BACK_NUM = "wxAnimationInBackCount";
+    public static final String KEY_PAGE_TIMER_BACK_NUM = "wxTimerInBackCount";
+    public static final String KEY_PAGE_STATS_ACTUAL_DOWNLOAD_TIME = "wxActualNetworkTime";
+
+    public static final String KEY_PAGE_STATS_IMG_LOAD_NUM = "wxImgLoadCount";
+    public static final String KEY_PAGE_STATS_IMG_LOAD_SUCCESS_NUM = "wxImgLoadSuccessCount";
+    public static final String KEY_PAGE_STATS_IMG_LOAD_FAIL_NUM = "wxImgLoadFailCount";
+    public static final String KEY_PAGE_STATS_NET_NUM = "wxNetworkRequestCount";
+    public static final String KEY_PAGE_STATS_NET_SUCCESS_NUM = "wxNetworkRequestSuccessCount";
+    public static final String KEY_PAGE_STATS_NET_FAIL_NUM = "wxNetworkRequestFailCount";
+    public static final String KEY_PAGE_STATS_JSLIB_INIT_TIME = "wxJSLibInitTime";
+    public static final String KEY_PAGE_STATS_VIEW_CREATE_COST = "wxViewCost";
+    public static final String KEY_PAGE_STATS_COMPONENT_CREATE_COST = "wxComponentCost";
+    public static final String KEY_PAGE_STATS_EXECUTE_JS_CALLBACK_COST = "wxExecJsCallBack";
+    public static final String KEY_PAGE_STATS_LAYOUT_TIME = "wxLayoutTime";
+
+
+    /************** value *****************/
+    public static final String VALUE_ERROR_CODE_DEFAULT = "0";
+    public static final String VALUE_BUNDLE_LOAD_LENGTH = "wxLoadedLength";
+
+    private String mInstanceId;
+    private IWXApmMonitorAdapter apmInstance;
+    private Map<String, Double> recordStatsMap;
+    public final Map<String, Long> stageMap;
+    private Map<String,Object> mPropertiesMap;
+    private boolean isFSEnd;
+    private boolean mHasInit = false;
+    private boolean mEnd = false;
+    private boolean hasRecordFistInteractionView =false;
+    public final Map<String,Object> extInfo;
+    public boolean forceStopRecordInteraction = false;
+    public Rect instanceRect;
+    public String reportPageName;
+    public boolean hasReportLayerOverDraw = false;
+    public boolean hasAddView;
+    private Handler mUIHandler;
+
+    public Set<String> exceptionRecord = new CopyOnWriteArraySet<String>();
+
+    private double interactionLayoutTime;
+    public long componentCreateTime;
+    private long interactionComponentCreateTime;
+    public long viewCreateTime;
+    private long interactionViewCreateTime;
+    //next version
+    private long wxExecJsCallBackTime;
+    private long interactionJsCallBackTime;
+
+
+    private boolean mHasRecordDetailData = false;
+
+    /**
+     * send performance value to js
+     **/
+    private boolean hasSendInteractionToJS = false;
+    public volatile boolean isReady = true;
+
+    public WXInstanceApm(String instanceId) {
+        mInstanceId = instanceId;
+        extInfo = new ConcurrentHashMap<>();
+        stageMap = new ConcurrentHashMap<>();
+        mUIHandler = new Handler(Looper.getMainLooper());
+        recordStatsMap = new ConcurrentHashMap<>();
+        mPropertiesMap = new ConcurrentHashMap<>();
+        IApmGenerator generator = WXSDKManager.getInstance().getApmGenerater();
+        if (null != generator) {
+            apmInstance = generator.generateApmInstance(WEEX_PAGE_TOPIC);
+        }
+    }
+
+    public void onInstanceReady(boolean isPreDownLoad){
+        this.isReady = true;
+        if (isPreDownLoad){
+            onStage(KEY_PAGE_STAGES_DOWN_BUNDLE_START);
+        }
+        doInit();
+        for (Map.Entry<String,Long> stage:stageMap.entrySet()){
+            sendStageInfo(stage.getKey(),stage.getValue());
+        }
+        for (Map.Entry<String,Double> stats:recordStatsMap.entrySet()){
+           sendStats(stats.getKey(),stats.getValue());
+        }
+        for (Map.Entry<String,Object> p:mPropertiesMap.entrySet()){
+           sendProperty(p.getKey(),p.getValue());
+        }
+    }
+
+    /**
+     * record event
+     */
+    public void onEvent(String name, Object value) {
+        if (null == apmInstance) {
+            return;
+        }
+        apmInstance.onEvent(name, value);
+    }
+
+    /**
+     * record stage
+     */
+    public void onStage(String name) {
+        long time =  WXUtils.getFixUnixTime();
+        onStageWithTime(name,time);
+    }
+
+    /**
+     *
+     * @param name stage
+     * @param time unixTime ,plz use WXUtils.getFixUnixTime
+     */
+    public void onStageWithTime(String name,long time){
+        if (mEnd){
+            return;
+        }
+        if (null == name){
+            return;
+        }
+        stageMap.put(name,time);
+        if (isReady){
+            sendStageInfo(name,time);
+        }
+    }
+
+    private void sendStageInfo(String name,long time){
+        if(WXAnalyzerDataTransfer.isOpenPerformance){
+            WXAnalyzerDataTransfer.transferPerformance(mInstanceId,"stage",name,time);
+        }
+
+        if (KEY_PAGE_STAGES_RENDER_ORGIGIN.equalsIgnoreCase(name)){
+            mUIHandler.postDelayed(jsPerformanceCallBack,8000);
+        }
+
+        if (null == apmInstance) {
+            return;
+        }
+
+        apmInstance.onStage(name, time);
+    }
+
+    private Runnable jsPerformanceCallBack = new Runnable() {
+        @Override
+        public void run() {
+            sendPerformanceToJS();
+        }
+    };
+
+    /**
+     * record property
+     */
+    public void addProperty(String key, Object value) {
+        if (mEnd){
+            return;
+        }
+        if (null == key || null == value){
+            return;
+        }
+        mPropertiesMap.put(key,value);
+        if (isReady){
+            sendProperty(key,value);
+        }
+    }
+
+    private void sendProperty(String key,Object value){
+        if(WXAnalyzerDataTransfer.isOpenPerformance){
+            WXAnalyzerDataTransfer.transferPerformance(mInstanceId,"properties",key,value);
+        }
+
+        if (null == apmInstance) {
+            return;
+        }
+        apmInstance.addProperty(key, value);
+    }
+
+    /**
+     * record statistic
+     */
+    public void addStats(String key, double value) {
+        if (mEnd){
+            return;
+        }
+        if (null == key){
+            return;
+        }
+        recordStatsMap.put(key,value);
+        if (isReady){
+            sendStats(key,value);
+        }
+    }
+
+    private void sendStats(String key,double value){
+        if(WXAnalyzerDataTransfer.isOpenPerformance){
+            WXAnalyzerDataTransfer.transferPerformance(mInstanceId,"stats",key,value);
+        }
+
+        if (null == apmInstance) {
+            return;
+        }
+        apmInstance.addStats(key, value);
+    }
+
+
+    public boolean hasInit(){
+        return mHasInit;
+    }
+
+    /**
+     * start record
+     */
+    public void doInit() {
+        if (!isReady){
+            return;
+        }
+        if (mHasInit){
+            return;
+        }
+        mHasInit = true;
+        if (null == apmInstance) {
+            return;
+        }
+        apmInstance.onStart(mInstanceId);
+        WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(mInstanceId);
+        String url = null == instance ? "unKnowUrl" : instance.getBundleUrl();
+        addProperty(KEY_PAGE_PROPERTIES_BUBDLE_URL, url);
+        addProperty(KEY_PROPERTIES_ERROR_CODE, VALUE_ERROR_CODE_DEFAULT);
+        addProperty(KEY_PAGE_PROPERTIES_JSLIB_VERSION, WXEnvironment.JS_LIB_SDK_VERSION);
+        addProperty(KEY_PAGE_PROPERTIES_WEEX_VERSION, WXEnvironment.WXSDK_VERSION);
+        addProperty(KEY_PAGE_PROPERTIES_WEEX_VERSION, WXEnvironment.WXSDK_VERSION);
+        addStats("wxReInitCount", WXBridgeManager.reInitCount);
+        if (null != instance){
+            addProperty(KEY_PAGE_PROPERTIES_UIKIT_TYPE, instance.getRenderType());
+        }
+
+        addProperty("wxUseRuntimeApi",WXEnvironment.sUseRunTimeApi);
+        if (instance != null && (instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER
+                || instance.getRenderStrategy() == WXRenderStrategy.DATA_RENDER_BINARY)) {
+            addProperty(KEY_PAGE_PROPERTIES_RENDER_TYPE, WXEnvironment.EAGLE);
+        }
+        if (null != instance) {
+            for (Map.Entry<String, String> entry : instance.getContainerInfo().entrySet()) {
+                addProperty(entry.getKey(), entry.getValue());
+            }
+        }
+    }
+
+    public void setPageName(String pageName) {
+        if (TextUtils.isEmpty(pageName)) {
+            WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(mInstanceId);
+            if (null != instance) {
+                pageName = instance.getContainerInfo().get(KEY_PAGE_PROPERTIES_CONTAINER_NAME);
+            }
+        }
+        reportPageName = null == apmInstance?pageName:apmInstance.parseReportUrl(pageName);
+        reportPageName = TextUtils.isEmpty(reportPageName) ? "emptyPageName" : reportPageName;
+        addProperty(KEY_PAGE_PROPERTIES_BIZ_ID, reportPageName);
+    }
+
+    public void onAppear(){
+        if (null == apmInstance) {
+            return;
+        }
+        apmInstance.onAppear();
+    }
+
+    public void onDisAppear(){
+        if (null == apmInstance) {
+            return;
+        }
+        apmInstance.onDisappear();
+    }
+
+    /**
+     * end record
+     */
+    public void onEnd() {
+        if (null == apmInstance || mEnd) {
+            return;
+        }
+        new Handler(Looper.getMainLooper()).removeCallbacks(delayCollectDataTask);
+        recordPerformanceDetailData();
+        exceptionRecord.clear();
+        mUIHandler.removeCallbacks(jsPerformanceCallBack);
+        onStage(KEY_PAGE_STAGES_DESTROY);
+        if (mHasInit && null != apmInstance){
+            apmInstance.onEnd();
+        }
+        mEnd = true;
+        if (WXEnvironment.isApkDebugable()){
+            printLog();
+        }
+    }
+
+    public void doDelayCollectData(){
+        new Handler(Looper.getMainLooper()).postDelayed(delayCollectDataTask,8000);
+    }
+
+    private Runnable delayCollectDataTask = new Runnable() {
+        @Override
+        public void run() {
+            recordPerformanceDetailData();
+        }
+    };
+
+
+    private void printLog(){
+        Long startDownLoad = stageMap.get(KEY_PAGE_STAGES_DOWN_BUNDLE_START);
+        Long endDownLoad = stageMap.get(KEY_PAGE_STAGES_DOWN_BUNDLE_END);
+        Long interaction = stageMap.get(KEY_PAGE_STAGES_INTERACTION);
+        Long containerReady = stageMap.get(KEY_PAGE_STAGES_CONTAINER_READY);
+        if (null != endDownLoad && null != startDownLoad){
+            WXLogUtils.d("test->", "downLoadTime: "+ (endDownLoad - startDownLoad));
+        }
+        if (null != endDownLoad && null != interaction){
+            WXLogUtils.d("test->", "renderTime: "+ (interaction - endDownLoad));
+        }
+        if (null != containerReady && null !=interaction){
+            WXLogUtils.d("test->", "showTime: "+ (interaction - containerReady));
+        }
+
+    }
+
+    public void arriveNewFsRenderTime(){
+        if (null == apmInstance){
+            return;
+        }
+        onStage(WXInstanceApm.KEY_PAGE_STAGES_NEW_FSRENDER);
+    }
+
+    public void arriveFSRenderTime() {
+        if (null == apmInstance){
+            return;
+        }
+        isFSEnd = true;
+        onStage(WXInstanceApm.KEY_PAGE_STAGES_FSRENDER);
+    }
+
+    public void arriveInteraction(WXComponent targetComponent) {
+        if (null == apmInstance || null == targetComponent || targetComponent.getInstance() == null) {
+            return;
+        }
+
+        if (WXAnalyzerDataTransfer.isOpenPerformance){
+            WXAnalyzerDataTransfer.transferInteractionInfo(targetComponent);
+        }
+
+
+        if (null == apmInstance){
+            return;
+        }
+
+        WXPerformance performanceRecord = targetComponent.getInstance().getWXPerformance();
+        if (null == performanceRecord){
+            return;
+        }
+
+        long curTime = WXUtils.getFixUnixTime();
+
+        if (WXAnalyzerDataTransfer.isInteractionLogOpen()){
+            Log.d(WXAnalyzerDataTransfer.INTERACTION_TAG, "[client][wxinteraction]"
+                + targetComponent.getInstance().getInstanceId()
+                +","+targetComponent.getComponentType()
+                +","+targetComponent.getRef()
+                +","+targetComponent.getStyles()
+                +","+targetComponent.getAttrs()
+            );
+        }
+
+        if (!hasRecordFistInteractionView){
+            onStage(KEY_PAGE_STAGES_FIRST_INTERACTION_VIEW);
+            hasRecordFistInteractionView = true;
+        }
+        if (forceStopRecordInteraction){
+            return;
+        }
+        long now = WXUtils.getFixUnixTime();
+        if (now - preUpdateTime > 50){
+            //for performance, reduce jni calls
+            WXBridgeManager.getInstance().onInteractionTimeUpdate(mInstanceId);
+            preUpdateTime = now;
+        }
+
+        interactionComponentCreateTime = componentCreateTime;
+        interactionViewCreateTime = viewCreateTime;
+        Double layoutTime = recordStatsMap.get("wxLayoutTime");
+        interactionLayoutTime = layoutTime ==null? 0:layoutTime;
+
+        performanceRecord.interactionTime = curTime - performanceRecord.renderUnixTimeOrigin;
+        performanceRecord.interactionRealUnixTime = System.currentTimeMillis();
+        onStageWithTime(KEY_PAGE_STAGES_INTERACTION,curTime);
+
+        updateDiffStats(KEY_PAGE_STATS_I_SCREEN_VIEW_COUNT, 1);
+        updateMaxStats(KEY_PAGE_STATS_I_ALL_VIEW_COUNT, performanceRecord.localInteractionViewAddCount);
+        WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
+        if (null != instance) {
+            updateMaxStats(KEY_PAGE_STATS_I_COMPONENT_CREATE_COUNT, instance.getWXPerformance().componentCount);
+        }
+    }
+
+    private long preUpdateTime = 0;
+
+    public void updateFSDiffStats(String name, double diffValue) {
+        if (null == apmInstance || isFSEnd) {
+            return;
+        }
+        updateDiffStats(name, diffValue);
+    }
+
+    public void recordPerformanceDetailData(){
+        if (mHasRecordDetailData){
+            return;
+        }
+        mHasRecordDetailData = true;
+        addStats(KEY_PAGE_STATS_VIEW_CREATE_COST,interactionViewCreateTime);
+        addStats(KEY_PAGE_STATS_COMPONENT_CREATE_COST,interactionComponentCreateTime);
+        addStats(KEY_PAGE_STATS_EXECUTE_JS_CALLBACK_COST,interactionJsCallBackTime);
+        addStats(KEY_PAGE_STATS_LAYOUT_TIME,interactionLayoutTime);
+    }
+
+    public void updateDiffStats(String name, double diffValue) {
+        if (null == apmInstance) {
+            return;
+        }
+        Double preVal = recordStatsMap.containsKey(name) ? recordStatsMap.get(name) : 0;
+        //fix by use ConcurrentHashMap,but not sure,so report if error still happen
+        if (null == preVal){
+            WXExceptionUtils.commitCriticalExceptionRT(
+                "",
+                WXErrorCode.WX_ERR_HASH_MAP_TMP,
+                "updateDiffStats",
+                "key : "+name,
+                null
+            );
+            return;
+        }
+
+        double currentValue = preVal + diffValue;
+        addStats(name, currentValue);
+    }
+
+    public void updateMaxStats(String name, double currentVal) {
+        if (null == apmInstance) {
+            return;
+        }
+        Double maxValue = recordStatsMap.containsKey(name) ? recordStatsMap.get(name) : 0;
+        //fix by use ConcurrentHashMap,but not sure,so report if error still happen
+        if (null == maxValue){
+            WXExceptionUtils.commitCriticalExceptionRT(
+                "",
+                WXErrorCode.WX_ERR_HASH_MAP_TMP,
+                "updateMaxStats",
+                "key : "+name,
+                null
+            );
+            return;
+        }
+        if (maxValue < currentVal) {
+            maxValue = currentVal;
+            addStats(name, maxValue);
+        }
+    }
+
+    public void updateRecordInfo(Map<String, Object> extParams) {
+        if (null == apmInstance || null == extParams) {
+            return;
+        }
+
+        addPropeyFromExtParms(KEY_PAGE_PROPERTIES_REQUEST_TYPE, KEY_PAGE_PROPERTIES_REQUEST_TYPE, extParams);
+        addPropeyFromExtParms("cacheType", KEY_PAGE_PROPERTIES_CACHE_TYPE, extParams);
+        addPropeyFromExtParms("zCacheInfo", KEY_PAGE_PROPERTIES_CACHE_INFO, extParams);
+
+        addStats(KEY_PAGE_STATS_JSLIB_INIT_TIME, WXEnvironment.sJSLibInitTime);
+        addProperty(KEY_PAGE_PROPERTIES_JS_FM_INI, WXEnvironment.JsFrameworkInit);
+
+        Object wxNetLibDownBundleTime = extParams.get("actualNetworkTime");
+        if (wxNetLibDownBundleTime instanceof Long) {
+            updateDiffStats(KEY_PAGE_STATS_ACTUAL_DOWNLOAD_TIME, ((Long)wxNetLibDownBundleTime).doubleValue());
+        }
+    }
+
+    private void addPropeyFromExtParms(String fromKey, String toKey, Map<String, Object> extParams) {
+        Object value = extParams.get(fromKey);
+        if (value instanceof String) {
+            addProperty(toKey, value);
+        }
+    }
+
+    /************** called by IWXHttpAdapter implementer *****************/
+
+    public void actionNetRequest() {
+        if (!isFSEnd) {
+            updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_REQUEST_NUM, 1);
+        }
+        updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_NET_NUM, 1);
+    }
+
+    public void actionNetResult(boolean succeed, String errorCode) {
+        if (succeed) {
+            updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_NET_SUCCESS_NUM, 1);
+        } else {
+            updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_NET_FAIL_NUM, 1);
+        }
+    }
+
+    /************** called by IWXImgLoaderAdapter implementer *****************/
+
+    public void actionLoadImg() {
+        updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_IMG_LOAD_NUM, 1);
+    }
+
+    public void actionLoadImgResult(boolean succeed, String errorCode) {
+        if (succeed) {
+            updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_IMG_LOAD_SUCCESS_NUM, 1);
+        } else {
+            updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_IMG_LOAD_FAIL_NUM, 1);
+        }
+    }
+
+    public void sendPerformanceToJS() {
+        if (hasSendInteractionToJS) {
+            return;
+        }
+        hasSendInteractionToJS = true;
+        WXSDKInstance instance = WXSDKManager.getInstance().getAllInstanceMap().get(mInstanceId);
+        if (null == instance) {
+            return;
+        }
+
+        Map<String,String> sendProperties = new HashMap<>(2);
+        sendProperties.put(KEY_PAGE_PROPERTIES_BIZ_ID,reportPageName);
+        sendProperties.put(KEY_PAGE_PROPERTIES_BUBDLE_URL,instance.getBundleUrl());
+
+        Map<String,Long> sendStage = new HashMap<>(1);
+        sendStage.put(KEY_PAGE_STAGES_INTERACTION,instance.getWXPerformance().interactionRealUnixTime);
+
+        Map<String, Object> data = new HashMap<>(2);
+        data.put("stage",sendStage);
+        data.put("properties",sendProperties);
+
+        instance.fireGlobalEventCallback("wx_apm", data);
+    }
+
+
+    public String toPerfString() {
+        Long start = stageMap.get(KEY_PAGE_STAGES_RENDER_ORGIGIN);
+        Long end = stageMap.get(KEY_PAGE_STAGES_INTERACTION);
+        Long wxNewFsRender = stageMap.get(KEY_PAGE_STAGES_NEW_FSRENDER);
+        StringBuilder builder = new StringBuilder();
+        if(start != null && end != null){
+            builder.append("interactiveTime " + (end - start) + "ms");
+        }
+        if(wxNewFsRender != null){
+            builder.append(" wxNewFsRender " + (wxNewFsRender) + "ms");
+        }
+        return builder.toString();
+   }
+
+   public void updateNativePerformanceData(Map<String,String> nativePerformanceData){
+        if (null == nativePerformanceData){
+            return;
+        }
+        for (Map.Entry<String,String> entry : nativePerformanceData.entrySet()){
+            double value = -1;
+            try {
+                value = Double.valueOf(entry.getValue());
+            }catch (Exception e){
+                e.printStackTrace();
+            }
+            if (value != -1){
+                recordStatsMap.put(entry.getKey(),value);
+            }
+        }
+   }
+ }
diff --git a/android/sdk/src/main/java/org/apache/weex/performance/WXStateRecord.java b/android/sdk/src/main/java/org/apache/weex/performance/WXStateRecord.java
new file mode 100644
index 0000000..00328ff
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/performance/WXStateRecord.java
@@ -0,0 +1,209 @@
+/**
+ * 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
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.weex.performance;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.ConcurrentLinkedQueue;
+
+import android.support.annotation.NonNull;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.utils.WXUtils;
+
+/**
+ * @author zhongcang
+ * @date 2019/6/19
+ */
+public class WXStateRecord {
+
+    private RecordList<Info> mExceptionHistory;
+    private RecordList<Info> mActionHistory;
+    private RecordList<Info> mJsfmInitHistory;
+    private RecordList<Info> mJscCrashHistory;
+    private RecordList<Info> mJscReloadHistory;
+    private RecordList<Info> mJsThradWatchHistory;
+    private RecordList<Info> mIPCExceptionHistory;
+
+    private static class SingleTonHolder {
+        private static final WXStateRecord S_INSTANCE = new WXStateRecord();
+    }
+
+    public static WXStateRecord getInstance() {
+        return SingleTonHolder.S_INSTANCE;
+    }
+
+    private WXStateRecord() {
+        mExceptionHistory = new RecordList<>(10);
+        mActionHistory = new RecordList<>(20);
+        mJsfmInitHistory = new RecordList<>(10);
+        mJscCrashHistory = new RecordList<>(10);
+        mJscReloadHistory = new RecordList<>(10);
+        mJsThradWatchHistory = new RecordList<>(20);
+        mIPCExceptionHistory = new RecordList<>(20);
+    }
+
+    /**
+     * check history exception (may be cause ws)
+     */
+    public void recordException(String instanceId, String exception) {
+        String shortException = exception.length() > 200 ?exception.substring(0,200) : exception;
+        recordCommon(mExceptionHistory,new Info(WXUtils.getFixUnixTime(), instanceId, shortException));
+    }
+
+    /**
+     * check history action (may be occupy cpu by preInstance or some task)
+     */
+    public void recordAction(String instanceId, String action) {
+        recordCommon(mActionHistory,new Info(WXUtils.getFixUnixTime(), instanceId, action));
+    }
+
+    public void recordIPCException (String instanceId,String exception){
+        String shortException = exception.length() > 200 ?exception.substring(0,200) : exception;
+        recordCommon(mIPCExceptionHistory,new Info(WXUtils.getFixUnixTime(), instanceId, shortException));
+    }
+
+    /**
+     * check onJSFMInit time,and we know when jsfm is init sucess in reloadJsEngine case
+     */
+    public void onJSFMInit() {
+        recoreJsfmInitHistory("setJsfmVersion");
+    }
+
+    public void recoreJsfmInitHistory(String msg){
+        recordCommon(mJsfmInitHistory,new Info(WXUtils.getFixUnixTime(), "JSFM", msg));
+    }
+
+    public void recordJsThreadWatch(String msg){
+        recordCommon(mJsThradWatchHistory,new Info(WXUtils.getFixUnixTime(), "jsWatch", msg));
+    }
+
+    /**
+     * check onJSEngineReload time,and we know how many times reload and each reload time
+     */
+    public void onJSEngineReload(String instanceId) {
+        recordCommon(mJscReloadHistory,new Info(WXUtils.getFixUnixTime(), instanceId, "onJSEngineReload"));
+    }
+
+    /**
+     * check jsc crash time,and we know how many times jscCrash and each crash time
+     */
+    public void onJSCCrash(String instanceId) {
+        recordCommon(mJscCrashHistory,new Info(WXUtils.getFixUnixTime(), instanceId, "onJSCCrash"));
+    }
+
+    private void recordCommon(RecordList<Info> list ,Info info){
+        if (null == list || null == info){
+            return;
+        }
+        try {
+            list.add(info);
+            if (!list.isEmpty() && list.size()>list.maxSize){
+                list.poll();
+            }
+        }catch (Throwable e){
+            e.getStackTrace();
+        }
+    }
+
+    public Map<String, String> getStateInfo() {
+        Map<String, String> stateInfo = new HashMap<>(5);
+        stateInfo.put("reInitCount", String.valueOf(WXBridgeManager.reInitCount));
+
+        int size = mExceptionHistory.size()+mActionHistory.size()+mJsfmInitHistory.size()
+            +mJscCrashHistory.size()+mJscReloadHistory.size()+mJsThradWatchHistory.size();
+
+        List<Info> reportTimeLineInfo = new ArrayList<>(size);
+        reportTimeLineInfo.addAll(mExceptionHistory);
+        reportTimeLineInfo.addAll(mActionHistory);
+        reportTimeLineInfo.addAll(mJsfmInitHistory);
+        reportTimeLineInfo.addAll(mJscCrashHistory);
+        reportTimeLineInfo.addAll(mJscReloadHistory);
+        reportTimeLineInfo.addAll(mJsThradWatchHistory);
+        reportTimeLineInfo.addAll(mIPCExceptionHistory);
+        Collections.sort(reportTimeLineInfo);
+        stateInfo.put("stateInfoList",reportTimeLineInfo.toString());
+
+        IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
+        if (null != adapter && "true".equalsIgnoreCase(adapter.getConfig("wxapm","dumpIpcPageInfo","true"))){
+            stateInfo.put("pageQueueInfo",WXBridgeManager.getInstance().dumpIpcPageInfo());
+        }
+        return stateInfo;
+    }
+
+    private static class RecordList<E> extends ConcurrentLinkedQueue<E> {
+        private int maxSize;
+
+        public RecordList(int maxSize) {
+            super();
+            this.maxSize = maxSize;
+        }
+    }
+
+    private static class Info implements Comparable<Info>{
+        private long time;
+        private String instanceId;
+        private String msg;
+
+        public Info(long time, String instance, String msg) {
+            this.time = time;
+            this.instanceId = instance;
+            this.msg = msg;
+        }
+
+        @Override
+        public String toString() {
+            return new StringBuilder()
+                .append('[').append(instanceId).append(',').append(time).append(',').append(msg).append("]->")
+                .toString();
+        }
+
+        @Override
+        public int compareTo(@NonNull Info next) {
+            if (this.time == next.time){
+                return 0;
+            }
+            return this.time > next.time? 1:-1;
+        }
+    }
+
+    public void startJSThreadWatchDog(){
+        WXBridgeManager.getInstance().post(jsThreadWatchTask);
+    }
+
+    private  long jsThreadTime =-1;
+
+    private Runnable jsThreadWatchTask = new Runnable() {
+        @Override
+        public void run() {
+            if (jsThreadTime == -1){
+                jsThreadTime = WXUtils.getFixUnixTime();
+            }
+            long diff = WXUtils.getFixUnixTime() - jsThreadTime;
+            recordJsThreadWatch("diff:"+diff);
+            jsThreadTime = WXUtils.getFixUnixTime();
+            WXBridgeManager.getInstance().postDelay(jsThreadWatchTask,500);
+        }
+    };
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/performance/WhiteScreenUtils.java b/android/sdk/src/main/java/org/apache/weex/performance/WhiteScreenUtils.java
new file mode 100644
index 0000000..0ea349c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/performance/WhiteScreenUtils.java
@@ -0,0 +1,176 @@
+/**
+ * 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
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.performance;
+
+import android.text.TextUtils;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewParent;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.utils.WXViewUtils;
+import org.json.JSONObject;
+
+/**
+ * @author zhongcang
+ * @date 2019/5/30
+ */
+public class WhiteScreenUtils {
+
+    public static boolean doWhiteScreenCheck() {
+        IWXConfigAdapter configAdapter = WXSDKManager.getInstance().getWxConfigAdapter();
+        if (null == configAdapter) {
+            return false;
+        }
+        double randomValue = Math.random() * 100;
+        double max = 100;
+        try {
+            String configValue = configAdapter.getConfig("wxapm", "new_ws_sampling", "100");
+            max = Double.valueOf(configValue);
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+        return randomValue < max;
+    }
+
+    public static boolean isWhiteScreen(WXSDKInstance instance) {
+        if (null == instance) {
+            return false;
+        }
+        View v = instance.getContainerView();
+        if (!(v instanceof ViewGroup)) {
+            return false;
+        }
+
+        if (!WXViewUtils.isViewVisible(v) || !checkParentVisible(v.getParent())){
+            return false;
+        }
+        if (isInWhiteList(instance)){
+            return false;
+        }
+        return !hasLeafViewOrSizeIgnore(v,3);
+    }
+
+    private static boolean isInWhiteList(WXSDKInstance instance){
+        IWXConfigAdapter configAdapter = WXSDKManager.getInstance().getWxConfigAdapter();
+        if (null == configAdapter){
+            return false;
+        }
+        String whiteList = configAdapter.getConfig("wxapm","ws_white_list",null);
+        if (TextUtils.isEmpty(whiteList)){
+            return false;
+        }
+        try {
+            String[] urlList = whiteList.split(";");
+            for (String whiteUrl : urlList){
+                if (instance.getBundleUrl() != null && instance.getBundleUrl().contains(whiteUrl)){
+                    return true;
+                }
+            }
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+
+        return false;
+    }
+
+    private static boolean checkParentVisible(ViewParent parent){
+        //root view getParent is null
+        if (!(parent instanceof View)){
+            return true;
+        }
+        View vp = (View)parent;
+        boolean visible = vp.getVisibility() == View.VISIBLE && vp.getAlpha()>0;
+        if (!visible){
+            return false;
+        }
+        return checkParentVisible(vp.getParent());
+    }
+
+    private static boolean hasLeafViewOrSizeIgnore(View v,int checkDeep) {
+
+        if (!(v instanceof ViewGroup)) {
+            return true;
+        }
+
+        if (checkDeep > 0){
+            if ( v.getHeight() < 10 || v.getWidth() < 10) {
+                return true;
+            }
+            checkDeep--;
+        }
+
+        ViewGroup group = (ViewGroup)v;
+        for (int i = 0; i < group.getChildCount(); i++) {
+            View child = group.getChildAt(i);
+            boolean res = hasLeafViewOrSizeIgnore(child,checkDeep);
+            if (res) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    /**
+     * get instance viewTree && component tree msg
+     */
+    public static String takeViewTreeSnapShot(WXSDKInstance instance) {
+        if (null == instance) {
+            return "nullInstance";
+        }
+        View v = instance.getContainerView();
+        JSONObject root = geViewDetailTreeMsg(v);
+        if (null != root) {
+            return root.toString();
+        }
+        return "";
+    }
+
+    private static JSONObject geViewDetailTreeMsg(View view) {
+        if (null == view) {
+            return null;
+        }
+        JSONObject node = new JSONObject();
+        try {
+            node.put("width", view.getWidth());
+            node.put("height", view.getHeight());
+            int[] location = new int[2];
+            location[0] = -1;
+            location[1] = -1;
+            view.getLocationOnScreen(location);
+            node.put("x", location[0]);
+            node.put("y", location[1]);
+
+            if (view instanceof ViewGroup) {
+                node.put("type", view.getClass().getSimpleName());
+                ViewGroup group = (ViewGroup)view;
+                for (int i = 0; i < group.getChildCount(); i++) {
+                    node.put("child_"+i, geViewDetailTreeMsg(group.getChildAt(i)));
+                }
+            } else {
+                node.put("type", view.getClass().getSimpleName());
+            }
+
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+        return node;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/render/WXAbstractRenderContainer.java b/android/sdk/src/main/java/org/apache/weex/render/WXAbstractRenderContainer.java
new file mode 100644
index 0000000..2fc3192
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/render/WXAbstractRenderContainer.java
@@ -0,0 +1,82 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.render;
+
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.util.AttributeSet;
+import android.view.MotionEvent;
+import android.widget.FrameLayout;
+import org.apache.weex.WXSDKInstance;
+import java.lang.ref.WeakReference;
+
+public class WXAbstractRenderContainer extends FrameLayout {
+
+    protected  WeakReference<WXSDKInstance> mSDKInstance;
+    protected boolean mHasConsumeEvent = false;
+
+    public WXAbstractRenderContainer(@NonNull Context context) {
+        super(context);
+    }
+
+    public WXAbstractRenderContainer(@NonNull Context context, @Nullable AttributeSet attrs) {
+        super(context, attrs);
+    }
+
+    public WXAbstractRenderContainer(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
+        super(context, attrs, defStyleAttr);
+    }
+
+    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
+    public WXAbstractRenderContainer(@NonNull Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) {
+        super(context, attrs, defStyleAttr, defStyleRes);
+    }
+
+    public void setSDKInstance(WXSDKInstance instance) {
+        mSDKInstance = new WeakReference<>(instance);
+    }
+
+    @Override
+    protected void onSizeChanged(int w, int h, int oldw, int oldh) {
+        super.onSizeChanged(w, h, oldw, oldh);
+        WXSDKInstance instance;
+        if (mSDKInstance != null && (instance = mSDKInstance.get()) != null) {
+            //re-render instance
+            instance.setSize(w, h);
+        }
+    }
+
+
+    @Override
+    public boolean dispatchTouchEvent(MotionEvent ev) {
+        mHasConsumeEvent = true;
+        return super.dispatchTouchEvent(ev);
+    }
+
+    public boolean hasConsumeEvent(){
+        return mHasConsumeEvent;
+    }
+
+    public void createInstanceRenderView(String instanceId){
+
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/tracing/Stopwatch.java b/android/sdk/src/main/java/org/apache/weex/tracing/Stopwatch.java
new file mode 100644
index 0000000..83f2f55
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/tracing/Stopwatch.java
@@ -0,0 +1,132 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.tracing;
+
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * Created by moxun on 2017/6/2.
+ */
+
+public class Stopwatch {
+  private static final ThreadLocal<Stopwatch> sThreadLocal = new ThreadLocal<>();
+  private long startNanos;
+  private List<ProcessEvent> splits = new ArrayList<>();
+  private long startMillis;
+
+  private static void prepare() {
+    if (sThreadLocal.get() == null) {
+      sThreadLocal.set(new Stopwatch());
+    }
+  }
+
+  public static void tick() {
+    if (WXTracing.isAvailable()) {
+      try {
+        prepare();
+        if (sThreadLocal.get().startNanos != 0L) {
+          WXLogUtils.w("Stopwatch", "Stopwatch is not reset");
+        }
+        sThreadLocal.get().startNanos = System.nanoTime();
+        sThreadLocal.get().startMillis = System.currentTimeMillis();
+      } catch (Throwable t) {
+        t.printStackTrace();
+      }
+    }
+  }
+
+  public static void split(String fname) {
+    if (WXTracing.isAvailable()) {
+      try {
+        ProcessEvent event = new ProcessEvent();
+        long start = sThreadLocal.get().startMillis;
+        double millis = tackAndTick();
+        event.fname = fname;
+        event.duration = millis;
+        event.startMillis = start;
+        sThreadLocal.get().splits.add(event);
+      } catch (Throwable throwable) {
+        throwable.printStackTrace();
+      }
+    }
+  }
+
+  public static List<ProcessEvent> getProcessEvents() {
+    if (WXTracing.isAvailable()) {
+      tack();
+      List<ProcessEvent> existedEvents = sThreadLocal.get().splits;
+      sThreadLocal.get().splits = new ArrayList<>();
+      return existedEvents;
+    } else {
+      return Collections.emptyList();
+    }
+  }
+
+  public static double tack() {
+    if (WXTracing.isAvailable()) {
+      try {
+        long startNanos = sThreadLocal.get().startNanos;
+        if (startNanos == 0L) {
+          WXLogUtils.w("Stopwatch", "Should call Stopwatch.tick() before Stopwatch.tack() called");
+        }
+        long nanos = System.nanoTime() - startNanos;
+        sThreadLocal.get().startNanos = 0L;
+        return nanosToMillis(nanos);
+      } catch (Throwable throwable) {
+        throwable.printStackTrace();
+      }
+    }
+    return -1;
+  }
+
+  public static long lastTickStamp() {
+    if (WXTracing.isAvailable()) {
+      try {
+        return sThreadLocal.get().startMillis;
+      } catch (Throwable t) {
+        t.printStackTrace();
+      }
+    }
+    return -1;
+  }
+
+  public static double tackAndTick() {
+    double ms = tack();
+    tick();
+    return ms;
+  }
+
+  public static double nanosToMillis(long nanos) {
+    return nanos / 1000000.0;
+  }
+
+  public static double millisUntilNow(long startNanos) {
+    return nanosToMillis(System.nanoTime() - startNanos);
+  }
+
+  public static class ProcessEvent {
+    public String fname;
+    public double duration;
+    public long startMillis;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/tracing/WXTracing.java b/android/sdk/src/main/java/org/apache/weex/tracing/WXTracing.java
new file mode 100644
index 0000000..834fb1c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/tracing/WXTracing.java
@@ -0,0 +1,129 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.tracing;
+
+import android.os.Looper;
+import android.util.SparseArray;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.ITracingAdapter;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.Map;
+import java.util.concurrent.atomic.AtomicInteger;
+
+/**
+ * Created by moxun on 2017/6/6.
+ */
+
+public class WXTracing {
+  private static final AtomicInteger sIdGenerator = new AtomicInteger(0);
+
+  public static int nextId() {
+    return sIdGenerator.getAndIncrement();
+  }
+
+  public static boolean isAvailable() {
+    return WXEnvironment.isApkDebugable();
+  }
+
+  public static synchronized void submit(TraceEvent event) {
+    ITracingAdapter tracingAdapter = WXSDKManager.getInstance().getTracingAdapter();
+    if (tracingAdapter != null) {
+      tracingAdapter.submitTracingEvent(event);
+    }
+  }
+
+  public static class TraceEvent {
+    public String fname;
+    public String tname;
+    public String ph;
+    public int traceId;
+    public long ts;
+    public String iid;
+    public String ref;
+    public String parentRef;
+    public String name;
+    public String classname;
+    public int parentId = -1;
+    public double duration;
+
+    /**
+     * Internal use
+     */
+    public SparseArray<TraceEvent> subEvents;
+    public String payload;
+    public double parseJsonTime;
+    public boolean isSegment;
+    public Map<String, Object> extParams;
+    public boolean firstScreenFinish;
+
+    private boolean submitted;
+
+    public TraceEvent() {
+      ts = System.currentTimeMillis();
+      traceId = nextId();
+      tname = currentThreadName();
+    }
+
+    public void submit() {
+      if (!submitted) {
+        submitted = true;
+        WXTracing.submit(this);
+      } else {
+        WXLogUtils.w("WXTracing", "Event " + traceId + " has been submitted.");
+      }
+    }
+  }
+
+  public static String currentThreadName() {
+    Thread thread = Thread.currentThread();
+    String name = thread.getName();
+
+    if ("WeexJSBridgeThread".equals(name)) {
+      return "JSThread";
+    } else if ("WeeXDomThread".equals(name)) {
+      return "DOMThread";
+    } else if (Looper.getMainLooper() == Looper.myLooper()) {
+      return "UIThread";
+    }
+
+    return name;
+  }
+
+  public static TraceEvent newEvent(String fname, String instanceId, int parentId) {
+    WXTracing.TraceEvent traceEvent = new TraceEvent();
+    traceEvent.fname = fname;
+    traceEvent.iid = instanceId;
+    traceEvent.traceId = WXTracing.nextId();
+    traceEvent.parentId = parentId;
+    return traceEvent;
+  }
+
+  public static class TraceInfo {
+    public int rootEventId;
+    public long domQueueTime;
+    public long uiQueueTime;
+    public long domThreadStart = -1;
+    public long domThreadNanos;
+    public long uiThreadStart = -1;
+    public long uiThreadNanos;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/ComponentCreator.java b/android/sdk/src/main/java/org/apache/weex/ui/ComponentCreator.java
new file mode 100644
index 0000000..c249182
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/ComponentCreator.java
@@ -0,0 +1,33 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+
+import java.lang.reflect.InvocationTargetException;
+
+/**
+ * Created by sospartan on 7/27/16.
+ */
+public interface ComponentCreator {
+  WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/ExternalLoaderComponentHolder.java b/android/sdk/src/main/java/org/apache/weex/ui/ExternalLoaderComponentHolder.java
new file mode 100644
index 0000000..1b2c680
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/ExternalLoaderComponentHolder.java
@@ -0,0 +1,103 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import android.util.Pair;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.bridge.Invoker;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Created by sospartan on 8/26/16.
+ */
+public class ExternalLoaderComponentHolder implements IFComponentHolder {
+  public static final String TAG = "SimpleComponentHolder";
+  private Map<String, Invoker> mPropertyInvokers;
+  private Map<String, Invoker> mMethodInvokers;
+  private final IExternalComponentGetter mClzGetter;
+  private final String mType;
+  private Class mClass;
+
+
+  public ExternalLoaderComponentHolder(String type,IExternalComponentGetter clzGetter) {
+    this.mClzGetter = clzGetter;
+    mType = type;
+  }
+
+  @Override
+  public void loadIfNonLazy() {
+  }
+
+  private synchronized boolean generate(){
+    if(mClass==null){
+      return false;
+    }
+
+    Pair<Map<String, Invoker>, Map<String, Invoker>> methodPair = SimpleComponentHolder.getMethods(mClass);
+    mPropertyInvokers = methodPair.first;
+    mMethodInvokers = methodPair.second;
+    return true;
+  }
+
+  @Override
+  public synchronized WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+    if (mClass == null) {
+      mClass = mClzGetter.getExternalComponentClass(mType, instance);
+    }
+    ComponentCreator creator = new SimpleComponentHolder.ClazzComponentCreator(mClass);
+    WXComponent component = creator.createInstance(instance, parent, basicComponentData);
+
+    component.bindHolder(this);
+    return component;
+  }
+
+  @Override
+  public synchronized Invoker getPropertyInvoker(String name){
+    if (mPropertyInvokers == null && !generate()) {
+      return null;
+    }
+
+    return mPropertyInvokers.get(name);
+  }
+
+  @Override
+  public Invoker getMethodInvoker(String name) {
+    if(mMethodInvokers == null && !generate()){
+      return null;
+    }
+    return mMethodInvokers.get(name);
+  }
+
+  @Override
+  public synchronized String[] getMethods() {
+    if(mMethodInvokers == null && !generate()){
+      //generate failed
+      return new String[0];
+    }
+    Set<String> keys = mMethodInvokers.keySet();
+    return keys.toArray(new String[keys.size()]);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/IExternalComponentGetter.java b/android/sdk/src/main/java/org/apache/weex/ui/IExternalComponentGetter.java
new file mode 100644
index 0000000..d78f535
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/IExternalComponentGetter.java
@@ -0,0 +1,29 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by zhengshihan on 16/8/25.
+ */
+public interface IExternalComponentGetter {
+    Class<? extends WXComponent> getExternalComponentClass(String type, WXSDKInstance instance);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/IExternalModuleGetter.java b/android/sdk/src/main/java/org/apache/weex/ui/IExternalModuleGetter.java
new file mode 100644
index 0000000..bc7ca92
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/IExternalModuleGetter.java
@@ -0,0 +1,30 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import android.content.Context;
+
+import org.apache.weex.common.WXModule;
+
+/**
+ * Created by zhengshihan on 16/8/25.
+ */
+public interface IExternalModuleGetter {
+    Class<? extends WXModule> getExternalModuleClass(String type, Context context);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/IFComponentHolder.java b/android/sdk/src/main/java/org/apache/weex/ui/IFComponentHolder.java
new file mode 100644
index 0000000..d3a21f2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/IFComponentHolder.java
@@ -0,0 +1,34 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import org.apache.weex.bridge.Invoker;
+import org.apache.weex.bridge.JavascriptInvokable;
+
+/**
+ * Created by sospartan on 6/23/16.
+ */
+public interface IFComponentHolder extends ComponentCreator, JavascriptInvokable {
+
+    /** Prepare component if not a lazy load componnet.**/
+    void loadIfNonLazy();
+
+    Invoker getPropertyInvoker(String name);
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/RenderContextImpl.java b/android/sdk/src/main/java/org/apache/weex/ui/RenderContextImpl.java
new file mode 100644
index 0000000..fe9d0e6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/RenderContextImpl.java
@@ -0,0 +1,77 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.dom.RenderContext;
+import org.apache.weex.ui.component.WXComponent;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+/**
+ * Class for rendering view. Method in this class should be run in main thread.
+ * This class is also <strong>not</storng> thread safe.
+ */
+class RenderContextImpl implements RenderContext {
+
+  private Map<String, WXComponent> mRegistry;
+  private WXSDKInstance mWXSDKInstance;
+
+  public RenderContextImpl(WXSDKInstance instance) {
+    mWXSDKInstance = instance;
+    mRegistry = new ConcurrentHashMap<>();
+  }
+
+  public void destroy() {
+    mWXSDKInstance = null;
+    try {
+      mRegistry.clear();
+    } catch (Throwable e) {
+      e.printStackTrace();
+    }
+  }
+
+  public WXSDKInstance getWXSDKInstance() {
+    return mWXSDKInstance;
+  }
+
+  @Override
+  public WXSDKInstance getInstance() {
+    return mWXSDKInstance;
+  }
+
+  @Override
+  public WXComponent getComponent(String ref) {
+    return mRegistry.get(ref);
+  }
+
+  public void registerComponent(String ref, WXComponent comp) {
+    mRegistry.put(ref, comp);
+  }
+
+  @Override
+  public WXComponent unregisterComponent(String ref) {
+    return mRegistry.remove(ref);
+  }
+
+  public int getComponentCount(){
+    return mRegistry.size();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/SimpleComponentHolder.java b/android/sdk/src/main/java/org/apache/weex/ui/SimpleComponentHolder.java
new file mode 100644
index 0000000..48c78ef
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/SimpleComponentHolder.java
@@ -0,0 +1,234 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import android.util.Pair;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.Invoker;
+import org.apache.weex.bridge.MethodInvoker;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXRuntimeException;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXComponentProp;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.lang.annotation.Annotation;
+import java.lang.reflect.Constructor;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.Set;
+import org.apache.weex.bridge.WXBridgeManager;
+
+/**
+ * Created by sospartan on 6/12/16.
+ */
+public class SimpleComponentHolder implements IFComponentHolder{
+  public static final String TAG = "SimpleComponentHolder";
+  private final Class<? extends WXComponent> mClz;
+  private Map<String, Invoker> mPropertyInvokers;
+  private Map<String, Invoker> mMethodInvokers;
+  private ComponentCreator mCreator;
+
+  public static class ClazzComponentCreator implements ComponentCreator{
+
+    private Constructor<? extends WXComponent> mConstructor;
+    private final Class<? extends WXComponent> mCompClz;
+
+    public ClazzComponentCreator(Class<? extends WXComponent> c){
+      mCompClz = c;
+    }
+
+    private void loadConstructor() {
+      Class<? extends WXComponent> c = mCompClz;
+      Constructor<? extends WXComponent> constructor;
+      try {
+        constructor = c.getConstructor(WXSDKInstance.class, WXVContainer.class, BasicComponentData.class);
+      } catch (NoSuchMethodException e) {
+        WXLogUtils.d("ClazzComponentCreator", "Use deprecated component constructor");
+        try {
+          //compatible deprecated constructor with 4 args
+          constructor = c.getConstructor(WXSDKInstance.class, WXVContainer.class, boolean.class, BasicComponentData.class);
+        } catch (NoSuchMethodException e1) {
+          try {
+            //compatible deprecated constructor with 5 args
+            constructor = c.getConstructor(WXSDKInstance.class, WXVContainer.class, String.class, boolean.class, BasicComponentData.class);
+          } catch (NoSuchMethodException e2) {
+            throw new WXRuntimeException("Can't find constructor of component.");
+          }
+        }
+      }
+      mConstructor = constructor;
+    }
+
+    @Override
+    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+      if(mConstructor == null){
+        loadConstructor();
+      }
+      int parameters = mConstructor.getParameterTypes().length;
+      WXComponent component;
+
+      if(parameters == 3){
+        component =  mConstructor.newInstance(instance,parent, basicComponentData);
+      }else if(parameters == 4){
+        component =  mConstructor.newInstance(instance,parent,false, basicComponentData);
+      }else{
+        //compatible deprecated constructor
+        component =  mConstructor.newInstance(instance,parent,instance.getInstanceId(),parent.isLazy());
+      }
+      return component;
+    }
+  }
+
+  public SimpleComponentHolder(Class<? extends WXComponent> clz) {
+    this(clz,new ClazzComponentCreator(clz));
+  }
+
+  public SimpleComponentHolder(Class<? extends WXComponent> clz,ComponentCreator customCreator) {
+    this.mClz = clz;
+    this.mCreator = customCreator;
+  }
+
+  @Override
+  public void loadIfNonLazy() {
+    Annotation[] annotations = mClz.getDeclaredAnnotations();
+    for (Annotation annotation :
+      annotations) {
+      if (annotation instanceof Component){
+        if(!((Component) annotation).lazyload() && mMethodInvokers == null){
+          generate();
+        }
+        return;
+      }
+    }
+  }
+
+  private synchronized void generate(){
+    if(WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d(TAG, "Generate Component:" + mClz.getSimpleName());
+    }
+
+    Pair<Map<String, Invoker>, Map<String, Invoker>> methodPair = getMethods(mClz);
+    mPropertyInvokers = methodPair.first;
+    mMethodInvokers = methodPair.second;
+  }
+
+  public static Pair<Map<String,Invoker>,Map<String,Invoker>> getMethods(Class clz){
+    Map<String, Invoker> methods = new HashMap<>();
+    Map<String, Invoker> mInvokers = new HashMap<>();
+
+    Annotation[] annotations;
+    Annotation anno;
+    try {
+      for (Method method : clz.getMethods()) {
+        try {
+          annotations = method.getDeclaredAnnotations();
+          for (int i = 0, annotationsCount = annotations.length;
+               i < annotationsCount; ++i) {
+            anno = annotations[i];
+            if(anno == null){
+              continue;
+            }
+            if (anno instanceof WXComponentProp) {
+              String name = ((WXComponentProp) anno).name();
+              methods.put(name, new MethodInvoker(method,true));
+              break;
+            }else if(anno instanceof JSMethod){
+              JSMethod methodAnno = (JSMethod)anno;
+              String name = methodAnno.alias();
+              if(JSMethod.NOT_SET.equals(name)){
+                name = method.getName();
+              }
+              mInvokers.put(name, new MethodInvoker(method,methodAnno.uiThread()));
+              break;
+            }
+          }
+        } catch (ArrayIndexOutOfBoundsException | IncompatibleClassChangeError e) {
+          //ignore: getDeclaredAnnotations may throw this
+        }
+      }
+    }catch (IndexOutOfBoundsException e){
+      e.printStackTrace();
+      //ignore: getMethods may throw this
+    }catch (Exception e){ // in meizhu mobile, throw class not found exception in getMethods
+      WXLogUtils.e(TAG, e);
+    }
+    return new Pair<>(methods,mInvokers);
+  }
+
+
+
+  @Override
+  public synchronized WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+    WXComponent component = mCreator.createInstance(instance, parent, basicComponentData);
+
+    component.bindHolder(this);
+    return component;
+  }
+
+  @Override
+  public synchronized Invoker getPropertyInvoker(String name){
+      if (mPropertyInvokers == null) {
+        generate();
+      }
+
+    return mPropertyInvokers.get(name);
+  }
+
+  @Override
+  public Invoker getMethodInvoker(String name) {
+    if(mMethodInvokers == null){
+      generate();
+    }
+    return mMethodInvokers.get(name);
+  }
+
+  @Override
+  public synchronized String[] getMethods() {
+    if(mMethodInvokers == null){
+      generate();
+    }
+    Set<String> keys = mMethodInvokers.keySet();
+    try {
+      return keys.toArray(new String[keys.size()]);
+    } catch (Throwable throwable) {
+      if(mClz != null) {
+        String name = mClz.getName();
+        String errorMsg = name + ": gen methods failed";
+        WXExceptionUtils.commitCriticalExceptionRT(null,
+                WXErrorCode.WX_KEY_EXCEPTION_INVOKE_REGISTER_COMPONENT,
+                WXBridgeManager.METHOD_REGISTER_COMPONENTS, errorMsg,
+                null);
+      }
+
+      return new String[1];
+    }
+
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/WXComponentRegistry.java b/android/sdk/src/main/java/org/apache/weex/ui/WXComponentRegistry.java
new file mode 100644
index 0000000..eee9be0
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/WXComponentRegistry.java
@@ -0,0 +1,146 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.WXException;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.cache.RegisterCache;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+import org.apache.weex.utils.cache.RegisterCache.ComponentCache;
+
+/**
+ * All components must be registered within this class before used.
+ */
+public class WXComponentRegistry {
+
+  private static Map<String, IFComponentHolder> sTypeComponentMap = new ConcurrentHashMap<>();
+  private static ArrayList<Map<String, Object>> sComponentInfos=new ArrayList<>();
+
+  public static synchronized boolean registerComponent(Map<String, ComponentCache> componentCacheMap) {
+    if (componentCacheMap.isEmpty())
+      return true;
+    final Iterator<Map.Entry<String, ComponentCache>> iterator = componentCacheMap.entrySet().iterator();
+    WXBridgeManager.getInstance().post(new Runnable() {
+      @Override
+      public void run() {
+        ArrayList<Map<String, Object>> coms = new ArrayList<>();
+        while (iterator.hasNext()) {
+          Map.Entry<String, ComponentCache> next = iterator.next();
+          try {
+            ComponentCache value = next.getValue();
+            Map<String, Object> registerInfo = value.componentInfo;
+            if (registerInfo == null) {
+              registerInfo = new HashMap<>();
+            }
+            registerInfo.put("type", value.type);
+            registerInfo.put("methods", value.holder.getMethods());
+            registerNativeComponent(value.type, value.holder);
+            sComponentInfos.add(registerInfo);
+            coms.add(registerInfo);
+          } catch (WXException e) {
+            e.printStackTrace();
+          }
+        }
+        WXSDKManager.getInstance().registerComponents(coms);
+      }
+    });
+    return true;
+  }
+
+  public static synchronized boolean registerComponent(final String type, final IFComponentHolder holder, final Map<String, Object> componentInfo) throws WXException {
+    if (holder == null || TextUtils.isEmpty(type)) {
+      return false;
+    }
+
+    if(RegisterCache.getInstance().cacheComponent(type,holder,componentInfo)) {
+      return true;
+    }
+
+    //execute task in js thread to make sure register order is same as the order invoke register method.
+    WXBridgeManager.getInstance()
+        .post(new Runnable() {
+      @Override
+      public void run() {
+        try {
+          Map<String, Object> registerInfo = componentInfo;
+          if (registerInfo == null){
+            registerInfo = new HashMap<>();
+          }
+
+          registerInfo.put("type",type);
+          registerInfo.put("methods",holder.getMethods());
+          registerNativeComponent(type, holder);
+          registerJSComponent(registerInfo);
+          sComponentInfos.add(registerInfo);
+        } catch (WXException e) {
+          WXLogUtils.e("register component error:", e);
+        }
+
+      }
+    });
+    return true;
+  }
+
+  private static boolean registerNativeComponent(String type, IFComponentHolder holder) throws WXException {
+    try {
+      holder.loadIfNonLazy();
+      sTypeComponentMap.put(type, holder);
+    }catch (ArrayStoreException e){
+      e.printStackTrace();
+      //ignore: ArrayStoreException: java.lang.String cannot be stored in an array of type java.util.HashMap$HashMapEntry[]
+    }
+    return true;
+  }
+
+  private static boolean registerJSComponent(Map<String, Object> componentInfo) throws WXException {
+    ArrayList<Map<String, Object>> coms = new ArrayList<>();
+    coms.add(componentInfo);
+    WXSDKManager.getInstance().registerComponents(coms);
+    return true;
+  }
+
+  public static IFComponentHolder getComponent(String type) {
+    return sTypeComponentMap.get(type);
+  }
+
+  public static void reload(){
+    WXBridgeManager.getInstance().post(new Runnable() {
+      @Override
+      public void run() {
+        try {
+          for(Map<String,Object> com:sComponentInfos){
+            registerJSComponent(com);
+          }
+        } catch (WXException e) {
+          WXLogUtils.e("", e);
+        }
+      }
+    });
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/WXRenderHandler.java b/android/sdk/src/main/java/org/apache/weex/ui/WXRenderHandler.java
new file mode 100644
index 0000000..58c7b7e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/WXRenderHandler.java
@@ -0,0 +1,42 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import android.os.Handler;
+import android.os.Looper;
+import android.os.Message;
+
+class WXRenderHandler extends Handler {
+
+    public WXRenderHandler() {
+        super(Looper.getMainLooper());
+    }
+
+    public final boolean post(String instanceId, Runnable r) {
+        Message msg = Message.obtain(this, r);
+        // Use what to match runnable. Make sure don't override callback method.
+        msg.what = instanceId.hashCode();
+        return sendMessageDelayed(msg, 0);
+    }
+
+    @Override
+    public void handleMessage(Message msg) {
+        super.handleMessage(msg);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/WXRenderManager.java b/android/sdk/src/main/java/org/apache/weex/ui/WXRenderManager.java
new file mode 100644
index 0000000..d401643
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/WXRenderManager.java
@@ -0,0 +1,311 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui;
+
+import android.opengl.GLES10;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXRuntimeException;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.dom.RenderContext;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.ui.action.BasicGraphicAction;
+import org.apache.weex.ui.action.GraphicActionBatchAction;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+import javax.microedition.khronos.egl.EGL10;
+import javax.microedition.khronos.egl.EGLConfig;
+import javax.microedition.khronos.egl.EGLContext;
+import javax.microedition.khronos.egl.EGLDisplay;
+import javax.microedition.khronos.egl.EGLSurface;
+
+
+/**
+ * Manager class for render operation, mainly for managing {@link RenderContextImpl}.
+ * This is <strong>not</strong> a thread-safe class
+ */
+public class WXRenderManager {
+
+  private volatile ConcurrentHashMap<String, RenderContextImpl> mRenderContext;
+  private WXRenderHandler mWXRenderHandler;
+  private String mCurrentBatchInstanceId = null;
+  private ArrayList<Map<String,Object>> mBatchActions = new ArrayList<>();
+  private final int MAX_DROP_FRAME_NATIVE_BATCH = 2000;
+  private final static  String sKeyAction = "Action";
+  private static int nativeBatchTimes = 0;
+  private static int mOpenGLRenderLimitValue = 0;
+
+  public WXRenderManager() {
+    mRenderContext = new ConcurrentHashMap<>();
+    mWXRenderHandler = new WXRenderHandler();
+  }
+
+  public RenderContext getRenderContext(String instanceId) {
+    return mRenderContext.get(instanceId);
+  }
+
+  public @Nullable
+  WXComponent getWXComponent(String instanceId, String ref) {
+    if (instanceId == null || TextUtils.isEmpty(ref)) {
+      return null;
+    }
+    RenderContext stmt = getRenderContext(instanceId);
+    return stmt == null ? null : stmt.getComponent(ref);
+  }
+
+  public WXSDKInstance getWXSDKInstance(String instanceId) {
+    RenderContextImpl statement = mRenderContext.get(instanceId);
+    if (statement == null) {
+      return null;
+    }
+    return statement.getWXSDKInstance();
+  }
+
+    public static int getOpenGLRenderLimitValue() {
+      if(mOpenGLRenderLimitValue == 0){
+          int maxsize = 0;
+              try {
+                  EGL10 egl = (EGL10) EGLContext.getEGL();
+                  EGLDisplay dpy = egl.eglGetDisplay(EGL10.EGL_DEFAULT_DISPLAY);
+                  int[] vers = new int[2];
+                  egl.eglInitialize(dpy, vers);
+                  int[] configAttr = {
+                          EGL10.EGL_COLOR_BUFFER_TYPE, EGL10.EGL_RGB_BUFFER,
+                          EGL10.EGL_LEVEL, 0,
+                          EGL10.EGL_SURFACE_TYPE, EGL10.EGL_PBUFFER_BIT,
+                          EGL10.EGL_NONE};
+                  EGLConfig[] configs = new EGLConfig[1];
+                  int[] numConfig = new int[1];
+                  egl.eglChooseConfig(dpy, configAttr, configs, 1, numConfig);
+                  if(numConfig[0] == 0){
+                      //There is something wrong with opengl environment.
+                      maxsize = -1;
+                      egl.eglTerminate(dpy);
+                  }else {
+                      EGLConfig config = configs[0];
+                      int[] surfAttr = {
+                              EGL10.EGL_WIDTH, 64,
+                              EGL10.EGL_HEIGHT, 64,
+                              EGL10.EGL_NONE};
+                      EGLSurface surf = egl.eglCreatePbufferSurface(dpy, config, surfAttr);
+                      final int EGL_CONTEXT_CLIENT_VERSION = 0x3098;// missing in EGL10
+                      int[] ctxAttrib = {
+                              EGL_CONTEXT_CLIENT_VERSION, 1,
+                              EGL10.EGL_NONE};
+                      EGLContext ctx = egl.eglCreateContext(dpy, config, EGL10.EGL_NO_CONTEXT, ctxAttrib);
+                      egl.eglMakeCurrent(dpy, surf, surf, ctx);
+                      int[] maxSize = new int[1];
+                      GLES10.glGetIntegerv(GLES10.GL_MAX_TEXTURE_SIZE, maxSize, 0);
+                      egl.eglMakeCurrent(dpy, EGL10.EGL_NO_SURFACE, EGL10.EGL_NO_SURFACE,
+                              EGL10.EGL_NO_CONTEXT);
+                      egl.eglDestroySurface(dpy, surf);
+                      egl.eglDestroyContext(dpy, ctx);
+                      egl.eglTerminate(dpy);
+                      maxsize = maxSize[0];
+                  }
+              } catch(Exception e){
+                  WXLogUtils.e(WXLogUtils.getStackTrace(e));
+              }
+          mOpenGLRenderLimitValue = maxsize;
+      }
+      return mOpenGLRenderLimitValue;
+    }
+
+  @RestrictTo(Scope.LIBRARY)
+  public void postOnUiThread(Runnable runnable, long delayMillis) {
+    mWXRenderHandler.postDelayed(WXThread.secure(runnable), delayMillis);
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  public void postOnUiThread(Runnable runnable,final String instanceId){
+    mWXRenderHandler.post(instanceId, WXThread.secure(runnable));
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  public void postOnUiThread(Runnable runnable){
+    mWXRenderHandler.post(WXThread.secure(runnable));
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  public void removeTask(Runnable runnable){
+    mWXRenderHandler.removeCallbacks(runnable);
+  }
+
+  /**
+   * Remove renderStatement, can only be invoked in UI thread.
+   *
+   * @param instanceId {@link WXSDKInstance#mInstanceId}
+   */
+  public void removeRenderStatement(String instanceId) {
+    if (!WXUtils.isUiThread()) {
+      throw new WXRuntimeException("[WXRenderManager] removeRenderStatement can only be called in main thread");
+    }
+    RenderContextImpl statement = mRenderContext.remove(instanceId);
+
+    if (statement != null) {
+      statement.destroy();
+    }
+    if(instanceId == null) {
+      mWXRenderHandler.removeCallbacksAndMessages(null);
+    } else {
+      // use hashCode to match message's what.
+      mWXRenderHandler.removeMessages(instanceId.hashCode());
+    }
+  }
+
+  private void postAllStashedGraphicAction(final String instanceId,final BasicGraphicAction action) {
+      final RenderContextImpl renderContext = mRenderContext.get(instanceId);
+
+      /// keep actions if renderContext still exist
+      ArrayList<Map<String, Object>> tmpList = null;
+      if (renderContext != null) {
+        tmpList = new ArrayList<>(mBatchActions);
+      }
+
+      // clear stashed actions
+      this.mBatchActions.clear();
+      mCurrentBatchInstanceId = null;
+      nativeBatchTimes = 0;
+
+      // return if renderContext has been destroyed
+      if (renderContext == null) {
+        return;
+      }
+
+      /// post actions if renderContext still exist
+      ArrayList<BasicGraphicAction> actions = new ArrayList<>(tmpList.size());
+      for (int i = 0 ; i < tmpList.size(); i ++) {
+          Map<String, Object> item = tmpList.get(i);
+          Object mustBeAction = item.get(sKeyAction);
+          if (!(mustBeAction instanceof BasicGraphicAction)) {
+            continue;
+          }
+          BasicGraphicAction tmpAction = (BasicGraphicAction)mustBeAction;
+          if (tmpAction.mActionType == BasicGraphicAction.ActionTypeBatchBegin || tmpAction.mActionType == BasicGraphicAction.ActionTypeBatchEnd) {
+            continue;
+          }
+          actions.add(tmpAction);
+      }
+      postGraphicAction(instanceId, new GraphicActionBatchAction(action.getWXSDKIntance(),action.getRef(), actions));
+  }
+
+  public void postGraphicAction(final String instanceId, final BasicGraphicAction action) {
+    final RenderContextImpl renderContext = mRenderContext.get(instanceId);
+    if (renderContext == null) {
+      return;
+    }
+
+    // If more than two pages exist and mCurrentBatchInstanceId not matches new instanceId, we will post all stashed actions at once.
+    // That will cause losing efficacy of batch action, but it is acceptable because it's not serious problem.
+    if (mCurrentBatchInstanceId != null && instanceId != null && !mCurrentBatchInstanceId.equals(instanceId) && mBatchActions.size() > 0) {
+      Map<String, Object> lastItem = mBatchActions.get(mBatchActions.size() - 1);
+      Object mustBeAction = lastItem.get(sKeyAction);
+      if (mustBeAction instanceof BasicGraphicAction) {
+        BasicGraphicAction lastAction = (BasicGraphicAction)mustBeAction;
+        postAllStashedGraphicAction(mCurrentBatchInstanceId, lastAction);
+      }
+    }
+
+    if (action.mActionType == BasicGraphicAction.ActionTypeBatchEnd) {
+        postAllStashedGraphicAction(instanceId,action);
+        return;
+    } else if (action.mActionType == BasicGraphicAction.ActionTypeBatchBegin || this.mBatchActions.size() > 0 ) {
+        nativeBatchTimes ++ ;
+        if (nativeBatchTimes > MAX_DROP_FRAME_NATIVE_BATCH) {
+            postAllStashedGraphicAction(instanceId,action);
+        } else {
+            HashMap<String, Object> item = new HashMap<>(1);
+            item.put(sKeyAction, action);
+            mBatchActions.add(item);
+            mCurrentBatchInstanceId = instanceId;
+            return;
+        }
+    }
+
+    mWXRenderHandler.post(instanceId, action);
+  }
+
+  public void registerInstance(WXSDKInstance instance) {
+    if (instance.getInstanceId() == null) {
+      WXExceptionUtils.commitCriticalExceptionRT(null,
+              WXErrorCode.WX_RENDER_ERR_INSTANCE_ID_NULL,
+              "registerInstance",
+              WXErrorCode.WX_RENDER_ERR_INSTANCE_ID_NULL.getErrorMsg() + "instanceId is null",
+              null);
+    } else {
+      mRenderContext.put(instance.getInstanceId(), new RenderContextImpl(instance));
+    }
+  }
+
+  public List<WXSDKInstance> getAllInstances() {
+    ArrayList<WXSDKInstance> instances = null;
+    if (mRenderContext != null && !mRenderContext.isEmpty()) {
+      instances = new ArrayList<WXSDKInstance>();
+      for (Map.Entry<String, RenderContextImpl> entry : mRenderContext.entrySet()) {
+        RenderContextImpl renderStatement = entry.getValue();
+        if (renderStatement != null) {
+          instances.add(renderStatement.getWXSDKInstance());
+        }
+      }
+    }
+    return instances;
+  }
+
+  public void registerComponent(String instanceId, String ref, WXComponent comp) {
+    RenderContextImpl statement = mRenderContext.get(instanceId);
+    if (statement != null) {
+      statement.registerComponent(ref, comp);
+      if (null != statement.getInstance()){
+        statement.getInstance().getApmForInstance().updateMaxStats(
+            WXInstanceApm.KEY_PAGE_STATS_MAX_COMPONENT_NUM,
+            statement.getComponentCount()
+        );
+      }
+    }
+  }
+
+  public WXComponent unregisterComponent(String instanceId, String ref) {
+    RenderContextImpl statement = mRenderContext.get(instanceId);
+    if (statement != null) {
+      if (null != statement.getInstance()){
+        statement.getInstance().getApmForInstance().updateMaxStats(
+            WXInstanceApm.KEY_PAGE_STATS_MAX_COMPONENT_NUM,
+            statement.getComponentCount()
+        );
+      }
+      return statement.unregisterComponent(ref);
+    } else {
+      return null;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/ActionAddRule.java b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionAddRule.java
new file mode 100644
index 0000000..70d3933
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionAddRule.java
@@ -0,0 +1,87 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+import android.text.TextUtils;
+
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.font.FontAdapter;
+import org.apache.weex.utils.FontDO;
+import org.apache.weex.utils.TypefaceUtil;
+
+/**
+ * Created by listen on 18/01/10.
+ */
+public class ActionAddRule implements IExecutable {
+
+  private final String mPageId;
+  private final String mType;
+  private final JSONObject mData;
+
+  public ActionAddRule(String pageId, String type, JSONObject data) {
+    this.mPageId = pageId;
+    this.mType = type;
+    this.mData = data;
+  }
+
+  @Override
+  public void executeAction() {
+    WXSDKInstance instance = WXSDKManager.getInstance().getWXRenderManager().getWXSDKInstance(mPageId);
+    if (instance == null || instance.isDestroy()) {
+      return;
+    }
+
+    if (!Constants.Name.FONT_FACE.equals(mType)) {
+      return;
+    }
+
+    FontDO fontDO = parseFontDO(mData, instance);
+    if (fontDO != null && !TextUtils.isEmpty(fontDO.getFontFamilyName())) {
+      notifyAddFontRule(instance, fontDO);
+      FontDO cacheFontDO = TypefaceUtil.getFontDO(fontDO.getFontFamilyName());
+      if (cacheFontDO == null || !TextUtils.equals(cacheFontDO.getUrl(), fontDO.getUrl())) {
+        TypefaceUtil.putFontDO(fontDO);
+        TypefaceUtil.loadTypeface(fontDO, true);
+      } else {
+        TypefaceUtil.loadTypeface(cacheFontDO, true);
+      }
+    }
+
+  }
+
+  private FontDO parseFontDO(JSONObject jsonObject,WXSDKInstance instance) {
+    if(jsonObject == null) {
+      return null;
+    }
+    String src = jsonObject.getString(Constants.Name.SRC);
+    String name = jsonObject.getString(Constants.Name.FONT_FAMILY);
+
+    return new FontDO(name, src,instance);
+  }
+
+
+  private void notifyAddFontRule(WXSDKInstance instance, FontDO fontDO){
+    FontAdapter fontAdapter = WXSDKManager.getInstance().getFontAdapter();
+    if(fontAdapter != null){
+        fontAdapter.onAddFontRule(instance.getInstanceId(), fontDO.getFontFamilyName(), fontDO.getUrl());
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/ActionGetComponentRect.java b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionGetComponentRect.java
new file mode 100644
index 0000000..9f2e96d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionGetComponentRect.java
@@ -0,0 +1,121 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.graphics.Rect;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+import android.view.View;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.bridge.SimpleJSCallback;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Created by listen on 18/01/10.
+ */
+public class ActionGetComponentRect extends BasicGraphicAction {
+
+  private final String mCallback;
+
+  public ActionGetComponentRect(WXSDKInstance instance, String ref, String callback) {
+    super(instance, ref);
+    this.mCallback = callback;
+  }
+
+  @Override
+  public void executeAction() {
+    WXSDKInstance instance = getWXSDKIntance();
+    if (instance == null || instance.isDestroy()) {
+      return;
+    }
+
+    JSCallback jsCallback = new SimpleJSCallback(instance.getInstanceId(), mCallback);
+
+    if (TextUtils.isEmpty(getRef())) {
+      Map<String, Object> options = new HashMap<>();
+      options.put("result", false);
+      options.put("errMsg", "Illegal parameter");
+      jsCallback.invoke(options);
+    } else if ("viewport".equalsIgnoreCase(getRef())) {
+      callbackViewport(instance, jsCallback);
+    } else {
+      WXComponent component = WXSDKManager
+          .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+      if (component == null) {
+        return;
+      }
+
+      Map<String, Object> options = new HashMap<>();
+      if (component != null) {
+        int viewPort = instance.getInstanceViewPortWidth();
+        Map<String, Float> size = new HashMap<>();
+        Rect sizes = component.getComponentSize();
+        size.put("width", getWebPxValue(sizes.width(),viewPort));
+        size.put("height", getWebPxValue(sizes.height(),viewPort));
+        size.put("bottom", getWebPxValue(sizes.bottom,viewPort));
+        size.put("left", getWebPxValue(sizes.left,viewPort));
+        size.put("right", getWebPxValue(sizes.right,viewPort));
+        size.put("top", getWebPxValue(sizes.top,viewPort));
+        options.put("size", size);
+        options.put("result", true);
+      } else {
+        options.put("errMsg", "Component does not exist");
+      }
+      jsCallback.invoke(options);
+    }
+  }
+
+  private void callbackViewport(WXSDKInstance instance, JSCallback jsCallback) {
+    View container;
+    if ((container = instance.getContainerView()) != null) {
+      Map<String, Object> options = new HashMap<>();
+      Map<String, Float> sizes = new HashMap<>();
+      int[] location = new int[2];
+      instance.getContainerView().getLocationOnScreen(location);
+      int viewport = instance.getInstanceViewPortWidth();
+      sizes.put("left", 0f);
+      sizes.put("top", 0f);
+      sizes.put("right", getWebPxValue(container.getWidth(),viewport));
+      sizes.put("bottom", getWebPxValue(container.getHeight(),viewport));
+      sizes.put("width", getWebPxValue(container.getWidth(),viewport));
+      sizes.put("height", getWebPxValue(container.getHeight(),viewport));
+      options.put("size", sizes);
+      options.put("result", true);
+      jsCallback.invoke(options);
+    } else {
+      Map<String, Object> options = new HashMap<>();
+      options.put("result", false);
+      options.put("errMsg", "Component does not exist");
+      jsCallback.invoke(options);
+    }
+  }
+
+  @NonNull
+  private float getWebPxValue(int value,int viewport) {
+    return WXViewUtils.getWebPxByWidth(value, viewport);
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/ActionGetLayoutDirection.java b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionGetLayoutDirection.java
new file mode 100644
index 0000000..64de952
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionGetLayoutDirection.java
@@ -0,0 +1,118 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+import android.view.View;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.bridge.SimpleJSCallback;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Created by listen on 18/09/12.
+ */
+public class ActionGetLayoutDirection extends BasicGraphicAction {
+
+  private final String mCallback;
+
+  public ActionGetLayoutDirection(WXSDKInstance instance, String ref, String callback) {
+    super(instance, ref);
+    this.mCallback = callback;
+  }
+
+  @Override
+  public void executeAction() {
+    WXSDKInstance instance = getWXSDKIntance();
+    if (instance == null || instance.isDestroy()) {
+      return;
+    }
+
+    JSCallback jsCallback = new SimpleJSCallback(instance.getInstanceId(), mCallback);
+
+    if (TextUtils.isEmpty(getRef())) {
+      Map<String, Object> options = new HashMap<>();
+      options.put("result", false);
+      options.put("errMsg", "Illegal parameter");
+      jsCallback.invoke(options);
+    } else if ("viewport".equalsIgnoreCase(getRef())) {
+      callbackViewport(instance, jsCallback);
+    } else {
+      WXComponent component = WXSDKManager
+          .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+      if (component == null) {
+        return;
+      }
+
+      String directionRet = "ltr";
+      if (component != null) {
+        int direction = NativeRenderObjectUtils.nativeRenderObjectGetLayoutDirectionFromPathNode(component.getRenderObjectPtr());
+        switch (direction) {
+          case 0: {
+            directionRet = "inherit";
+            break;
+          }
+          case 1: {
+            directionRet = "ltr";
+            break;
+          }
+          case 2: {
+            directionRet = "rtl";
+            break;
+          }
+          default: {
+            directionRet = "ltr";
+            break;
+          }
+
+        }
+      }
+      jsCallback.invoke(directionRet);
+    }
+  }
+
+  private void callbackViewport(WXSDKInstance instance, JSCallback jsCallback) {
+    View container;
+    if ((container = instance.getContainerView()) != null) {
+      Map<String, Object> options = new HashMap<>();
+      options.put("direction", "ltr");
+      options.put("result", true);
+      jsCallback.invoke(options);
+    } else {
+      Map<String, Object> options = new HashMap<>();
+      options.put("result", false);
+      options.put("errMsg", "Component does not exist");
+      jsCallback.invoke(options);
+    }
+  }
+
+  @NonNull
+  private float getWebPxValue(int value,int viewport) {
+    return WXViewUtils.getWebPxByWidth(value, viewport);
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/ActionInvokeMethod.java b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionInvokeMethod.java
new file mode 100644
index 0000000..0d5bf2a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionInvokeMethod.java
@@ -0,0 +1,55 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import com.alibaba.fastjson.JSONArray;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.WXLogUtils;
+
+/**
+ * Created by listen on 18/01/10.
+ */
+public class ActionInvokeMethod implements IExecutable {
+
+  private static final String TAG = "ActionInvokeMethod";
+
+  private final String mMethod;
+  private final JSONArray mArgs;
+  private String mPageId;
+  private String mRef;
+
+  public ActionInvokeMethod(String pageId, String ref, String method, JSONArray args) {
+    this.mPageId = pageId;
+    this.mRef = ref;
+    this.mMethod = method;
+    this.mArgs = args;
+  }
+
+  @Override
+  public void executeAction() {
+    WXComponent component = WXSDKManager
+        .getInstance().getWXRenderManager().getWXComponent(mPageId, mRef);
+    if(component == null){
+      WXLogUtils.e(TAG,"target component not found.");
+      return;
+    }
+    component.invoke(mMethod,mArgs);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/ActionReloadPage.java b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionReloadPage.java
new file mode 100644
index 0000000..96830c3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/ActionReloadPage.java
@@ -0,0 +1,49 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.util.Log;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+
+/**
+ * Created by listen on 18/01/09.
+ */
+public class ActionReloadPage implements IExecutable {
+
+  private final String TAG = "ReloadPageAction";
+  private boolean mReloadThis;
+  private String mPageId;
+
+  public ActionReloadPage(String pageId, boolean reloadThis) {
+    this.mPageId = pageId;
+    this.mReloadThis = reloadThis;
+  }
+
+  @Override
+  public void executeAction() {
+    final WXSDKInstance instance = WXSDKManager.getInstance().getWXRenderManager().getWXSDKInstance(mPageId);
+    if (instance != null) {
+      instance.reloadPage(mReloadThis);
+    } else {
+      Log.e(TAG, "ReloadPageAction executeDom reloadPage instance is null");
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/BasicComponentData.java b/android/sdk/src/main/java/org/apache/weex/ui/action/BasicComponentData.java
new file mode 100644
index 0000000..c91969c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/BasicComponentData.java
@@ -0,0 +1,310 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.annotation.NonNull;
+import android.view.View;
+
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.Map;
+import java.util.Set;
+
+public class BasicComponentData<T extends View> {
+
+  public String mRef;
+  public String mComponentType;
+  public String mParentRef;
+  private WXStyle mStyles;
+  private WXAttr mAttributes;
+  private WXEvent mEvents;
+  private CSSShorthand mMargins;
+  private CSSShorthand mPaddings;
+  private CSSShorthand mBorders;
+  private long renderObjectPr = 0;
+
+  public BasicComponentData(String ref, String componentType, String parentRef) {
+    this.mRef = ref;
+    this.mComponentType = componentType;
+    this.mParentRef = parentRef;
+  }
+
+  public void addStyle(Map<String, Object> styles) {
+    addStyle(styles, false);
+  }
+
+  public final void addStyle(Map<String, Object> styles, boolean byPesudo) {
+    if (styles == null || styles.isEmpty()) {
+      return;
+    }
+    if (mStyles == null) {
+      mStyles = new WXStyle(styles);
+    }
+    else {
+      mStyles.putAll(styles, byPesudo);
+    }
+  }
+
+  public final void addAttr(Map<String, Object> attrs) {
+    if (attrs == null || attrs.isEmpty()) {
+      return;
+    }
+    if (mAttributes == null) {
+      mAttributes = new WXAttr(attrs, 0);
+    }
+    else {
+      mAttributes.putAll(attrs);
+    }
+  }
+
+  public final void addEvent(Set<String> events) {
+    if (events == null || events.isEmpty()) {
+      return;
+    }
+    if (mEvents == null) {
+      mEvents = new WXEvent();
+    }
+    mEvents.addAll(events);
+  }
+
+  public final void addShorthand(float[] shorthand, CSSShorthand.TYPE type) {
+    if (shorthand == null) {
+      shorthand = new float[] {0, 0, 0, 0};
+    }
+    if (shorthand.length == 4) {
+      switch (type) {
+        case MARGIN:
+          if (mMargins == null) {
+            mMargins = new CSSShorthand(shorthand);
+          } else {
+            mMargins.replace(shorthand);
+          }
+          break;
+        case PADDING:
+          if (mPaddings == null) {
+            mPaddings = new CSSShorthand(shorthand);
+          } else {
+            mPaddings.replace(shorthand);
+          }
+          break;
+        case BORDER:
+          if (mBorders == null) {
+            mBorders = new CSSShorthand(shorthand);
+          } else {
+            mBorders.replace(shorthand);
+          }
+          break;
+        default:
+          break;
+      }
+    }
+  }
+
+  public final void addShorthand(Map<String, String> shorthand) {
+    if (shorthand != null && !shorthand.isEmpty()) {
+      for (Map.Entry<String, String> item : shorthand.entrySet()) {
+        String key = item.getKey();
+        switch (key) {
+          case Constants.Name.MARGIN:
+            addMargin(CSSShorthand.EDGE.ALL, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.MARGIN_LEFT:
+            addMargin(CSSShorthand.EDGE.LEFT, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.MARGIN_TOP:
+            addMargin(CSSShorthand.EDGE.TOP, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.MARGIN_RIGHT:
+            addMargin(CSSShorthand.EDGE.RIGHT, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.MARGIN_BOTTOM:
+            addMargin(CSSShorthand.EDGE.BOTTOM,WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.BORDER_WIDTH:
+            addBorder(CSSShorthand.EDGE.ALL, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.BORDER_TOP_WIDTH:
+            addBorder(CSSShorthand.EDGE.TOP, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.BORDER_RIGHT_WIDTH:
+            addBorder(CSSShorthand.EDGE.RIGHT, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.BORDER_BOTTOM_WIDTH:
+            addBorder(CSSShorthand.EDGE.BOTTOM, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.BORDER_LEFT_WIDTH:
+            addBorder(CSSShorthand.EDGE.LEFT, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.PADDING:
+            addPadding(CSSShorthand.EDGE.ALL, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.PADDING_LEFT:
+            addPadding(CSSShorthand.EDGE.LEFT, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.PADDING_TOP:
+            addPadding(CSSShorthand.EDGE.TOP, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.PADDING_RIGHT:
+            addPadding(CSSShorthand.EDGE.RIGHT, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+          case Constants.Name.PADDING_BOTTOM:
+            addPadding(CSSShorthand.EDGE.BOTTOM, WXUtils.fastGetFloat(shorthand.get(key)));
+            break;
+        }
+      }
+    }
+  }
+
+  private void addMargin(CSSShorthand.EDGE spacingType, float margin) {
+    if (mMargins == null) {
+      mMargins = new CSSShorthand();
+    }
+    mMargins.set(spacingType, margin);
+  }
+
+  private void addPadding(CSSShorthand.EDGE spacingType, float padding) {
+    if (mPaddings == null) {
+      mPaddings = new CSSShorthand();
+    }
+    mPaddings.set(spacingType, padding);
+  }
+
+  private void addBorder(CSSShorthand.EDGE spacingType, float border) {
+    if (mBorders == null) {
+      mBorders = new CSSShorthand();
+    }
+    mBorders.set(spacingType, border);
+  }
+
+  public final @NonNull
+  WXStyle getStyles() {
+    if (mStyles == null) {
+      mStyles = new WXStyle();
+    }
+    return mStyles;
+  }
+
+  public final @NonNull
+  WXAttr getAttrs() {
+    if (mAttributes == null) {
+      mAttributes = new WXAttr();
+    }
+    return mAttributes;
+  }
+
+  public final @NonNull
+  WXEvent getEvents() {
+    if (mEvents == null) {
+      mEvents = new WXEvent();
+    }
+    return mEvents;
+  }
+
+  /**
+   * Get this node's margin, as defined by cssstyle + default margin.
+   */
+  public final @NonNull
+  CSSShorthand getMargin() {
+    if (mMargins == null) {
+      mMargins = new CSSShorthand();
+    }
+    return mMargins;
+  }
+
+  /**
+   * Get this node's padding, as defined by cssstyle + default padding.
+   */
+  public final @NonNull
+  CSSShorthand getPadding() {
+    if (mPaddings == null) {
+      mPaddings = new CSSShorthand();
+    }
+    return mPaddings;
+  }
+
+  /**
+   * Get this node's border, as defined by cssstyle.
+   */
+  public @NonNull
+  CSSShorthand getBorder() {
+    if (mBorders == null) {
+      mBorders = new CSSShorthand();
+    }
+    return mBorders;
+  }
+
+  public final void setMargins(@NonNull CSSShorthand mMargins) {
+    this.mMargins = mMargins;
+  }
+
+  public final void setPaddings(@NonNull CSSShorthand mPaddings) {
+    this.mPaddings = mPaddings;
+  }
+
+  public final void setBorders(@NonNull CSSShorthand mBorders) {
+    this.mBorders = mBorders;
+  }
+
+
+
+  @Override
+  public BasicComponentData clone() throws CloneNotSupportedException {
+    BasicComponentData basicComponentData = new BasicComponentData(mRef, mComponentType, mParentRef);
+    basicComponentData.setBorders(getBorder().clone());
+    basicComponentData.setMargins(getMargin().clone());
+    basicComponentData.setPaddings(getPadding().clone());
+    if(mAttributes != null){
+      basicComponentData.mAttributes = mAttributes.clone();
+    }
+    if(mStyles != null){
+      basicComponentData.mStyles = mStyles.clone();
+    }
+    if(mEvents != null){
+      basicComponentData.mEvents = mEvents.clone();
+    }
+
+    if(renderObjectPr != 0){
+      basicComponentData.setRenderObjectPr(NativeRenderObjectUtils.nativeCopyRenderObject(renderObjectPr));
+    }
+    return basicComponentData;
+  }
+
+  public long getRenderObjectPr() {
+    return renderObjectPr;
+  }
+
+  public boolean isRenderPtrEmpty(){
+    return  renderObjectPr == 0;
+  }
+
+  public synchronized void setRenderObjectPr(long renderObjectPr) {
+    if(this.renderObjectPr != renderObjectPr){
+      if(this.renderObjectPr != 0){
+        throw  new  RuntimeException("RenderObjectPr has " + renderObjectPr + " old renderObjectPtr " + this.renderObjectPr);
+      }
+      this.renderObjectPr = renderObjectPr;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/BasicGraphicAction.java b/android/sdk/src/main/java/org/apache/weex/ui/action/BasicGraphicAction.java
new file mode 100644
index 0000000..16e5472
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/BasicGraphicAction.java
@@ -0,0 +1,80 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.text.TextUtils;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.utils.WXLogUtils;
+
+public abstract class BasicGraphicAction implements IExecutable, Runnable {
+
+  private WXSDKInstance mInstance;
+  private final String mRef;
+  public int mActionType = ActionTypeNormal;
+  public static final int ActionTypeBatchBegin = 1;
+  public static final int ActionTypeBatchEnd = 2;
+  public static final int ActionTypeNormal = 0;
+
+
+  public BasicGraphicAction(WXSDKInstance instance, String ref) {
+    this.mInstance = instance;
+    this.mRef = ref;
+  }
+
+  public final WXSDKInstance getWXSDKIntance() {
+    return mInstance;
+  }
+
+  public final String getPageId() {
+    return mInstance.getInstanceId();
+  }
+
+  public final String getRef() {
+    return mRef;
+  }
+
+  public void executeActionOnRender() {
+    if (TextUtils.isEmpty(mInstance.getInstanceId())) {
+        WXLogUtils.e("[BasicGraphicAction] pageId can not be null");
+        if (WXEnvironment.isApkDebugable()) {
+            throw new RuntimeException("["+getClass().getName()+"] pageId can not be null");
+        }
+        return;
+    }
+    WXSDKManager
+        .getInstance().getWXRenderManager().postGraphicAction(mInstance.getInstanceId(), this);
+  }
+
+  @Override
+  public void run() {
+    try {
+      executeAction();
+    } catch (Throwable e) {
+      //catch everything may throw from exection.
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e("BasicGraphicAction",
+            "SafeRunnable run throw expection:" + e.getMessage());
+        throw e;
+      }
+      WXLogUtils.w("BasicGraphicAction", e);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAbstractAddElement.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAbstractAddElement.java
new file mode 100644
index 0000000..13e429e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAbstractAddElement.java
@@ -0,0 +1,103 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.v4.util.ArrayMap;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXComponentFactory;
+import org.apache.weex.ui.component.WXVContainer;
+import java.util.Map;
+import java.util.Set;
+
+public abstract class GraphicActionAbstractAddElement extends BasicGraphicAction {
+
+  protected String mComponentType;
+  protected String mParentRef;
+  protected int mIndex = -1;
+  protected Map<String, String> mStyle;
+  protected Map<String, String> mAttributes;
+  protected Set<String> mEvents;
+  protected float[] mMargins;
+  protected float[] mPaddings;
+  protected float[] mBorders;
+  private long startTime;
+
+  public GraphicActionAbstractAddElement(WXSDKInstance instance, String ref) {
+    super(instance, ref);
+    startTime = System.currentTimeMillis();
+  }
+
+  protected WXComponent createComponent(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    long createComponentStart = System.currentTimeMillis();
+    if (basicComponentData != null) {
+      basicComponentData.addStyle(mStyle);
+      basicComponentData.addAttr(mAttributes);
+      basicComponentData.addEvent(mEvents);
+      basicComponentData.addShorthand(mMargins, CSSShorthand.TYPE.MARGIN);
+      basicComponentData.addShorthand(mPaddings, CSSShorthand.TYPE.PADDING);
+      basicComponentData.addShorthand(mBorders, CSSShorthand.TYPE.BORDER);
+    }
+
+    WXComponent component = WXComponentFactory.newInstance(instance, parent, basicComponentData);
+    WXSDKManager
+        .getInstance().getWXRenderManager().registerComponent(getPageId(), getRef(), component);
+    if(mStyle != null && mStyle.containsKey(Constants.Name.TRANSFORM) && component.getTransition() == null) {
+      Map<String, Object> animationMap = new ArrayMap<>(2);
+      animationMap.put(Constants.Name.TRANSFORM, mStyle.get(Constants.Name.TRANSFORM));
+      animationMap
+          .put(Constants.Name.TRANSFORM_ORIGIN, mStyle.get(Constants.Name.TRANSFORM_ORIGIN));
+      component.addAnimationForElement(animationMap);
+    }
+    instance.onComponentCreate(component,System.currentTimeMillis() -createComponentStart);
+    return component;
+  }
+
+  @Override
+  public void executeAction() {
+    getWXSDKIntance().callActionAddElementTime(System.currentTimeMillis() - startTime);
+  }
+
+  public String getComponentType() {
+    return mComponentType;
+  }
+
+  public String getParentRef() {
+    return mParentRef;
+  }
+
+  public int getIndex() {
+    return mIndex;
+  }
+
+  public Map<String, String> getStyle() {
+    return mStyle;
+  }
+
+  public Map<String, String> getAttributes() {
+    return mAttributes;
+  }
+
+  public Set<String> getEvents() {
+    return mEvents;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddChildToRichtext.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddChildToRichtext.java
new file mode 100755
index 0000000..e2e7ca7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddChildToRichtext.java
@@ -0,0 +1,46 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.annotation.NonNull;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.richtext.WXRichText;
+
+import java.util.HashMap;
+
+public class GraphicActionAddChildToRichtext extends BasicGraphicAction {
+
+    public GraphicActionAddChildToRichtext(@NonNull WXSDKInstance instance, String nodeType, String ref, String parentRef, String richTextRef,
+                                           HashMap<String, String> styles, HashMap<String, String> attrs){
+        super(instance,richTextRef);
+        if(WXSDKManager.getInstance() != null && WXSDKManager.getInstance().getWXRenderManager() != null) {
+            WXRichText richText = (WXRichText) WXSDKManager.getInstance().getWXRenderManager()
+                    .getWXComponent(getPageId(), richTextRef);
+            if (richText != null) {
+                richText.AddChildNode(ref, nodeType, parentRef, styles, attrs);
+            }
+        }
+    }
+    @Override
+    public void executeAction() {
+
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddElement.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddElement.java
new file mode 100644
index 0000000..8ab6cba
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddElement.java
@@ -0,0 +1,214 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.support.annotation.WorkerThread;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+import android.util.Log;
+import org.apache.weex.BuildConfig;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.dom.transition.WXTransition;
+import org.apache.weex.performance.WXAnalyzerDataTransfer;
+import org.apache.weex.performance.WXStateRecord;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.Arrays;
+import java.util.Locale;
+import java.util.Map;
+import java.util.Set;
+
+public class GraphicActionAddElement extends GraphicActionAbstractAddElement {
+
+  private WXVContainer parent;
+  private WXComponent child;
+  private GraphicPosition layoutPosition;
+  private GraphicSize layoutSize;
+  private boolean isLayoutRTL;
+
+  public GraphicActionAddElement(@NonNull WXSDKInstance instance, String ref,
+                                 String componentType, String parentRef,
+                                 int index,
+                                 Map<String, String> style,
+                                 Map<String, String> attributes,
+                                 Set<String> events,
+                                 float[] margins,
+                                 float[] paddings,
+                                 float[] borders) {
+    super(instance, ref);
+    this.mComponentType = componentType;
+    this.mParentRef = parentRef;
+    this.mIndex = index;
+    this.mStyle = style;
+    this.mAttributes = attributes;
+    this.mEvents = events;
+    this.mPaddings = paddings;
+    this.mMargins = margins;
+    this.mBorders = borders;
+
+    if (instance.getContext() == null) {
+      return;
+    }
+      if (WXAnalyzerDataTransfer.isInteractionLogOpen()){
+        Log.d(WXAnalyzerDataTransfer.INTERACTION_TAG, "[client][addelementStart]"+instance.getInstanceId()+","+componentType+","+ref);
+      }
+    try {
+      parent = (WXVContainer) WXSDKManager.getInstance().getWXRenderManager()
+          .getWXComponent(getPageId(), mParentRef);
+      long start = WXUtils.getFixUnixTime();
+      BasicComponentData basicComponentData = new BasicComponentData(ref, mComponentType,
+          mParentRef);
+      child = createComponent(instance, parent, basicComponentData);
+      child.setTransition(WXTransition.fromMap(child.getStyles(), child));
+      long diff = WXUtils.getFixUnixTime()-start;
+      instance.getApmForInstance().componentCreateTime += diff;
+      if (null != parent && parent.isIgnoreInteraction){
+        child.isIgnoreInteraction = true;
+      }
+      if (!child.isIgnoreInteraction ){
+        Object flag = null;
+        if (null != child.getAttrs()){
+          flag = child.getAttrs().get("ignoreInteraction");
+        }
+        if ("false".equals(flag) || "0".equals(flag)){
+          child.isIgnoreInteraction = false;
+        }else if ("1".equals(flag) || "true".equals(flag) || child.isFixed()){
+          child.isIgnoreInteraction = true;
+        }
+      }
+      WXStateRecord.getInstance().recordAction(instance.getInstanceId(),"addElement");
+
+    } catch (ClassCastException e) {
+      Map<String, String> ext = new ArrayMap<>();
+      WXComponent parent = WXSDKManager.getInstance().getWXRenderManager()
+          .getWXComponent(getPageId(), mParentRef);
+
+      if (mStyle != null && !mStyle.isEmpty()) {
+        ext.put("child.style", mStyle.toString());
+      }
+      if (parent != null && parent.getStyles() != null && !parent.getStyles().isEmpty()) {
+        ext.put("parent.style", parent.getStyles().toString());
+      }
+
+      if (mAttributes != null && !mAttributes.isEmpty()) {
+        ext.put("child.attr", mAttributes.toString());
+      }
+      if (parent != null && parent.getAttrs() != null && !parent.getAttrs().isEmpty()) {
+        ext.put("parent.attr", parent.getAttrs().toString());
+      }
+
+      if (mEvents != null && !mEvents.isEmpty()) {
+        ext.put("child.event", mEvents.toString());
+      }
+      if (parent != null && parent.getEvents() != null && !parent.getEvents().isEmpty()) {
+        ext.put("parent.event", parent.getEvents().toString());
+      }
+
+      if (mMargins != null && mMargins.length > 0) {
+        ext.put("child.margin", Arrays.toString(mMargins));
+      }
+      if (parent != null && parent.getMargin() != null) {
+        ext.put("parent.margin", parent.getMargin().toString());
+      }
+
+      if (mPaddings != null && mPaddings.length > 0) {
+        ext.put("child.padding", Arrays.toString(mPaddings));
+      }
+      if (parent != null && parent.getPadding() != null) {
+        ext.put("parent.padding", parent.getPadding().toString());
+      }
+
+      if (mBorders != null && mBorders.length > 0) {
+        ext.put("child.border", Arrays.toString(mBorders));
+      }
+      if (parent != null && parent.getBorder() != null) {
+        ext.put("parent.border", parent.getBorder().toString());
+      }
+
+      WXExceptionUtils.commitCriticalExceptionRT(instance.getInstanceId(),
+          WXErrorCode.WX_RENDER_ERR_CONTAINER_TYPE,
+          "GraphicActionAddElement",
+          String.format(Locale.ENGLISH,"You are trying to add a %s to a %2$s, which is illegal as %2$s is not a container",
+              componentType,
+              WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), mParentRef).getComponentType()),
+          ext);
+    }
+
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  @WorkerThread
+  public void setRTL(boolean isRTL){
+    this.isLayoutRTL = isRTL;
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  @WorkerThread
+  public void setSize(GraphicSize graphicSize){
+    this.layoutSize = graphicSize;
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  @WorkerThread
+  public void setPosition(GraphicPosition position){
+    this.layoutPosition = position;
+  }
+
+  @RestrictTo(Scope.LIBRARY)
+  @WorkerThread
+  public void setIndex(int index){
+    mIndex = index;
+  }
+
+  @Override
+  public void executeAction() {
+    super.executeAction();
+    try {
+      if (!TextUtils.equals(mComponentType, "video") && !TextUtils.equals(mComponentType, "videoplus"))
+        child.mIsAddElementToTree = true;
+
+      long start = WXUtils.getFixUnixTime();
+      parent.addChild(child, mIndex);
+      parent.createChildViewAt(mIndex);
+
+      child.setIsLayoutRTL(isLayoutRTL);
+      if(layoutPosition !=null && layoutSize != null) {
+        child.setDemission(layoutSize, layoutPosition);
+      }
+      child.applyLayoutAndEvent(child);
+      child.bindData(child);
+      long diff = WXUtils.getFixUnixTime() - start;
+      if (null != getWXSDKIntance()){
+        getWXSDKIntance().getApmForInstance().viewCreateTime +=diff;
+      }
+
+    } catch (Exception e) {
+      WXLogUtils.e("add component failed.", e);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddEvent.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddEvent.java
new file mode 100644
index 0000000..0134ead
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAddEvent.java
@@ -0,0 +1,54 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.tracing.Stopwatch;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by listen on 18/01/11.
+ */
+public class GraphicActionAddEvent extends BasicGraphicAction {
+
+  private final String mEvent;
+
+  public GraphicActionAddEvent(WXSDKInstance instance, String ref, Object event) {
+    super(instance, ref);
+    this.mEvent = WXEvent.getEventName(event);
+  }
+
+  @Override
+  public void executeAction() {
+    WXComponent component = WXSDKManager
+        .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null) {
+      return;
+    }
+
+    Stopwatch.tick();
+    if (!component.getEvents().contains(mEvent)) {
+      component.getEvents().addEvent(mEvent);
+    }
+    component.addEvent(mEvent);
+    Stopwatch.split("addEventToComponent");
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAnimation.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAnimation.java
new file mode 100644
index 0000000..f7831be
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAnimation.java
@@ -0,0 +1,290 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.animation.Animator;
+import android.animation.AnimatorListenerAdapter;
+import android.animation.ArgbEvaluator;
+import android.animation.ObjectAnimator;
+import android.animation.PropertyValuesHolder;
+import android.graphics.drawable.ColorDrawable;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v4.view.animation.PathInterpolatorCompat;
+import android.text.TextUtils;
+import android.util.Pair;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.animation.AccelerateDecelerateInterpolator;
+import android.view.animation.AccelerateInterpolator;
+import android.view.animation.DecelerateInterpolator;
+import android.view.animation.Interpolator;
+import android.view.animation.LinearInterpolator;
+
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.animation.BackgroundColorProperty;
+import org.apache.weex.ui.animation.HeightProperty;
+import org.apache.weex.ui.animation.WXAnimationBean;
+import org.apache.weex.ui.animation.WXAnimationModule;
+import org.apache.weex.ui.animation.WidthProperty;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.list.template.TemplateDom;
+import org.apache.weex.ui.view.border.BorderDrawable;
+import org.apache.weex.utils.SingleFunctionParser;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.HashMap;
+import java.util.List;
+
+public class GraphicActionAnimation extends BasicGraphicAction {
+
+  private final static String TAG = "GraphicActionAnimation";
+
+  private final boolean styleNeedInit;
+
+  @Nullable
+  private
+  final String callback;
+
+  @Nullable
+  private
+  WXAnimationBean mAnimationBean;
+
+  public GraphicActionAnimation(@NonNull WXSDKInstance instance, @NonNull String ref, @NonNull WXAnimationBean animationBean) {
+    super(instance, ref);
+    this.styleNeedInit = false;
+    this.callback = null;
+    this.mAnimationBean = animationBean;
+  }
+
+  public GraphicActionAnimation(@NonNull WXSDKInstance instance, @NonNull String ref, @Nullable String animation,
+                                @Nullable final String callBack) {
+    super(instance, ref);
+    this.styleNeedInit = true;
+    this.callback = callBack;
+    if (!TextUtils.isEmpty(animation)) {
+      this.mAnimationBean = JSONObject.parseObject(animation, WXAnimationBean.class);
+    }
+  }
+  public GraphicActionAnimation(@NonNull WXSDKInstance instance, @NonNull String ref, @NonNull WXAnimationBean animationBean,
+                                @Nullable final String callBack) {
+    super(instance, ref);
+    this.styleNeedInit = false;
+    this.mAnimationBean = animationBean;
+    this.callback = callBack;
+  }
+
+  @Override
+  public void executeAction() {
+    if (null == mAnimationBean) {
+      return;
+    }
+
+    WXComponent component = WXSDKManager
+        .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null) {
+      if(!TemplateDom.isVirtualDomRef(getRef())){
+        return;
+      }
+      component = TemplateDom.findVirtualComponentByVRef(getPageId(), getRef());
+      if(component == null){
+        return;
+      }
+    }
+
+    WXSDKInstance instance = WXSDKManager.getInstance().getWXRenderManager().getWXSDKInstance(getPageId());
+    if (instance == null) {
+      return;
+    }
+
+    if (null != mAnimationBean.styles) {
+      if(styleNeedInit) {
+        // Synchronize transformOrigin between component styles and animation style before
+        // animation start.
+        String transformOrigin = (String) component.getStyles().get(Constants.Name.TRANSFORM_ORIGIN);
+        if (TextUtils.isEmpty(mAnimationBean.styles.transformOrigin)) {
+          mAnimationBean.styles.transformOrigin = transformOrigin;
+        }
+        mAnimationBean.styles.init(mAnimationBean.styles.transformOrigin,
+            mAnimationBean.styles.transform, (int) component.getLayoutWidth(),
+            (int) component.getLayoutHeight(),
+            instance.getInstanceViewPortWidth(), instance);
+      }
+      startAnimation(instance, component);
+    }
+  }
+
+
+
+  private void startAnimation(@NonNull WXSDKInstance instance, @Nullable WXComponent component) {
+    if (component != null) {
+      if (mAnimationBean != null) {
+        component.setNeedLayoutOnAnimation(mAnimationBean.needLayout);
+      }
+      if (component.getHostView() == null) {
+        WXAnimationModule.AnimationHolder holder = new WXAnimationModule.AnimationHolder(mAnimationBean, callback);
+        component.postAnimation(holder);
+      } else {
+        try {
+          Animator animator = createAnimator(component.getHostView(), instance
+              .getInstanceViewPortWidth());
+          if (animator != null) {
+            Animator.AnimatorListener animatorCallback = createAnimatorListener(instance, callback);
+            if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR2 && component
+                .isLayerTypeEnabled() ) {
+              component.getHostView().setLayerType(View.LAYER_TYPE_HARDWARE, null);
+            }
+            Interpolator interpolator = createTimeInterpolator();
+            if (animatorCallback != null) {
+              animator.addListener(animatorCallback);
+            }
+            if (interpolator != null) {
+              animator.setInterpolator(interpolator);
+            }
+            component.getHostView().setCameraDistance(mAnimationBean.styles.getCameraDistance());
+            animator.setDuration(mAnimationBean.duration);
+            animator.start();
+          }
+        } catch (RuntimeException e) {
+          WXLogUtils.e(TAG, WXLogUtils.getStackTrace(e));
+        }
+      }
+    }
+  }
+
+  private
+  @Nullable
+  ObjectAnimator createAnimator(final View target, final int viewPortWidth) {
+    if (target == null) {
+      return null;
+    }
+    WXAnimationBean.Style style = mAnimationBean.styles;
+    if (style != null) {
+      ObjectAnimator animator;
+      List<PropertyValuesHolder> holders = style.getHolders();
+      if (!TextUtils.isEmpty(style.backgroundColor)) {
+        BorderDrawable borderDrawable;
+        if ((borderDrawable = WXViewUtils.getBorderDrawable(target)) != null) {
+          holders.add(PropertyValuesHolder.ofObject(
+              new BackgroundColorProperty(), new ArgbEvaluator(),
+              borderDrawable.getColor(),
+              WXResourceUtils.getColor(style.backgroundColor)));
+        } else if (target.getBackground() instanceof ColorDrawable) {
+          holders.add(PropertyValuesHolder.ofObject(
+              new BackgroundColorProperty(), new ArgbEvaluator(),
+              ((ColorDrawable) target.getBackground()).getColor(),
+              WXResourceUtils.getColor(style.backgroundColor)));
+        }
+      }
+
+      if (target.getLayoutParams() != null &&
+          (!TextUtils.isEmpty(style.width) || !TextUtils.isEmpty(style.height))) {
+        ViewGroup.LayoutParams layoutParams = target.getLayoutParams();
+        if (!TextUtils.isEmpty(style.width)) {
+          holders.add(PropertyValuesHolder.ofInt(new WidthProperty(), layoutParams.width,
+              (int) WXViewUtils.getRealPxByWidth(WXUtils.getFloat(style.width), viewPortWidth)));
+        }
+        if (!TextUtils.isEmpty(style.height)) {
+          holders.add(PropertyValuesHolder.ofInt(new HeightProperty(), layoutParams.height,
+              (int) WXViewUtils.getRealPxByWidth(WXUtils.getFloat(style.height), viewPortWidth)));
+        }
+      }
+
+      if (style.getPivot() != null) {
+        Pair<Float, Float> pair = style.getPivot();
+        target.setPivotX(pair.first);
+        target.setPivotY(pair.second);
+      }
+      animator = ObjectAnimator.ofPropertyValuesHolder(
+          target, holders.toArray(new PropertyValuesHolder[holders.size()]));
+      animator.setStartDelay(mAnimationBean.delay);
+      return animator;
+    } else {
+      return null;
+    }
+  }
+
+  private
+  @Nullable
+  Animator.AnimatorListener createAnimatorListener(final WXSDKInstance instance, @Nullable final String callBack) {
+    if (!TextUtils.isEmpty(callBack)) {
+      return new AnimatorListenerAdapter() {
+        @Override
+        public void onAnimationEnd(Animator animation) {
+          if (instance == null || instance.isDestroy()) {
+            WXLogUtils.e("RenderContextImpl-onAnimationEnd WXSDKInstance == null NPE or instance is destroyed");
+          } else {
+            WXSDKManager.getInstance().callback(instance.getInstanceId(),
+                                                callBack,
+                                                new HashMap<String, Object>());
+          }
+        }
+      };
+    } else {
+      return null;
+    }
+  }
+
+  private
+  @Nullable
+  Interpolator createTimeInterpolator() {
+    String interpolator = mAnimationBean.timingFunction;
+    if (!TextUtils.isEmpty(interpolator)) {
+      switch (interpolator) {
+        case WXAnimationBean.EASE_IN:
+          return new AccelerateInterpolator();
+        case WXAnimationBean.EASE_OUT:
+          return new DecelerateInterpolator();
+        case WXAnimationBean.EASE_IN_OUT:
+          return new AccelerateDecelerateInterpolator();
+        case WXAnimationBean.LINEAR:
+          return new LinearInterpolator();
+        default:
+          //Parse cubic-bezier
+          try {
+            SingleFunctionParser<Float> parser = new SingleFunctionParser<>(
+                mAnimationBean.timingFunction,
+                new SingleFunctionParser.FlatMapper<Float>() {
+                  @Override
+                  public Float map(String raw) {
+                    return Float.parseFloat(raw);
+                  }
+                });
+            List<Float> params = parser.parse(WXAnimationBean.CUBIC_BEZIER);
+            if (params != null && params.size() == WXAnimationBean.NUM_CUBIC_PARAM) {
+              return PathInterpolatorCompat.create(
+                  params.get(0), params.get(1), params.get(2), params.get(3));
+            } else {
+              return null;
+            }
+          } catch (RuntimeException e) {
+            return null;
+          }
+      }
+    }
+    return null;
+  }
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAppendTreeCreateFinish.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAppendTreeCreateFinish.java
new file mode 100644
index 0000000..8e3a62e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionAppendTreeCreateFinish.java
@@ -0,0 +1,46 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+
+/**
+ * Created by listen on 18/01/09.
+ */
+public class GraphicActionAppendTreeCreateFinish extends BasicGraphicAction {
+
+  WXComponent component;
+
+  public GraphicActionAppendTreeCreateFinish(WXSDKInstance instance, String ref) {
+    super(instance, ref);
+
+    component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), ref);
+    if (null != component && component instanceof WXVContainer) {
+      ((WXVContainer)component).appendTreeCreateFinish();
+    }
+  }
+
+  @Override
+  public void executeAction() {
+
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchAction.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchAction.java
new file mode 100644
index 0000000..53cddfb
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchAction.java
@@ -0,0 +1,41 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class GraphicActionBatchAction extends BasicGraphicAction {
+    private List<BasicGraphicAction> mActions;
+
+    public GraphicActionBatchAction(WXSDKInstance instance, String ref, List<BasicGraphicAction> mActions) {
+        super(instance, ref);
+        this.mActions = new ArrayList<>(mActions);
+    }
+
+    @Override
+    public void executeAction() {
+        for (int i = 0;i < mActions.size();i ++) {
+            mActions.get(i).executeAction();
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchBegin.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchBegin.java
new file mode 100644
index 0000000..e99772d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchBegin.java
@@ -0,0 +1,34 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+
+public class GraphicActionBatchBegin extends BasicGraphicAction {
+    public GraphicActionBatchBegin(WXSDKInstance instance, String ref) {
+        super(instance, ref);
+        this.mActionType = ActionTypeBatchBegin;
+    }
+
+    @Override
+    public void executeAction() {
+
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchEnd.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchEnd.java
new file mode 100644
index 0000000..3ba8355
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionBatchEnd.java
@@ -0,0 +1,34 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+
+public class GraphicActionBatchEnd extends BasicGraphicAction {
+    public GraphicActionBatchEnd(WXSDKInstance instance, String ref) {
+        super(instance, ref);
+        this.mActionType = ActionTypeBatchEnd;
+    }
+
+    @Override
+    public void executeAction() {
+
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionCreateBody.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionCreateBody.java
new file mode 100644
index 0000000..dad6032
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionCreateBody.java
@@ -0,0 +1,92 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.annotation.NonNull;
+import android.widget.ScrollView;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.WXRenderStrategy;
+import org.apache.weex.dom.transition.WXTransition;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXScroller;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.Map;
+import java.util.Set;
+
+public class GraphicActionCreateBody extends GraphicActionAbstractAddElement {
+
+  private WXComponent component;
+
+  public GraphicActionCreateBody(@NonNull WXSDKInstance instance, String ref,
+                                 String componentType,
+                                 Map<String, String> style,
+                                 Map<String, String> attributes,
+                                 Set<String> events,
+                                 float[] margins,
+                                 float[] paddings,
+                                 float[] borders) {
+    super(instance, ref);
+    this.mComponentType = componentType;
+    this.mStyle = style;
+    this.mAttributes = attributes;
+    this.mEvents = events;
+    this.mMargins = margins;
+    this.mPaddings = paddings;
+    this.mBorders = borders;
+
+    if (instance.getContext() == null) {
+      return;
+    }
+
+    BasicComponentData basicComponentData = new BasicComponentData(getRef(), mComponentType, null);
+    component = createComponent(instance, null, basicComponentData);
+    if (component == null) {
+      return;
+    }
+    component.setTransition(WXTransition.fromMap(component.getStyles(), component));
+  }
+
+  @Override
+  public void executeAction() {
+    super.executeAction();
+    try {
+      component.createView();
+      component.applyLayoutAndEvent(component);
+      component.bindData(component);
+      WXSDKInstance instance = getWXSDKIntance();
+
+      if (component instanceof WXScroller) {
+        WXScroller scroller = (WXScroller) component;
+        if (scroller.getInnerView() instanceof ScrollView) {
+          instance.setRootScrollView((ScrollView) scroller.getInnerView());
+        }
+      }
+
+      instance.onRootCreated(component);
+
+      if (instance.getRenderStrategy() != WXRenderStrategy.APPEND_ONCE) {
+        instance.onCreateFinish();
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("create body failed.", e);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionCreateFinish.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionCreateFinish.java
new file mode 100644
index 0000000..717934f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionCreateFinish.java
@@ -0,0 +1,72 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.annotation.NonNull;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.RenderTypes;
+import org.apache.weex.common.WXRenderStrategy;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by listen on 18/01/09.
+ */
+public class GraphicActionCreateFinish extends BasicGraphicAction {
+
+  private int mLayoutWidth;
+  private int mLayoutHeight;
+
+  public GraphicActionCreateFinish(@NonNull WXSDKInstance instance) {
+    super(instance, "");
+    WXComponent component = instance.getRootComponent();
+    if (null != component) {
+        this.mLayoutWidth = (int) component.getLayoutWidth();
+        this.mLayoutHeight = (int) component.getLayoutHeight();
+    }
+    instance.getApmForInstance().onStage(WXInstanceApm.KEY_PAGE_STAGES_CREATE_FINISH);
+    instance.getApmForInstance().extInfo.put(WXInstanceApm.KEY_PAGE_STAGES_CREATE_FINISH,true);
+  }
+
+  @Override
+  public void executeAction() {
+    final WXSDKInstance instance = getWXSDKIntance();
+    if (instance == null || instance.getContext() == null) {
+      return;
+    }
+    if(instance.mHasCreateFinish){
+        return;
+    }
+
+    if (instance.getRenderStrategy() == WXRenderStrategy.APPEND_ONCE) {
+      instance.onCreateFinish();
+    }else{
+      if(!RenderTypes.RENDER_TYPE_NATIVE.equals(instance.getRenderType())){
+          instance.onCreateFinish();
+      }
+    }
+
+    instance.mHasCreateFinish = true;
+
+    if (null != instance.getWXPerformance()){
+      instance.getWXPerformance().callCreateFinishTime = System.currentTimeMillis()-instance.getWXPerformance().renderTimeOrigin;
+    }
+    instance.onOldFsRenderTimeLogic();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionLayout.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionLayout.java
new file mode 100644
index 0000000..c2c2c0c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionLayout.java
@@ -0,0 +1,51 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.WXComponent;
+
+public class GraphicActionLayout extends BasicGraphicAction {
+
+  private final GraphicPosition mLayoutPosition;
+  private final GraphicSize mLayoutSize;
+  private final boolean mIsLayoutRTL;
+
+  public GraphicActionLayout(WXSDKInstance instance, String ref, GraphicPosition layoutPosition, GraphicSize layoutSize, boolean isRTL) {
+    super(instance, ref);
+    this.mLayoutPosition = layoutPosition;
+    this.mLayoutSize = layoutSize;
+    this.mIsLayoutRTL = isRTL;
+  }
+
+  @Override
+  public void executeAction() {
+    WXComponent component = WXSDKManager
+        .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null) {
+      return;
+    }
+
+    component.setIsLayoutRTL(mIsLayoutRTL);
+    component.setDemission(mLayoutSize, mLayoutPosition);
+    component.setSafeLayout(component);
+    component.setPadding(component.getPadding(), component.getBorder());
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionMoveElement.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionMoveElement.java
new file mode 100644
index 0000000..4c38840
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionMoveElement.java
@@ -0,0 +1,71 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+
+public class GraphicActionMoveElement extends BasicGraphicAction {
+
+  private String mParentref;
+  private int mIndex;
+
+  public GraphicActionMoveElement(WXSDKInstance instance, String ref, String parentRef, int index) {
+    super(instance, ref);
+    this.mParentref = parentRef;
+    this.mIndex = index;
+  }
+
+  @Override
+  public void executeAction() {
+    WXComponent component = WXSDKManager
+        .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if(component == null) {
+      return;
+    }
+    WXVContainer oldParent = component.getParent();
+    WXComponent newParent = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), mParentref);
+    if (oldParent == null
+            || newParent == null || !(newParent instanceof WXVContainer)) {
+      return;
+    }
+
+    if (component.getHostView() != null && !TextUtils.equals(component.getComponentType(), "video") && !TextUtils.equals(component.getComponentType(), "videoplus")) {
+      int[] location = new  int[2] ;
+      component.getHostView().getLocationInWindow(location);
+    }
+
+    oldParent.remove(component, false);
+
+    ((WXVContainer) newParent).addChild(component, mIndex);
+
+    if (component.getHostView() != null && !TextUtils.equals(component.getComponentType(), "video") && !TextUtils.equals(component.getComponentType(), "videoplus")) {
+      int[] location = new  int[2] ;
+      component.getHostView().getLocationInWindow(location);
+    }
+
+    if (!component.isVirtualComponent()) {
+      ((WXVContainer) newParent).addSubView(component.getHostView(), mIndex);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRefreshFinish.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRefreshFinish.java
new file mode 100644
index 0000000..3f6fde7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRefreshFinish.java
@@ -0,0 +1,52 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.annotation.NonNull;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by listen on 18/01/09.
+ */
+public class GraphicActionRefreshFinish extends BasicGraphicAction {
+
+  private int mLayoutWidth;
+  private int mLayoutHeight;
+
+  public GraphicActionRefreshFinish(@NonNull WXSDKInstance instance) {
+    super(instance, "");
+    WXComponent component = instance.getRootComponent();
+    if (null != component) {
+        this.mLayoutWidth = (int) component.getLayoutWidth();
+        this.mLayoutHeight = (int) component.getLayoutHeight();
+    }
+  }
+
+  @Override
+  public void executeAction() {
+    final WXSDKInstance instance = getWXSDKIntance();
+    if (instance == null || instance.getContext() == null) {
+      return;
+    }
+
+    instance.onRefreshSuccess(mLayoutWidth, mLayoutHeight);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveChildFromRichtext.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveChildFromRichtext.java
new file mode 100755
index 0000000..0c405fc
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveChildFromRichtext.java
@@ -0,0 +1,42 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.richtext.WXRichText;
+
+public class GraphicActionRemoveChildFromRichtext extends BasicGraphicAction{
+    private String ref;
+    private String parentRef;
+    private WXRichText richText;
+    public GraphicActionRemoveChildFromRichtext(WXSDKInstance instance,String ref,String parentRef,String richtextRef){
+        super(instance, richtextRef);
+        this.ref = ref;
+        this.parentRef = parentRef;
+        richText = (WXRichText) WXSDKManager.getInstance().getWXRenderManager().
+                getWXComponent(instance.getInstanceId(),richtextRef);
+        if(richText != null){
+            richText.removeChildNode(parentRef,ref);
+        }
+    }
+    @Override
+    public void executeAction() {
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveElement.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveElement.java
new file mode 100644
index 0000000..abf4a8b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveElement.java
@@ -0,0 +1,67 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+
+public class GraphicActionRemoveElement extends BasicGraphicAction {
+
+  public GraphicActionRemoveElement(WXSDKInstance instance, String ref) {
+    super(instance, ref);
+  }
+
+  @Override
+  public void executeAction() {
+    WXComponent component = WXSDKManager
+        .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null || component.getParent() == null || component.getInstance() == null) {
+      return;
+    }
+    clearRegistryForComponent(component);
+    WXVContainer parent = component.getParent();
+
+    if (component.getHostView() != null && !TextUtils.equals(component.getComponentType(), "video") && !TextUtils.equals(component.getComponentType(), "videoplus")) {
+      int[] location = new  int[2];
+      component.getHostView().getLocationInWindow(location);
+      //component.getInstance().onChangeElement(parent, location[1] > component.getInstance().getWeexHeight() + 1);
+    }
+
+    parent.remove(component, true);
+  }
+
+  private void clearRegistryForComponent(WXComponent component) {
+    WXComponent removedComponent = WXSDKManager.getInstance().getWXRenderManager().unregisterComponent(getPageId(), getRef());
+    if (removedComponent != null) {
+      removedComponent.removeAllEvent();
+      removedComponent.removeStickyStyle();
+    }
+    if (component instanceof WXVContainer) {
+      WXVContainer container = (WXVContainer) component;
+      int count = container.childCount();
+      for (int i = count - 1; i >= 0; --i) {
+        clearRegistryForComponent(container.getChild(i));
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveEvent.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveEvent.java
new file mode 100644
index 0000000..5727044
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRemoveEvent.java
@@ -0,0 +1,51 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.tracing.Stopwatch;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by listen on 18/01/11.
+ */
+public class GraphicActionRemoveEvent extends BasicGraphicAction {
+
+  private final String mEvent;
+
+  public GraphicActionRemoveEvent(WXSDKInstance instance, String ref, Object event) {
+    super(instance, ref);
+    this.mEvent = WXEvent.getEventName(event);
+  }
+
+  @Override
+  public void executeAction() {
+    WXComponent component = WXSDKManager
+        .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null) {
+      return;
+    }
+
+    Stopwatch.tick();
+    component.removeEvent(mEvent);
+    Stopwatch.split("removeEventFromComponent");
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRenderSuccess.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRenderSuccess.java
new file mode 100644
index 0000000..8c8615f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionRenderSuccess.java
@@ -0,0 +1,48 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.annotation.NonNull;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.ui.component.WXComponent;
+
+public class GraphicActionRenderSuccess extends BasicGraphicAction {
+
+    public GraphicActionRenderSuccess(@NonNull WXSDKInstance instance) {
+        super(instance, "");
+    }
+
+    @Override
+    public void executeAction() {
+        final WXSDKInstance instance = getWXSDKIntance();
+        if (instance == null || instance.getContext() == null) {
+            return;
+        }
+        WXComponent component = instance.getRootComponent();
+        int layoutWidth = 0;
+        int layoutHeight = 0;
+        if (null != component) {
+            layoutWidth = (int) component.getLayoutWidth();
+            layoutHeight = (int) component.getLayoutHeight();
+        }
+        instance.onRenderSuccess(layoutWidth, layoutHeight);
+    }
+
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionScrollToElement.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionScrollToElement.java
new file mode 100644
index 0000000..5a4b809
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionScrollToElement.java
@@ -0,0 +1,53 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.Scrollable;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by listen on 18/01/09.
+ */
+public class GraphicActionScrollToElement extends BasicGraphicAction {
+
+  private final JSONObject mOptions;
+
+  public GraphicActionScrollToElement(WXSDKInstance instance, String ref, JSONObject options) {
+    super(instance, ref);
+    this.mOptions = options;
+  }
+
+  @Override
+  public void executeAction() {
+    WXComponent component = WXSDKManager
+        .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null) {
+      return;
+    }
+
+    Scrollable scroller = component.getParentScroller();
+    if (scroller == null) {
+      return;
+    }
+    scroller.scrollTo(component, mOptions);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateAttr.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateAttr.java
new file mode 100644
index 0000000..d7713ce
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateAttr.java
@@ -0,0 +1,54 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.WXComponent;
+
+import java.util.Map;
+
+public class GraphicActionUpdateAttr extends BasicGraphicAction {
+
+  private Map<String, String> mAttrs;
+  private WXComponent component;
+
+  public GraphicActionUpdateAttr(WXSDKInstance instance, String ref,
+                                 Map<String, String> attrs) {
+    super(instance, ref);
+    this.mAttrs = attrs;
+
+    component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null) {
+      return;
+    }
+    if (mAttrs != null) {
+      component.addAttr(mAttrs);
+    }
+  }
+
+  @Override
+  public void executeAction() {
+    if (component == null) {
+      return;
+    }
+    component.getAttrs().mergeAttr();
+    component.updateAttrs(mAttrs);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateRichtextAttr.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateRichtextAttr.java
new file mode 100755
index 0000000..19b896b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateRichtextAttr.java
@@ -0,0 +1,43 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.richtext.WXRichText;
+import java.util.HashMap;
+import java.util.Map;
+
+public class GraphicActionUpdateRichtextAttr extends BasicGraphicAction{
+
+    public GraphicActionUpdateRichtextAttr(WXSDKInstance instance, String ref, HashMap<String, String> attrs, String parentRef, String richTextRef){
+        super(instance, richTextRef);
+        WXRichText richText =  (WXRichText) WXSDKManager.getInstance().getWXRenderManager()
+                .getWXComponent(getPageId(), richTextRef);
+        if(richText != null) {
+            Map<String, Object> map = new HashMap<>();
+            map.putAll(attrs);
+            richText.updateChildNodeAttrs(ref, map);
+        }
+    }
+    @Override
+    public void executeAction() {
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateRichtextStyle.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateRichtextStyle.java
new file mode 100755
index 0000000..b9cc2e5
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateRichtextStyle.java
@@ -0,0 +1,44 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.richtext.WXRichText;
+
+import java.util.HashMap;
+import java.util.Map;
+
+public class GraphicActionUpdateRichtextStyle  extends BasicGraphicAction{
+    public GraphicActionUpdateRichtextStyle(WXSDKInstance instance, String ref, HashMap<String, String> styles, String parentRef, String richTextRef){
+        super(instance, richTextRef);
+        WXRichText richText =  (WXRichText) WXSDKManager.getInstance().getWXRenderManager()
+                .getWXComponent(getPageId(), richTextRef);
+        if(richText != null){
+                Map<String, Object> map = new HashMap<>();
+                map.putAll(styles);
+                richText.updateChildNodeStyles(ref, map);
+
+        }
+    }
+    @Override
+    public void executeAction() {
+
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateStyle.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateStyle.java
new file mode 100644
index 0000000..fd9e999
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicActionUpdateStyle.java
@@ -0,0 +1,142 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.support.v4.util.ArrayMap;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.dom.transition.WXTransition;
+import org.apache.weex.ui.component.WXComponent;
+
+import java.util.Map;
+
+public class GraphicActionUpdateStyle extends BasicGraphicAction {
+
+  private Map<String, Object> mStyle;
+  private WXComponent component;
+  private boolean mIsCausedByPesudo;
+  private boolean mIsBorderSet;
+
+  public GraphicActionUpdateStyle(WXSDKInstance instance, String ref,
+                                  Map<String, Object> style,
+                                  Map<String, String> paddings,
+                                  Map<String, String> margins,
+                                  Map<String, String> borders) {
+    this(instance, ref, style, paddings, margins, borders, false);
+  }
+
+  public GraphicActionUpdateStyle(WXSDKInstance instance, String ref,
+                                  Map<String, Object> style,
+                                  CSSShorthand paddings,
+                                  CSSShorthand margins,
+                                  CSSShorthand borders, boolean byPesudo) {
+    super(instance, ref);
+    this.mStyle = style;
+    this.mIsCausedByPesudo = byPesudo;
+
+    component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null) {
+      return;
+    }
+    if (null != mStyle) {
+      component.updateStyle(mStyle, mIsCausedByPesudo);
+      if(style.containsKey(Constants.Name.TRANSFORM) && component.getTransition() == null) {
+        Map<String, Object> animationMap = new ArrayMap<>(2);
+        animationMap.put(Constants.Name.TRANSFORM, style.get(Constants.Name.TRANSFORM));
+        animationMap
+            .put(Constants.Name.TRANSFORM_ORIGIN, style.get(Constants.Name.TRANSFORM_ORIGIN));
+        component.addAnimationForElement(animationMap);
+      }
+    }
+
+    if (null != paddings) {
+      component.setPaddings(paddings);
+    }
+
+    if (null != margins) {
+      component.setMargins(margins);
+    }
+
+    if (null != borders) {
+      mIsBorderSet = true;
+      component.setBorders(borders);
+    }
+  }
+
+  public GraphicActionUpdateStyle(WXSDKInstance instance, String ref,
+                                  Map<String, Object> style,
+                                  Map<String, String> paddings,
+                                  Map<String, String> margins,
+                                  Map<String, String> borders, boolean byPesudo) {
+    super(instance, ref);
+    this.mStyle = style;
+    this.mIsCausedByPesudo = byPesudo;
+
+    component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+    if (component == null) {
+      return;
+    }
+    if (null != mStyle) {
+      component.addStyle(mStyle, mIsCausedByPesudo);
+      if(style.containsKey(Constants.Name.TRANSFORM) && component.getTransition() == null){
+        Map<String, Object> animationMap = new ArrayMap<>(2);
+        animationMap.put(Constants.Name.TRANSFORM, style.get(Constants.Name.TRANSFORM));
+        animationMap.put(Constants.Name.TRANSFORM_ORIGIN, style.get(Constants.Name.TRANSFORM_ORIGIN));
+        component.addAnimationForElement(animationMap);
+        WXBridgeManager.getInstance().markDirty(component.getInstanceId(), component.getRef(), true);
+      }
+    }
+
+    if (null != paddings) {
+      component.addShorthand(paddings);
+    }
+
+    if (null != margins) {
+      component.addShorthand(margins);
+    }
+
+    if (null != borders) {
+      mIsBorderSet = true;
+      component.addShorthand(borders);
+    }
+  }
+
+  @Override
+  public void executeAction() {
+    if (component == null) return;
+    if (mStyle != null) {
+      if(component.getTransition() != null){
+        component.getTransition().updateTranstionParams(mStyle);
+        if(component.getTransition().hasTransitionProperty(mStyle)){
+          component.getTransition().startTransition(mStyle);
+        }
+      } else {
+        component.setTransition(WXTransition.fromMap(mStyle, component));
+        component.updateStyles(mStyle);
+      }
+    } else if (mIsBorderSet) {
+      component.updateStyles(component);
+    }
+  }
+}
+
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicPosition.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicPosition.java
new file mode 100644
index 0000000..5796caf
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicPosition.java
@@ -0,0 +1,74 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+public class GraphicPosition {
+
+  private float mLeft;
+  private float mTop;
+  private float mRight;
+  private float mBottom;
+
+  public GraphicPosition(float left, float top, float right, float bottom) {
+    this.mLeft = left;
+    this.mTop = top;
+    this.mRight = right;
+    this.mBottom = bottom;
+  }
+
+  public float getLeft() {
+    return mLeft;
+  }
+
+  public void setLeft(float left) {
+    this.mLeft = left;
+  }
+
+  public float getTop() {
+    return mTop;
+  }
+
+  public void setTop(float top) {
+    this.mTop = top;
+  }
+
+  public float getRight() {
+    return mRight;
+  }
+
+  public void setRight(float right) {
+    this.mRight = right;
+  }
+
+  public float getBottom() {
+    return mBottom;
+  }
+
+  public void setBottom(float bottom) {
+    this.mBottom = bottom;
+  }
+
+
+  public void update(float top, float bottom, float left, float right) {
+    this.mTop = top;
+    this.mBottom = bottom;
+    this.mLeft = left;
+    this.mRight = right;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicSize.java b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicSize.java
new file mode 100644
index 0000000..f523644
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/GraphicSize.java
@@ -0,0 +1,51 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+public class GraphicSize {
+
+  private float mWidth;
+  private float mHeight;
+
+  public GraphicSize(float width, float height) {
+    this.mWidth = width;
+    this.mHeight = height;
+  }
+
+  public float getWidth() {
+    return mWidth;
+  }
+
+  public void setWidth(float width) {
+    this.mWidth = width;
+  }
+
+  public float getHeight() {
+    return mHeight;
+  }
+
+  public void setHeight(float height) {
+    this.mHeight = height;
+  }
+
+  public void update(float width, float height) {
+    this.mWidth = width;
+    this.mHeight = height;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/IExecutable.java b/android/sdk/src/main/java/org/apache/weex/ui/action/IExecutable.java
new file mode 100644
index 0000000..c140e49
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/IExecutable.java
@@ -0,0 +1,25 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+public interface IExecutable {
+
+  void executeAction();
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/action/UpdateComponentDataAction.java b/android/sdk/src/main/java/org/apache/weex/ui/action/UpdateComponentDataAction.java
new file mode 100644
index 0000000..ef14a2e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/action/UpdateComponentDataAction.java
@@ -0,0 +1,71 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.action;
+
+import android.text.TextUtils;
+
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.SimpleJSCallback;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.list.template.CellDataManager;
+import org.apache.weex.ui.component.list.template.WXRecyclerTemplateList;
+import org.apache.weex.utils.WXLogUtils;
+
+
+/**
+ * Created by furture on 2018/1/23.
+ */
+
+public class UpdateComponentDataAction extends BasicGraphicAction{
+
+    private String virtualComponentId;
+    private JSONObject data;
+    private String callback;
+
+
+    public UpdateComponentDataAction(WXSDKInstance instance, String virtualComponentId,
+                                     JSONObject data, String callback) {
+        super(instance, CellDataManager.getListRef(virtualComponentId));
+        this.virtualComponentId = virtualComponentId;
+        this.data = data;
+        this.callback = callback;
+    }
+
+    @Override
+    public void executeAction() {
+        if(TextUtils.isEmpty(getRef())){
+            WXLogUtils.e("wrong virtualComponentId split error " + virtualComponentId);
+            return;
+        }
+        WXComponent component = WXSDKManager
+            .getInstance().getWXRenderManager().getWXComponent(getPageId(), getRef());
+        if(component instanceof WXRecyclerTemplateList){
+            WXRecyclerTemplateList templateList = (WXRecyclerTemplateList) component;
+            templateList.getCellDataManager().updateVirtualComponentData(virtualComponentId, data);
+            templateList.notifyUpdateList();
+            SimpleJSCallback jsCallback = new SimpleJSCallback(component.getInstanceId(), callback);
+            jsCallback.invoke(true);
+        }else{
+            WXLogUtils.e("recycler-list wrong virtualComponentId " + virtualComponentId);
+        }
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/animation/BackgroundColorProperty.java b/android/sdk/src/main/java/org/apache/weex/ui/animation/BackgroundColorProperty.java
new file mode 100644
index 0000000..b6eab01
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/animation/BackgroundColorProperty.java
@@ -0,0 +1,66 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.ui.animation;
+
+
+import android.graphics.Color;
+import android.graphics.drawable.ColorDrawable;
+import android.util.Property;
+import android.view.View;
+
+import org.apache.weex.ui.view.border.BorderDrawable;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+public class BackgroundColorProperty extends Property<View, Integer> {
+
+  private final static String TAG = "BackgroundColorAnimation";
+
+  public BackgroundColorProperty() {
+    super(Integer.class, WXAnimationBean.Style.BACKGROUND_COLOR);
+  }
+
+  @Override
+  public Integer get(View object) {
+    int color;
+    BorderDrawable borderDrawable;
+    if ((borderDrawable = WXViewUtils.getBorderDrawable(object)) != null) {
+      color = borderDrawable.getColor();
+    } else if (object.getBackground() instanceof ColorDrawable) {
+      color = ((ColorDrawable) object.getBackground()).getColor();
+    } else {
+      color = Color.TRANSPARENT;
+      WXLogUtils.e(TAG, "Unsupported background type");
+    }
+    return color;
+  }
+
+  @Override
+  public void set(View object, Integer value) {
+    BorderDrawable borderDrawable;
+    if ((borderDrawable = WXViewUtils.getBorderDrawable(object)) != null) {
+      borderDrawable.setColor(value);
+    } else if (object.getBackground() instanceof ColorDrawable) {
+      ((ColorDrawable) object.getBackground()).setColor(value);
+    } else {
+      WXLogUtils.e(TAG, "Unsupported background type");
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/animation/CameraDistanceProperty.java b/android/sdk/src/main/java/org/apache/weex/ui/animation/CameraDistanceProperty.java
new file mode 100644
index 0000000..5024388
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/animation/CameraDistanceProperty.java
@@ -0,0 +1,54 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.animation;
+
+import android.os.Build.VERSION;
+import android.os.Build.VERSION_CODES;
+import android.util.Property;
+import android.view.View;
+
+
+class CameraDistanceProperty extends Property<View, Float> {
+
+  private final static String TAG = "CameraDistance";
+  private static CameraDistanceProperty instance;
+
+  static Property<View, Float> getInstance(){
+    return instance;
+  }
+
+  private CameraDistanceProperty() {
+    super(Float.class, TAG);
+  }
+
+  @Override
+  public Float get(View view) {
+    if (VERSION.SDK_INT >= VERSION_CODES.JELLY_BEAN) {
+      return view.getCameraDistance();
+    }
+    else{
+      return Float.NaN;
+    }
+  }
+
+  @Override
+  public void set(View object, Float value) {
+    object.setCameraDistance(value);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/animation/HeightProperty.java b/android/sdk/src/main/java/org/apache/weex/ui/animation/HeightProperty.java
new file mode 100644
index 0000000..9fc404e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/animation/HeightProperty.java
@@ -0,0 +1,35 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.animation;
+
+
+import android.view.ViewGroup.LayoutParams;
+
+public class HeightProperty extends LayoutParamsProperty {
+
+  @Override
+  protected Integer getProperty(LayoutParams layoutParams) {
+    return layoutParams.height;
+  }
+
+  @Override
+  protected void setProperty(LayoutParams layoutParams, Integer expected) {
+    layoutParams.height = expected;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/animation/LayoutParamsProperty.java b/android/sdk/src/main/java/org/apache/weex/ui/animation/LayoutParamsProperty.java
new file mode 100644
index 0000000..f4ef1d7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/animation/LayoutParamsProperty.java
@@ -0,0 +1,64 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.animation;
+
+
+import android.util.Property;
+import android.view.View;
+import android.view.ViewGroup.LayoutParams;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.view.IRenderResult;
+
+/**
+ * android.util.IntProperty<T> cannot be applied here, as it is only added at API 24.
+ */
+abstract class LayoutParamsProperty extends Property<View, Integer> {
+
+  LayoutParamsProperty() {
+    super(Integer.class, "layoutParams");
+  }
+
+  @Override
+  public Integer get(View object) {
+    LayoutParams layoutParams;
+    if (object != null && (layoutParams = object.getLayoutParams()) != null) {
+      return getProperty(layoutParams);
+    }
+    return 0;
+  }
+
+  @Override
+  public void set(View object, Integer value) {
+    LayoutParams layoutParams;
+    if (object != null && (layoutParams = object.getLayoutParams()) != null) {
+      setProperty(layoutParams, value);
+      if (object instanceof IRenderResult) {
+        WXComponent component = ((IRenderResult) object).getComponent();
+        if (component != null) {
+            component.notifyNativeSizeChanged(layoutParams.width, layoutParams.height);
+        }
+      }
+      object.requestLayout();
+    }
+  }
+
+  protected abstract Integer getProperty(LayoutParams layoutParams);
+
+  protected abstract void setProperty(LayoutParams layoutParams, Integer expected);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/animation/TransformParser.java b/android/sdk/src/main/java/org/apache/weex/ui/animation/TransformParser.java
new file mode 100644
index 0000000..9087fab
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/animation/TransformParser.java
@@ -0,0 +1,310 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.animation;
+
+import android.animation.PropertyValuesHolder;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+import android.util.Pair;
+import android.util.Property;
+import android.view.View;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.utils.FunctionParser;
+import org.apache.weex.utils.WXDataStructureUtil;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.LinkedHashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Created by furture on 2017/10/24.
+ */
+
+public class TransformParser {
+
+    public final static String WX_TRANSLATE = "translate";
+    public final static String WX_TRANSLATE_X = "translateX";
+    public final static String WX_TRANSLATE_Y = "translateY";
+    public final static String WX_ROTATE = "rotate";
+    public final static String WX_ROTATE_X ="rotateX";
+    public final static String WX_ROTATE_Y ="rotateY";
+    public final static String WX_ROTATE_Z ="rotateZ";
+    public final static String WX_SCALE = "scale";
+    public final static String WX_SCALE_X = "scaleX";
+    public final static String WX_SCALE_Y = "scaleY";
+
+    public final static String BACKGROUND_COLOR = Constants.Name.BACKGROUND_COLOR;
+    public final static String WIDTH = Constants.Name.WIDTH;
+    public final static String HEIGHT = Constants.Name.HEIGHT;
+    public final static String TOP = "top";
+    public final static String BOTTOM = "bottom";
+    public final static String RIGHT = "right";
+    public final static String LEFT = "left";
+    public final static String CENTER = "center";
+    private static final String HALF = "50%";
+    private static final String FULL = "100%";
+    private static final String ZERO = "0%";
+    private static final String PX = "px";
+    private static final String DEG = "deg";
+    public static Map<String, List<Property<View,Float>>> wxToAndroidMap = new ArrayMap<>();
+
+
+    static {
+        wxToAndroidMap.put(WX_TRANSLATE, Arrays.asList
+                (View.TRANSLATION_X, View.TRANSLATION_Y));
+        wxToAndroidMap.put(WX_TRANSLATE_X, Collections.singletonList(View.TRANSLATION_X));
+        wxToAndroidMap.put(WX_TRANSLATE_Y, Collections.singletonList(View.TRANSLATION_Y));
+        wxToAndroidMap.put(WX_ROTATE, Collections.singletonList(View.ROTATION));
+        wxToAndroidMap.put(WX_ROTATE_Z, Collections.singletonList(View.ROTATION));
+        wxToAndroidMap.put(WX_ROTATE_X, Collections.singletonList(View.ROTATION_X));
+        wxToAndroidMap.put(WX_ROTATE_Y, Collections.singletonList(View.ROTATION_Y));
+        wxToAndroidMap.put(WX_SCALE, Arrays.asList(View.SCALE_X, View.SCALE_Y));
+        wxToAndroidMap.put(WX_SCALE_X, Collections.singletonList(View.SCALE_X));
+        wxToAndroidMap.put(WX_SCALE_Y, Collections.singletonList(View.SCALE_Y));
+        wxToAndroidMap.put(Constants.Name.PERSPECTIVE, Collections.singletonList(CameraDistanceProperty.getInstance()));
+        wxToAndroidMap = Collections.unmodifiableMap(wxToAndroidMap);
+    }
+
+    public static PropertyValuesHolder[] toHolders(Map<Property<View,Float>, Float> transformMap){
+        PropertyValuesHolder[]  holders = new PropertyValuesHolder[transformMap.size()];
+        int i=0;
+        for (Map.Entry<Property<View, Float>, Float> entry : transformMap.entrySet()) {
+            holders[i] = PropertyValuesHolder.ofFloat(entry.getKey(), entry.getValue());
+            i++;
+        }
+        return holders;
+    }
+
+    public static Map<Property<View,Float>, Float> parseTransForm(String instanceId, @Nullable String rawTransform, final int width,
+                                                                  final int height, final int viewportW) {
+        try{
+
+            if (!TextUtils.isEmpty(rawTransform)) {
+                FunctionParser<Property<View,Float>, Float> parser = new FunctionParser<>
+                        (rawTransform, new FunctionParser.Mapper<Property<View,Float>, Float>() {
+                            @Override
+                            public Map<Property<View,Float>, Float> map(String functionName, List<String> raw) {
+                                if (raw != null && !raw.isEmpty()) {
+                                    if (wxToAndroidMap.containsKey(functionName)) {
+                                        return convertParam(width, height,viewportW, wxToAndroidMap.get(functionName), raw);
+                                    }
+                                }
+                                return new HashMap<>();
+                            }
+
+                            private Map<Property<View,Float>, Float> convertParam(int width, int height, int viewportW,
+                                                                                  @NonNull List<Property<View,Float>> propertyList,
+                                                                                  @NonNull List<String> rawValue) {
+
+                                Map<Property<View,Float>, Float> result = WXDataStructureUtil.newHashMapWithExpectedSize(propertyList.size());
+                                List<Float> convertedList = new ArrayList<>(propertyList.size());
+                                if (propertyList.contains(View.ROTATION) ||
+                                        propertyList.contains(View.ROTATION_X) ||
+                                        propertyList.contains(View.ROTATION_Y)) {
+                                    convertedList.addAll(parseRotationZ(rawValue));
+                                }else if (propertyList.contains(View.TRANSLATION_X) ||
+                                        propertyList.contains(View.TRANSLATION_Y)) {
+                                    convertedList.addAll(parseTranslation(propertyList, width, height, rawValue,viewportW));
+                                } else if (propertyList.contains(View.SCALE_X) ||
+                                        propertyList.contains(View.SCALE_Y)) {
+                                    convertedList.addAll(parseScale(propertyList.size(), rawValue));
+                                }
+                                else if(propertyList.contains(CameraDistanceProperty.getInstance())){
+                                    convertedList.add(parseCameraDistance(rawValue));
+                                }
+                                if (propertyList.size() == convertedList.size()) {
+                                    for (int i = 0; i < propertyList.size(); i++) {
+                                        result.put(propertyList.get(i), convertedList.get(i));
+                                    }
+                                }
+                                return result;
+                            }
+
+                            private List<Float> parseScale(int size, @NonNull List<String> rawValue) {
+                                List<Float> convertedList = new ArrayList<>(rawValue.size() * 2);
+                                List<Float> rawFloat = new ArrayList<>(rawValue.size());
+                                for (String item : rawValue) {
+                                    rawFloat.add(WXUtils.fastGetFloat(item));
+                                }
+                                convertedList.addAll(rawFloat);
+                                if (size != 1 && rawValue.size() == 1) {
+                                    convertedList.addAll(rawFloat);
+                                }
+                                return convertedList;
+                            }
+
+                            private @NonNull
+                            List<Float> parseRotationZ(@NonNull List<String> rawValue) {
+                                List<Float> convertedList = new ArrayList<>(1);
+                                int suffix;
+                                for (String raw : rawValue) {
+                                    if ((suffix = raw.lastIndexOf(DEG)) != -1) {
+                                        convertedList.add(WXUtils.fastGetFloat(raw.substring(0, suffix)));
+                                    } else {
+                                        convertedList.add((float) Math.toDegrees(WXUtils.fastGetFloat(raw)));
+                                    }
+                                }
+                                return convertedList;
+                            }
+
+                            /**
+                             * As "translate(50%, 25%)" or "translate(25px, 30px)" both are valid,
+                             * parsing translate is complicated than other method.
+                             * Add your waste time here if you try to optimize this method like {@link #parseScale(int, List)}
+                             * Time: 0.5h
+                             */
+                            private List<Float> parseTranslation(List<Property<View,Float>> propertyList,
+                                                                 int width, int height,
+                                                                 @NonNull List<String> rawValue, int viewportW) {
+                                List<Float> convertedList = new ArrayList<>(2);
+                                String first = rawValue.get(0);
+                                if (propertyList.size() == 1) {
+                                    parseSingleTranslation(propertyList, width, height, convertedList, first,viewportW);
+                                } else {
+                                    parseDoubleTranslation(width, height, rawValue, convertedList, first,viewportW);
+                                }
+                                return convertedList;
+                            }
+
+                            private void parseSingleTranslation(List<Property<View,Float>> propertyList, int width, int height,
+                                                                List<Float> convertedList, String first, int viewportW) {
+                                if (propertyList.contains(View.TRANSLATION_X)) {
+                                    convertedList.add(parsePercentOrPx(first, width,viewportW));
+                                } else if (propertyList.contains(View.TRANSLATION_Y)) {
+                                    convertedList.add(parsePercentOrPx(first, height,viewportW));
+                                }
+                            }
+
+                            private void parseDoubleTranslation(int width, int height,
+                                                                @NonNull List<String> rawValue,
+                                                                List<Float> convertedList, String first, int viewportW) {
+                                String second;
+                                if (rawValue.size() == 1) {
+                                    second = first;
+                                } else {
+                                    second = rawValue.get(1);
+                                }
+                                convertedList.add(parsePercentOrPx(first, width,viewportW));
+                                convertedList.add(parsePercentOrPx(second, height,viewportW));
+                            }
+
+                            private Float parseCameraDistance(List<String> rawValue){
+                                float ret= Float.MAX_VALUE;
+                                if(rawValue.size() == 1){
+                                    float value = WXViewUtils.getRealPxByWidth(WXUtils.getFloat(rawValue.get(0)), viewportW);
+                                    float scale = WXEnvironment.getApplication().getResources().getDisplayMetrics().density;
+                                    if (!Float.isNaN(value) && value > 0) {
+                                        ret = value * scale;
+                                    }
+                                }
+                                return ret;
+                            }
+                        });
+                return parser.parse();
+            }
+        }catch (Exception e){
+            WXLogUtils.e("TransformParser", e);
+            WXExceptionUtils.commitCriticalExceptionRT(instanceId,
+                    WXErrorCode.WX_RENDER_ERR_TRANSITION,
+                    "parse animation transition",
+                    WXErrorCode.WX_RENDER_ERR_TRANSITION.getErrorMsg() + "parse transition error: " +  e.getMessage(),
+                    null);
+        }
+        return new LinkedHashMap<>();
+    }
+
+    private static Pair<Float, Float> parsePivot(@Nullable String transformOrigin,
+                                                 int width, int height, int viewportW) {
+        if (!TextUtils.isEmpty(transformOrigin)) {
+            int firstSpace = transformOrigin.indexOf(FunctionParser.SPACE);
+            if (firstSpace != -1) {
+                int i = firstSpace;
+                for (; i < transformOrigin.length(); i++) {
+                    if (transformOrigin.charAt(i) != FunctionParser.SPACE) {
+                        break;
+                    }
+                }
+                if (i < transformOrigin.length() && transformOrigin.charAt(i) != FunctionParser.SPACE) {
+                    List<String> list = new ArrayList<>(2);
+                    list.add(transformOrigin.substring(0, firstSpace).trim());
+                    list.add(transformOrigin.substring(i, transformOrigin.length()).trim());
+                    return parsePivot(list, width, height,viewportW);
+                }
+            }
+        }
+        return null;
+    }
+
+    private static Pair<Float, Float> parsePivot(@NonNull List<String> list, int width, int height, int viewportW) {
+        return new Pair<>(
+                parsePivotX(list.get(0), width,viewportW), parsePivotY(list.get(1), height,viewportW));
+    }
+
+    private static float parsePivotX(String x, int width, int viewportW) {
+        String value = x;
+        if (WXAnimationBean.Style.LEFT.equals(x)) {
+            value = ZERO;
+        } else if (WXAnimationBean.Style.RIGHT.equals(x)) {
+            value = FULL;
+        } else if (WXAnimationBean.Style.CENTER.equals(x)) {
+            value = HALF;
+        }
+        return parsePercentOrPx(value, width,viewportW);
+    }
+
+    private static float parsePivotY(String y, int height, int viewportW) {
+        String value = y;
+        if (WXAnimationBean.Style.TOP.equals(y)) {
+            value = ZERO;
+        } else if (WXAnimationBean.Style.BOTTOM.equals(y)) {
+            value = FULL;
+        } else if (WXAnimationBean.Style.CENTER.equals(y)) {
+            value = HALF;
+        }
+        return parsePercentOrPx(value, height,viewportW);
+    }
+
+    private static float parsePercentOrPx(String raw, int unit, int viewportW) {
+        final int precision = 1;
+        int suffix;
+        if ((suffix = raw.lastIndexOf(WXUtils.PERCENT)) != -1) {
+            return parsePercent(raw.substring(0, suffix), unit, precision);
+        } else if ((suffix = raw.lastIndexOf(PX)) != -1) {
+            return WXViewUtils.getRealPxByWidth(WXUtils.fastGetFloat(raw.substring(0, suffix), precision),viewportW);
+        }
+        return WXViewUtils.getRealPxByWidth(WXUtils.fastGetFloat(raw, precision),viewportW);
+    }
+
+    private static float parsePercent(String percent, int unit, int precision) {
+        return WXUtils.fastGetFloat(percent, precision) / 100 * unit;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/animation/WXAnimationBean.java b/android/sdk/src/main/java/org/apache/weex/ui/animation/WXAnimationBean.java
new file mode 100644
index 0000000..57a8bc7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/animation/WXAnimationBean.java
@@ -0,0 +1,239 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.animation;
+
+import android.animation.PropertyValuesHolder;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+import android.util.Pair;
+import android.util.Property;
+import android.view.View;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.Constants.Name;
+import org.apache.weex.utils.FunctionParser;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.LinkedHashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.Map.Entry;
+
+public class WXAnimationBean {
+
+  public final static String LINEAR = "linear";
+  public final static String EASE_IN_OUT = "ease-in-out";
+  public final static String EASE_IN = "ease-in";
+  public final static String EASE_OUT = "ease-out";
+  public final static String CUBIC_BEZIER = "cubic-bezier";
+  public final static int NUM_CUBIC_PARAM = 4;
+  public long delay;
+  public long duration;
+  public String timingFunction;
+  public @Nullable Style styles;
+  public boolean needLayout;
+
+  public static class Style {
+
+    public final static String WX_TRANSLATE = "translate";
+    public final static String WX_TRANSLATE_X = "translateX";
+    public final static String WX_TRANSLATE_Y = "translateY";
+    public final static String WX_ROTATE = "rotate";
+    public final static String WX_SCALE_X = "scaleX";
+    public final static String WX_SCALE_Y = "scaleY";
+    public final static String WX_SCALE = "scale";
+    public final static String WX_ROTATE_X ="rotateX";
+    public final static String WX_ROTATE_Y ="rotateY";
+    public final static String BACKGROUND_COLOR = Constants.Name.BACKGROUND_COLOR;
+    public final static String WIDTH = Constants.Name.WIDTH;
+    public final static String HEIGHT = Constants.Name.HEIGHT;
+    public final static String TOP = "top";
+    public final static String BOTTOM = "bottom";
+    public final static String RIGHT = "right";
+    public final static String LEFT = "left";
+    public final static String CENTER = "center";
+    private static final String HALF = "50%";
+    private static final String FULL = "100%";
+    private static final String ZERO = "0%";
+    private static final String PX = "px";
+    private static final String DEG = "deg";
+    public static Map<String, List<Property<View,Float>>> wxToAndroidMap = new ArrayMap<>();
+    private static Map<Property<View, Float>, Float> defaultMap= new ArrayMap<>();
+
+
+    static {
+      wxToAndroidMap.put(WX_TRANSLATE, Arrays.asList
+              (View.TRANSLATION_X, View.TRANSLATION_Y));
+      wxToAndroidMap.put(WX_TRANSLATE_X, Collections.singletonList(View.TRANSLATION_X));
+      wxToAndroidMap.put(WX_TRANSLATE_Y, Collections.singletonList(View.TRANSLATION_Y));
+      wxToAndroidMap.put(WX_ROTATE, Collections.singletonList(View.ROTATION));
+      wxToAndroidMap.put(WX_ROTATE_X, Collections.singletonList(View.ROTATION_X));
+      wxToAndroidMap.put(WX_ROTATE_Y, Collections.singletonList(View.ROTATION_Y));
+      wxToAndroidMap.put(WX_SCALE, Arrays.asList(View.SCALE_X, View.SCALE_Y));
+      wxToAndroidMap.put(WX_SCALE_X, Collections.singletonList(View.SCALE_X));
+      wxToAndroidMap.put(WX_SCALE_Y, Collections.singletonList(View.SCALE_Y));
+      wxToAndroidMap.put(Name.PERSPECTIVE, Collections.singletonList(CameraDistanceProperty.getInstance()));
+      wxToAndroidMap = Collections.unmodifiableMap(wxToAndroidMap);
+      defaultMap.put(View.TRANSLATION_X, 0f);
+      defaultMap.put(View.TRANSLATION_Y, 0f);
+      defaultMap.put(View.SCALE_X, 1f);
+      defaultMap.put(View.SCALE_Y, 1f);
+      defaultMap.put(View.ROTATION, 0f);
+      defaultMap.put(View.ROTATION_X, 0f);
+      defaultMap.put(View.ROTATION_Y, 0f);
+    }
+
+    public String opacity;
+    public String backgroundColor;
+    public String width;
+    public String height;
+    public String transform;
+    public String transformOrigin;
+    private Map<Property<View, Float>, Float> transformMap = new LinkedHashMap<>();
+    private Pair<Float, Float> pivot;
+    private List<PropertyValuesHolder> holders=new LinkedList<>();
+    private float cameraDistance = Float.MAX_VALUE;
+
+
+    private static Pair<Float, Float> parsePivot(@Nullable String transformOrigin,
+                                                 int width, int height,int viewportW) {
+      if (!TextUtils.isEmpty(transformOrigin)) {
+        int firstSpace = transformOrigin.indexOf(FunctionParser.SPACE);
+        if (firstSpace != -1) {
+          int i = firstSpace;
+          for (; i < transformOrigin.length(); i++) {
+            if (transformOrigin.charAt(i) != FunctionParser.SPACE) {
+              break;
+            }
+          }
+          if (i < transformOrigin.length() && transformOrigin.charAt(i) != FunctionParser.SPACE) {
+            List<String> list = new ArrayList<>(2);
+            list.add(transformOrigin.substring(0, firstSpace).trim());
+            list.add(transformOrigin.substring(i, transformOrigin.length()).trim());
+            return parsePivot(list, width, height,viewportW);
+          }
+        }
+      }
+      return null;
+    }
+
+    private static Pair<Float, Float> parsePivot(@NonNull List<String> list, int width, int height,int viewportW) {
+      return new Pair<>(
+              parsePivotX(list.get(0), width,viewportW), parsePivotY(list.get(1), height,viewportW));
+    }
+
+    private static float parsePivotX(String x, int width,int viewportW) {
+      String value = x;
+      if (WXAnimationBean.Style.LEFT.equals(x)) {
+        value = ZERO;
+      } else if (WXAnimationBean.Style.RIGHT.equals(x)) {
+        value = FULL;
+      } else if (WXAnimationBean.Style.CENTER.equals(x)) {
+        value = HALF;
+      }
+      return parsePercentOrPx(value, width,viewportW);
+    }
+
+    private static float parsePivotY(String y, int height,int viewportW) {
+      String value = y;
+      if (WXAnimationBean.Style.TOP.equals(y)) {
+        value = ZERO;
+      } else if (WXAnimationBean.Style.BOTTOM.equals(y)) {
+        value = FULL;
+      } else if (WXAnimationBean.Style.CENTER.equals(y)) {
+        value = HALF;
+      }
+      return parsePercentOrPx(value, height,viewportW);
+    }
+
+    private static float parsePercentOrPx(String raw, int unit,int viewportW) {
+      final int precision = 1;
+      int suffix;
+      if ((suffix = raw.lastIndexOf(WXUtils.PERCENT)) != -1) {
+        return parsePercent(raw.substring(0, suffix), unit, precision);
+      } else if ((suffix = raw.lastIndexOf(PX)) != -1) {
+        return WXViewUtils.getRealPxByWidth(WXUtils.fastGetFloat(raw.substring(0, suffix), precision),viewportW);
+      }
+      return WXViewUtils.getRealPxByWidth(WXUtils.fastGetFloat(raw, precision),viewportW);
+    }
+
+    private static float parsePercent(String percent, int unit, int precision) {
+      return WXUtils.fastGetFloat(percent, precision) / 100 * unit;
+    }
+
+    private void resetToDefaultIfAbsent() {
+      for (Entry<Property<View, Float>, Float> entry : defaultMap.entrySet()) {
+        if (!transformMap.containsKey(entry.getKey())) {
+          transformMap.put(entry.getKey(), entry.getValue());
+        }
+      }
+    }
+
+    public @Nullable Pair<Float, Float> getPivot() {
+      return pivot;
+    }
+
+    public void init(@Nullable String transformOrigin,@Nullable String rawTransform,
+                     final int width, final int height,int viewportW, WXSDKInstance instance){
+      pivot = parsePivot(transformOrigin,width,height,viewportW);
+      transformMap.putAll(TransformParser.parseTransForm(instance.getInstanceId(), rawTransform, width,height,viewportW));
+      resetToDefaultIfAbsent();
+      if (transformMap.containsKey(CameraDistanceProperty.getInstance())) {
+        cameraDistance = transformMap.remove(CameraDistanceProperty.getInstance());
+      }
+      initHolders();
+    }
+
+    /**
+     * Use this method to init if you already have a list of Property
+     * The key is something like {@link View#TRANSLATION_X} and the value is a {@link Pair},
+     * of which the first is beginning value and the second is ending value.
+     * @param styles a list of Property
+     */
+    public void init(@NonNull Map<Property<View, Float>, Pair<Float, Float>> styles){
+      for(Entry<Property<View, Float>, Pair<Float, Float>> entry:styles.entrySet()){
+        holders.add(PropertyValuesHolder.ofFloat(entry.getKey(), entry.getValue().first, entry.getValue().second));
+      }
+    }
+
+    private void initHolders(){
+      for (Map.Entry<Property<View, Float>, Float> entry : transformMap.entrySet()) {
+        holders.add(PropertyValuesHolder.ofFloat(entry.getKey(), entry.getValue()));
+      }
+      if (!TextUtils.isEmpty(opacity)) {
+        holders.add(PropertyValuesHolder.ofFloat(View.ALPHA, WXUtils.fastGetFloat(opacity, 3)));
+      }
+    }
+
+    public List<PropertyValuesHolder> getHolders(){
+      return holders;
+    }
+
+    public float getCameraDistance(){
+      return cameraDistance;
+    }
+  }
+}
+
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/animation/WXAnimationModule.java b/android/sdk/src/main/java/org/apache/weex/ui/animation/WXAnimationModule.java
new file mode 100644
index 0000000..6874630
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/animation/WXAnimationModule.java
@@ -0,0 +1,65 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.animation;
+
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.ui.action.GraphicActionAnimation;
+import org.apache.weex.ui.component.WXComponent;
+
+public class WXAnimationModule extends WXModule {
+
+  @JSMethod
+  public void transition(@Nullable String ref, @Nullable String animation, @Nullable String callBack) {
+    if (!TextUtils.isEmpty(ref) && !TextUtils.isEmpty(animation) && mWXSDKInstance != null) {
+      //Due to animation module rely on the result of the css-layout and the batch mechanism of
+      //css-layout, the animation.transition must be delayed the batch time.
+      GraphicActionAnimation action = new GraphicActionAnimation(mWXSDKInstance, ref, animation, callBack);
+      WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+    }
+  }
+
+
+ 
+
+  //add by moxun on 12/26/2016
+  public static class AnimationHolder {
+
+    private WXAnimationBean wxAnimationBean;
+    private String callback;
+
+    public void execute(WXSDKInstance instance, WXComponent component) {
+      if (null != instance && null != component) {
+        GraphicActionAnimation action = new GraphicActionAnimation(instance, component.getRef(), wxAnimationBean, callback);
+        WXSDKManager.getInstance().getWXRenderManager().postGraphicAction(action.getPageId(), action);
+      }
+    }
+
+    public AnimationHolder(WXAnimationBean wxAnimationBean, String callback) {
+      this.wxAnimationBean = wxAnimationBean;
+      this.callback = callback;
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/animation/WidthProperty.java b/android/sdk/src/main/java/org/apache/weex/ui/animation/WidthProperty.java
new file mode 100644
index 0000000..1e9bf82
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/animation/WidthProperty.java
@@ -0,0 +1,35 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.animation;
+
+
+import android.view.ViewGroup.LayoutParams;
+
+public class WidthProperty extends LayoutParamsProperty {
+
+  @Override
+  protected Integer getProperty(LayoutParams layoutParams) {
+    return layoutParams.width;
+  }
+
+  @Override
+  protected void setProperty(LayoutParams layoutParams, Integer expected) {
+    layoutParams.width = expected;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/AbstractEditComponent.java b/android/sdk/src/main/java/org/apache/weex/ui/component/AbstractEditComponent.java
new file mode 100644
index 0000000..3111b4f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/AbstractEditComponent.java
@@ -0,0 +1,1064 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.app.Activity;
+import android.content.Context;
+import android.graphics.Rect;
+import android.support.annotation.NonNull;
+import android.text.Editable;
+import android.text.InputFilter;
+import android.text.InputType;
+import android.text.TextPaint;
+import android.text.TextUtils;
+import android.text.TextWatcher;
+import android.text.method.PasswordTransformationMethod;
+import android.util.Log;
+import android.util.TypedValue;
+import android.view.Gravity;
+import android.view.KeyEvent;
+import android.view.View;
+import android.view.inputmethod.EditorInfo;
+import android.view.inputmethod.InputMethodManager;
+import android.widget.EditText;
+import android.widget.TextView;
+
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.dom.CSSConstants;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.layout.ContentBoxMeasurement;
+import org.apache.weex.layout.MeasureMode;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.helper.SoftKeyboardDetector;
+import org.apache.weex.ui.component.helper.WXTimeInputHelper;
+import org.apache.weex.ui.view.WXEditText;
+import org.apache.weex.utils.TypefaceUtil;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.regex.Pattern;
+import java.util.regex.PatternSyntaxException;
+
+import static org.apache.weex.dom.WXStyle.UNSET;
+
+/**
+ * Created by sospartan on 7/11/16.
+ */
+public abstract class AbstractEditComponent extends WXComponent<WXEditText> {
+
+  private final InputMethodManager mInputMethodManager;
+  private String mBeforeText = "";
+  private boolean mAutoFocus;
+  private String mType = "text";
+  private String mMax = null;
+  private String mMin = null;
+  private String mLastValue = "";
+  private int mEditorAction = EditorInfo.IME_ACTION_DONE;
+  private String mReturnKeyType = null;
+  private List<TextView.OnEditorActionListener> mEditorActionListeners;
+  private boolean mListeningKeyboard = false;
+  private SoftKeyboardDetector.Unregister mUnregister;
+  private boolean mIgnoreNextOnInputEvent = false;
+  private boolean mKeepSelectionIndex = false;
+  private TextFormatter mFormatter = null;
+  private List<TextWatcher> mTextChangedListeners;
+  private TextWatcher mTextChangedEventDispatcher;
+  private int mFormatRepeatCount = 0;
+  private static final int MAX_TEXT_FORMAT_REPEAT = 3;
+
+  private TextPaint mPaint = new TextPaint();
+  private int mLineHeight = UNSET;
+
+  public AbstractEditComponent(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+    super(instance, parent, isLazy, basicComponentData);
+    mInputMethodManager = (InputMethodManager) getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
+    setContentBoxMeasurement(new ContentBoxMeasurement() {
+      /** uiThread = false **/
+      @Override
+      public void measureInternal(float width, float height, int widthMeasureMode, int heightMeasureMode) {
+        if (CSSConstants.isUndefined(width) || widthMeasureMode == MeasureMode.UNSPECIFIED) {
+          width = 0;
+        }
+        mMeasureWidth = width;
+        mMeasureHeight = getMeasureHeight();
+      }
+
+      /** uiThread = false **/
+      @Override
+      public void layoutBefore() {
+        updateStyleAndAttrs();
+      }
+
+      /** uiThread = false **/
+      @Override
+      public void layoutAfter(float computedWidth, float computedHeight) {
+
+      }
+    });
+  }
+
+  @Override
+  protected void layoutDirectionDidChanged(boolean isRTL) {
+    String alignStr = (String) getStyles().get(Constants.Name.TEXT_ALIGN);
+    int textAlign = getTextAlign(alignStr);
+    if (textAlign <= 0) {
+      textAlign = Gravity.START;
+    }
+    if (getHostView() instanceof WXEditText) {
+      getHostView().setGravity(textAlign | getVerticalGravity());
+    }
+  }
+
+  protected final float getMeasuredLineHeight() {
+    return mLineHeight != UNSET && mLineHeight > 0 ? mLineHeight : mPaint.getFontMetrics(null);
+  }
+
+  protected float getMeasureHeight() {
+    return getMeasuredLineHeight();
+  }
+
+  protected void updateStyleAndAttrs() {
+    if (getStyles().size() > 0) {
+      int fontSize = UNSET, fontStyle = UNSET, fontWeight = UNSET;
+      String fontFamily = null;
+      if (getStyles().containsKey(Constants.Name.FONT_SIZE)) {
+        fontSize = WXStyle.getFontSize(getStyles(),getViewPortWidth());
+      }
+
+      if (getStyles().containsKey(Constants.Name.FONT_FAMILY)) {
+        fontFamily = WXStyle.getFontFamily(getStyles());
+      }
+
+      if (getStyles().containsKey(Constants.Name.FONT_STYLE)) {
+        fontStyle = WXStyle.getFontStyle(getStyles());
+      }
+
+      if (getStyles().containsKey(Constants.Name.FONT_WEIGHT)) {
+        fontWeight = WXStyle.getFontWeight(getStyles());
+      }
+
+      int lineHeight = WXStyle.getLineHeight(getStyles(),getViewPortWidth());
+      if (lineHeight != UNSET)
+        mLineHeight = lineHeight;
+
+      if (fontSize != UNSET)
+        mPaint.setTextSize(fontSize);
+
+      if (fontFamily != null) {
+        TypefaceUtil.applyFontStyle(mPaint, fontStyle, fontWeight, fontFamily);
+      }
+    }
+  }
+
+  @Override
+  protected WXEditText initComponentHostView(@NonNull Context context) {
+    final WXEditText inputView = new WXEditText(context);
+    appleStyleAfterCreated(inputView);
+    return inputView;
+  }
+
+  @Override
+  protected void onHostViewInitialized(WXEditText host) {
+    super.onHostViewInitialized(host);
+    addFocusChangeListener(new OnFocusChangeListener() {
+      @Override
+      public void onFocusChange(boolean hasFocus) {
+        if (!hasFocus) {
+          decideSoftKeyboard();
+        }
+        setPseudoClassStatus(Constants.PSEUDO.FOCUS,hasFocus);
+      }
+    });
+
+    addKeyboardListener(host);
+  }
+
+  @Override
+  protected boolean isConsumeTouch() {
+    //EditText always consume touch event except disabled.
+    return !isDisabled();
+  }
+
+  private OnClickListener mOnClickListener = new OnClickListener() {
+    @Override
+    public void onHostViewClick() {
+      switch (mType) {
+        case Constants.Value.DATE:
+          hideSoftKeyboard();
+          if (getParent() != null) {
+            getParent().interceptFocus();
+          }
+          WXTimeInputHelper.pickDate(mMax, mMin, AbstractEditComponent.this);
+          break;
+        case Constants.Value.TIME:
+          hideSoftKeyboard();
+          if (getParent() != null) {
+            getParent().interceptFocus();
+          }
+          WXTimeInputHelper.pickTime(AbstractEditComponent.this);
+          break;
+      }
+    }
+  };
+
+  private void applyOnClickListener() {
+    addClickListener(mOnClickListener);
+  }
+
+
+  protected int getVerticalGravity(){
+    return Gravity.CENTER_VERTICAL;
+  }
+
+  /**
+   * Process view after created.
+   *
+   * @param editText
+   */
+  protected void appleStyleAfterCreated(final WXEditText editText) {
+    String alignStr = (String) getStyles().get(Constants.Name.TEXT_ALIGN);
+    int textAlign = getTextAlign(alignStr);
+    if (textAlign <= 0) {
+      textAlign = Gravity.START;
+    }
+    editText.setGravity(textAlign | getVerticalGravity());
+    final int colorInt = WXResourceUtils.getColor("#999999");
+    if (colorInt != Integer.MIN_VALUE) {
+      editText.setHintTextColor(colorInt);
+    }
+
+    mTextChangedEventDispatcher = new TextWatcher() {
+      @Override
+      public void beforeTextChanged(CharSequence s, int start, int count, int after) {
+        if (mTextChangedListeners != null) {
+          for (TextWatcher watcher : mTextChangedListeners) {
+            watcher.beforeTextChanged(s, start, count, after);
+          }
+        }
+      }
+
+      @Override
+      public void onTextChanged(CharSequence s, int start, int before, int count) {
+        if (mFormatter != null) {
+          String raw = mFormatter.recover(s.toString());
+          String result = mFormatter.format(raw);
+          // prevent infinite loop caused by bad format and recover regexp
+          if (!result.equals(s.toString()) && mFormatRepeatCount < MAX_TEXT_FORMAT_REPEAT) {
+            mFormatRepeatCount = mFormatRepeatCount + 1;
+            int index = editText.getSelectionStart();
+            int cursorIndex = mFormatter.format(mFormatter.recover(s.subSequence(0, index).toString())).length();
+            editText.setText(result);
+            editText.setSelection(cursorIndex);
+            return;
+          }
+
+          mFormatRepeatCount = 0;
+        }
+
+        if (mTextChangedListeners != null) {
+          for (TextWatcher watcher : mTextChangedListeners) {
+            watcher.onTextChanged(s, start, before, count);
+          }
+        }
+      }
+
+      @Override
+      public void afterTextChanged(Editable s) {
+        if (mTextChangedListeners != null) {
+          for (TextWatcher watcher : mTextChangedListeners) {
+            watcher.afterTextChanged(s);
+          }
+        }
+      }
+    };
+    editText.addTextChangedListener(mTextChangedEventDispatcher);
+
+    editText.setTextSize(TypedValue.COMPLEX_UNIT_PX, WXStyle.getFontSize(getStyles(), getInstance().getInstanceViewPortWidth()));
+  }
+
+
+  @Override
+  public void addEvent(final String type) {
+    super.addEvent(type);
+    if (getHostView() == null || TextUtils.isEmpty(type)) {
+      return;
+    }
+    final TextView text = getHostView();
+
+    if (type.equals(Constants.Event.CHANGE)) {
+      addFocusChangeListener(new OnFocusChangeListener() {
+        @Override
+        public void onFocusChange(boolean hasFocus) {
+          if (hasFocus) {
+            mLastValue = text.getText().toString();
+          } else {
+            CharSequence newValue = text.getText();
+            newValue = newValue == null ? "" : newValue;
+            if (!newValue.toString().equals(mLastValue)) {
+              fireEvent(Constants.Event.CHANGE, newValue.toString());
+              mLastValue = text.getText().toString();
+            }
+          }
+        }
+      });
+
+      addEditorActionListener(new TextView.OnEditorActionListener() {
+        @Override
+        public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
+          if (actionId == mEditorAction) {
+            CharSequence newValue = text.getText();
+            newValue = newValue == null ? "" : newValue;
+            if (!newValue.toString().equals(mLastValue)) {
+              fireEvent(Constants.Event.CHANGE, newValue.toString());
+              mLastValue = text.getText().toString();
+            }
+            if (getParent() != null) {
+              getParent().interceptFocus();
+            }
+            hideSoftKeyboard();
+            return true;
+          }
+          return false;
+        }
+      });
+    } else if (type.equals(Constants.Event.INPUT)) {
+      addTextChangedListener(new TextWatcher() {
+        @Override
+        public void beforeTextChanged(CharSequence s, int start, int count, int after) {
+
+        }
+
+        @Override
+        public void onTextChanged(CharSequence s, int start, int before, int count) {
+          if (mIgnoreNextOnInputEvent) {
+            mIgnoreNextOnInputEvent = false;
+            mBeforeText = s.toString();
+            return;
+          }
+
+          if (mBeforeText.equals(s.toString())) {
+            return;
+          }
+
+          mBeforeText = s.toString();
+
+          fireEvent(Constants.Event.INPUT, s.toString());
+        }
+
+        @Override
+        public void afterTextChanged(Editable s) {
+
+        }
+      });
+    }
+
+    if (Constants.Event.RETURN.equals(type)) {
+      addEditorActionListener(new TextView.OnEditorActionListener() {
+        @Override
+        public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
+          if (actionId == mEditorAction) {
+            Map<String, Object> ret = new HashMap<>(2);
+            ret.put("returnKeyType", mReturnKeyType);
+            ret.put("value", v.getText().toString());
+            fireEvent(Constants.Event.RETURN, ret);
+            return true;
+          }
+          return false;
+        }
+      });
+    }
+
+    if (Constants.Event.KEYBOARD.equals(type)) {
+      mListeningKeyboard = true;
+    }
+  }
+
+  private void fireEvent(String event, String value) {
+    if (event != null) {
+      Map<String, Object> params = new HashMap<>(2);
+      params.put("value", value);
+      params.put("timeStamp", System.currentTimeMillis());
+
+      Map<String, Object> domChanges = new HashMap<>();
+      Map<String, Object> attrsChanges = new HashMap<>();
+      attrsChanges.put("value", value);
+      domChanges.put("attrs", attrsChanges);
+
+      WXSDKManager.getInstance().fireEvent(getInstanceId(), getRef(), event, params, domChanges);
+    }
+  }
+
+  public void performOnChange(String value) {
+    if (getEvents() != null) {
+      String event = getEvents().contains(Constants.Event.CHANGE) ? Constants.Event.CHANGE : null;
+      fireEvent(event, value);
+    }
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.DISABLED:
+        Boolean disabled = WXUtils.getBoolean(param, null);
+        if (disabled != null && mHost != null) {
+          if (disabled) {
+            mHost.setFocusable(false);
+            mHost.setFocusableInTouchMode(false);
+          } else {
+            mHost.setFocusableInTouchMode(true);
+            mHost.setFocusable(true);
+          }
+        }
+        return true;
+      case Constants.Name.PLACEHOLDER:
+        String placeholder = WXUtils.getString(param, null);
+        if (placeholder != null)
+          setPlaceholder(placeholder);
+        return true;
+      case Constants.Name.PLACEHOLDER_COLOR:
+        String placeholder_color = WXUtils.getString(param, null);
+        if (placeholder_color != null)
+          setPlaceholderColor(placeholder_color);
+        return true;
+      case Constants.Name.TYPE:
+        String input_type = WXUtils.getString(param, null);
+        if (input_type != null)
+          setType(input_type);
+        return true;
+      case Constants.Name.AUTOFOCUS:
+        Boolean result = WXUtils.getBoolean(param, null);
+        if (result != null)
+          setAutofocus(result);
+        return true;
+      case Constants.Name.COLOR:
+        String color = WXUtils.getString(param, null);
+        if (color != null)
+          setColor(color);
+        return true;
+      case Constants.Name.FONT_SIZE:
+        String fontsize = WXUtils.getString(param, null);
+        if (fontsize != null)
+          setFontSize(fontsize);
+        return true;
+      case Constants.Name.TEXT_ALIGN:
+        String text_align = WXUtils.getString(param, null);
+        if (text_align != null)
+          setTextAlign(text_align);
+        return true;
+      case Constants.Name.SINGLELINE:
+        Boolean singLineResult = WXUtils.getBoolean(param, null);
+        if (singLineResult != null)
+          setSingleLine(singLineResult);
+        return true;
+      case Constants.Name.LINES:
+        Integer lines = WXUtils.getInteger(param, null);
+        if (lines != null)
+          setLines(lines);
+        return true;
+      case Constants.Name.MAX_LENGTH:
+        Integer maxlength = WXUtils.getInteger(param, null);
+        if (maxlength != null)
+          setMaxLength(maxlength);
+        return true;
+      case Constants.Name.MAXLENGTH:
+        Integer maxLength = WXUtils.getInteger(param, null);
+        if (maxLength != null)
+          setMaxLength(maxLength);
+        return true;
+      case Constants.Name.MAX:
+        setMax(String.valueOf(param));
+        return true;
+      case Constants.Name.MIN:
+        setMin(String.valueOf(param));
+        return true;
+      case Constants.Name.RETURN_KEY_TYPE:
+        setReturnKeyType(String.valueOf(param));
+        return true;
+      case Constants.Name.KEEP_SELECTION_INDEX:
+        boolean keepIndex = WXUtils.getBoolean(param, false);
+        mKeepSelectionIndex = keepIndex;
+        return true;
+      case Constants.Name.ALLOW_COPY_PASTE:
+        boolean allowCopyPaste = WXUtils.getBoolean(param, true);
+        if (getHostView() != null) {
+          getHostView().setAllowCopyPaste(allowCopyPaste);
+        }
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @WXComponentProp(name = Constants.Name.RETURN_KEY_TYPE)
+  public void setReturnKeyType(String type) {
+    if (getHostView() == null) {
+      return;
+    }
+    mReturnKeyType = type;
+    switch (type) {
+      case ReturnTypes.DEFAULT:
+        mEditorAction = EditorInfo.IME_ACTION_UNSPECIFIED;
+        break;
+      case ReturnTypes.GO:
+        mEditorAction = EditorInfo.IME_ACTION_GO;
+        break;
+      case ReturnTypes.NEXT:
+        mEditorAction = EditorInfo.IME_ACTION_NEXT;
+        break;
+      case ReturnTypes.SEARCH:
+        mEditorAction = EditorInfo.IME_ACTION_SEARCH;
+        break;
+      case ReturnTypes.SEND:
+        mEditorAction = EditorInfo.IME_ACTION_SEND;
+        break;
+      case ReturnTypes.DONE:
+        mEditorAction = EditorInfo.IME_ACTION_DONE;
+        break;
+      default:
+        break;
+    }
+
+    //remove focus and hide keyboard first, the ImeOptions will take effect when show keyboard next time
+    blur();
+    getHostView().setImeOptions(mEditorAction);
+  }
+
+  @WXComponentProp(name = Constants.Name.PLACEHOLDER)
+  public void setPlaceholder(String placeholder) {
+    if (placeholder == null || getHostView() == null) {
+      return;
+    }
+    ((WXEditText) getHostView()).setHint(placeholder);
+  }
+
+  @WXComponentProp(name = Constants.Name.PLACEHOLDER_COLOR)
+  public void setPlaceholderColor(String color) {
+    if (getHostView() != null && !TextUtils.isEmpty(color)) {
+      int colorInt = WXResourceUtils.getColor(color);
+      if (colorInt != Integer.MIN_VALUE) {
+        ((WXEditText) getHostView()).setHintTextColor(colorInt);
+      }
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.TYPE)
+  public void setType(String type) {
+    Log.e("weex", "setType=" + type);
+    if (type == null || getHostView() == null) {
+      return;
+    }
+    mType = type;
+    ((EditText) getHostView()).setInputType(getInputType(mType));
+    switch (mType) {
+      case Constants.Value.DATE:
+      case Constants.Value.TIME:
+        applyOnClickListener();
+        break;
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.AUTOFOCUS)
+  public void setAutofocus(boolean autofocus) {
+    if (getHostView() == null) {
+      return;
+    }
+    mAutoFocus = autofocus;
+    EditText inputView = getHostView();
+    if (mAutoFocus) {
+      inputView.setFocusable(true);
+      inputView.requestFocus();
+      inputView.setFocusableInTouchMode(true);
+      showSoftKeyboard();
+    } else {
+      hideSoftKeyboard();
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.VALUE)
+  public void setValue(String value) {
+    WXEditText view;
+    if ((view = getHostView()) == null) {
+      return;
+    }
+    if (TextUtils.equals(view.getText(), value)) {
+      return;
+    }
+
+    mIgnoreNextOnInputEvent = true;
+    int oldIndex = view.getSelectionStart();
+    view.setText(value);
+    int index = mKeepSelectionIndex ? oldIndex : value.length();
+    view.setSelection(value == null ? 0 : index);
+  }
+
+  @WXComponentProp(name = Constants.Name.COLOR)
+  public void setColor(String color) {
+    if (getHostView() != null && !TextUtils.isEmpty(color)) {
+      int colorInt = WXResourceUtils.getColor(color);
+      if (colorInt != Integer.MIN_VALUE) {
+        getHostView().setTextColor(colorInt);
+      }
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.FONT_SIZE)
+  public void setFontSize(String fontSize) {
+    if (getHostView() != null && fontSize != null ) {
+      Map<String, Object> map = new HashMap<>(1);
+      map.put(Constants.Name.FONT_SIZE, fontSize);
+      getHostView().setTextSize(TypedValue.COMPLEX_UNIT_PX, WXStyle.getFontSize(map, getInstance().getInstanceViewPortWidth()));
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.TEXT_ALIGN)
+  public void setTextAlign(String textAlign) {
+    int align = getTextAlign(textAlign);
+    if (align > 0) {
+      getHostView().setGravity(align | getVerticalGravity());
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.SINGLELINE)
+  public void setSingleLine(boolean singleLine) {
+    if (getHostView() == null) {
+      return;
+    }
+    getHostView().setSingleLine(singleLine);
+  }
+
+  @WXComponentProp(name = Constants.Name.LINES)
+  public void setLines(int lines) {
+    if (getHostView() == null) {
+      return;
+    }
+    getHostView().setLines(lines);
+  }
+
+  /**
+   * Compatible with both 'max-length' and 'maxlength'
+   * @param maxLength
+   */
+  @WXComponentProp(name = Constants.Name.MAX_LENGTH)
+  public void setMaxLength(int maxLength) {
+    if (getHostView() == null) {
+      return;
+    }
+    getHostView().setFilters(new InputFilter[]{new InputFilter.LengthFilter(maxLength)});
+  }
+
+  /**
+   * Compatible with both 'max-length' and 'maxlength'
+   * @param maxLength
+   */
+  @WXComponentProp(name = Constants.Name.MAXLENGTH)
+  @Deprecated
+  public void setMaxlength(int maxLength) {
+    setMaxLength(maxLength);
+  }
+
+  private int getInputType(String type) {
+    int inputType;
+    switch (type) {
+      case Constants.Value.TEXT:
+        inputType = InputType.TYPE_CLASS_TEXT;
+        break;
+      case Constants.Value.DATE:
+        inputType = InputType.TYPE_NULL;
+        getHostView().setFocusable(false);
+        break;
+      case Constants.Value.DATETIME:
+        inputType = InputType.TYPE_CLASS_DATETIME;
+        break;
+      case Constants.Value.EMAIL:
+        inputType = InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_EMAIL_ADDRESS;
+        break;
+      case Constants.Value.PASSWORD:
+        inputType = InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_PASSWORD;
+        if(getHostView() != null){
+            getHostView().setTransformationMethod(PasswordTransformationMethod.getInstance());
+        }
+        break;
+      case Constants.Value.TEL:
+        inputType = InputType.TYPE_CLASS_PHONE;
+        break;
+      case Constants.Value.TIME:
+        inputType = InputType.TYPE_NULL;
+        if(getHostView() != null){
+            getHostView().setFocusable(false);
+        }
+        break;
+      case Constants.Value.URL:
+        inputType = InputType.TYPE_CLASS_TEXT | InputType.TYPE_TEXT_VARIATION_URI;
+        break;
+      case Constants.Value.NUMBER:
+        inputType = InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_FLAG_DECIMAL;
+        break;
+      default:
+        inputType = InputType.TYPE_CLASS_TEXT;
+    }
+    return inputType;
+  }
+
+  @WXComponentProp(name = Constants.Name.MAX)
+  public void setMax(String max) {
+    mMax = max;
+  }
+
+  @WXComponentProp(name = Constants.Name.MIN)
+  public void setMin(String min) {
+    mMin = min;
+  }
+
+  private boolean showSoftKeyboard() {
+    if (getHostView() == null) {
+      return false;
+    } else {
+      getHostView().postDelayed(WXThread.secure(new Runnable() {
+        @Override
+        public void run() {
+          if (getInstance() != null && getInstance().getApmForInstance() != null){
+            getInstance().getApmForInstance().forceStopRecordInteraction = true;
+          }
+          mInputMethodManager.showSoftInput(getHostView(), InputMethodManager.SHOW_IMPLICIT);
+        }
+      }), 100);
+    }
+    return true;
+  }
+
+  private void hideSoftKeyboard() {
+    if (getHostView() != null) {
+      getHostView().postDelayed(WXThread.secure(new Runnable() {
+        @Override
+        public void run() {
+          mInputMethodManager.hideSoftInputFromWindow(getHostView().getWindowToken(), 0);
+        }
+      }), 16);
+    }
+  }
+
+  private int getTextAlign(String textAlign) {
+    boolean isRTL = isLayoutRTL();
+    int align = isRTL ? Gravity.END : Gravity.START;
+    if (TextUtils.isEmpty(textAlign)) {
+      return align;
+    }
+
+    if (textAlign.equals(Constants.Value.LEFT)) {
+      align = Gravity.START;
+    } else if (textAlign.equals(Constants.Value.CENTER)) {
+      align = Gravity.CENTER;
+    } else if (textAlign.equals(Constants.Value.RIGHT)) {
+      align = Gravity.END;
+    }
+    return align;
+  }
+
+  @JSMethod
+  public void blur() {
+    WXEditText host = getHostView();
+    if (host != null && host.hasFocus()) {
+      if (getParent() != null) {
+        getParent().interceptFocus();
+      }
+      host.clearFocus();
+      hideSoftKeyboard();
+    }
+  }
+
+  @JSMethod
+  public void focus() {
+    WXEditText host = getHostView();
+    if (host != null && !host.hasFocus()) {
+      if (getParent() != null) {
+        getParent().ignoreFocus();
+      }
+      host.requestFocus();
+      host.setFocusable(true);
+      host.setFocusableInTouchMode(true);
+      showSoftKeyboard();
+    }
+  }
+
+  @Override
+  protected Object convertEmptyProperty(String propName, Object originalValue) {
+    switch (propName) {
+      case Constants.Name.FONT_SIZE:
+        return WXText.sDEFAULT_SIZE;
+      case Constants.Name.COLOR:
+        return "black";
+    }
+    return super.convertEmptyProperty(propName, originalValue);
+  }
+
+  private void decideSoftKeyboard() {
+    View hostView;
+    if ((hostView = getHostView()) != null) {
+      final Context context = getContext();
+      if (context != null && context instanceof Activity) {
+        hostView.postDelayed(WXThread.secure(new Runnable() {
+          @Override
+          public void run() {
+            View currentFocus = ((Activity) context).getCurrentFocus();
+            if (!(currentFocus instanceof EditText)) {
+              mInputMethodManager.hideSoftInputFromWindow(getHostView().getWindowToken(), 0);
+            }
+          }
+        }), 16);
+      }
+    }
+  }
+
+  @JSMethod
+  public void setSelectionRange(int selectionStart, int selectionEnd) {
+    EditText hostView;
+    if ((hostView = getHostView()) != null) {
+      int length = getHostView().length();
+      if (selectionStart > length || selectionEnd > length) {
+        return;
+      }
+      focus();
+      hostView.setSelection(selectionStart, selectionEnd);
+    }
+  }
+
+  @JSMethod
+  public void getSelectionRange(String callbackId) {
+    EditText hostView;
+    Map<String, Object> result = new HashMap<>(2);
+    if ((hostView = getHostView()) != null) {
+      int start = hostView.getSelectionStart();
+      int end = hostView.getSelectionEnd();
+
+      if (!hostView.hasFocus()) {
+        //The default behavior, same as iOS and web
+        start = 0;
+        end = 0;
+      }
+
+      result.put(Constants.Name.SELECTION_START, start);
+      result.put(Constants.Name.SELECTION_END, end);
+    }
+    WXBridgeManager.getInstance().callback(getInstanceId(), callbackId, result, false);
+  }
+
+  @JSMethod
+  public void setTextFormatter(JSONObject params) {
+    try {
+      String formatRule = params.getString("formatRule");
+      String formatReplace = params.getString("formatReplace");
+      String recoverRule = params.getString("recoverRule");
+      String recoverReplace = params.getString("recoverReplace");
+
+      PatternWrapper format = parseToPattern(formatRule, formatReplace);
+      PatternWrapper recover = parseToPattern(recoverRule, recoverReplace);
+
+      if (format != null && recover != null) {
+        mFormatter = new TextFormatter(format, recover);
+      }
+    } catch (Throwable t) {
+      t.printStackTrace();
+    }
+  }
+
+  protected final void addEditorActionListener(TextView.OnEditorActionListener listener) {
+    TextView view;
+    if (listener != null && (view = getHostView()) != null) {
+      if (mEditorActionListeners == null) {
+        mEditorActionListeners = new ArrayList<>();
+        view.setOnEditorActionListener(new TextView.OnEditorActionListener() {
+          private boolean handled = true;
+
+          @Override
+          public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
+            for (TextView.OnEditorActionListener l : mEditorActionListeners) {
+              if (l != null) {
+                handled = handled & l.onEditorAction(v, actionId, event);
+              }
+            }
+            return handled;
+          }
+        });
+      }
+      mEditorActionListeners.add(listener);
+    }
+  }
+
+  public final void addTextChangedListener(TextWatcher watcher) {
+    if (mTextChangedListeners == null) {
+      mTextChangedListeners = new ArrayList<>();
+    }
+    mTextChangedListeners.add(watcher);
+  }
+
+  private void addKeyboardListener(final WXEditText host) {
+    if (host == null) {
+      return;
+    }
+    final Context context = host.getContext();
+    if (context != null && context instanceof Activity) {
+      SoftKeyboardDetector.registerKeyboardEventListener((Activity) context, new SoftKeyboardDetector.OnKeyboardEventListener() {
+        @Override
+        public void onKeyboardEvent(boolean isShown) {
+          if (mListeningKeyboard) {
+            Map<String, Object> event = new HashMap<>(1);
+            event.put("isShow", isShown);
+            if (isShown) {
+              Rect r = new Rect();
+              ((Activity) context).getWindow().getDecorView().getWindowVisibleDisplayFrame(r);
+              float keyboardSize = WXViewUtils.getWebPxByWidth(WXViewUtils.getScreenHeight(context) - (r.bottom - r.top),
+                      getInstance().getInstanceViewPortWidth());
+              event.put("keyboardSize", keyboardSize);
+            }
+            fireEvent(Constants.Event.KEYBOARD, event);
+          }
+          if (!isShown) {
+            blur();
+          }
+        }
+      });
+    }
+  }
+
+  @Override
+  public void destroy() {
+    super.destroy();
+    if (mUnregister != null) {
+      try {
+        mUnregister.execute();
+        mUnregister = null;
+      } catch (Throwable throwable) {
+        WXLogUtils.w("Unregister throw ", throwable);
+      }
+    }
+  }
+
+  private PatternWrapper parseToPattern(String jsPattern, String replace) {
+    if (jsPattern == null || replace == null) {
+      return null;
+    }
+
+    String checker = "/[\\S]+/[i]?[m]?[g]?";
+    if (!Pattern.compile(checker).matcher(jsPattern).matches()) {
+      WXLogUtils.w("WXInput", "Illegal js pattern syntax: " + jsPattern);
+      return null;
+    }
+
+    int flags = 0;
+    boolean global = false;
+    String flagsStr = jsPattern.substring(jsPattern.lastIndexOf("/") + 1);
+    String regExp = jsPattern.substring(jsPattern.indexOf("/") + 1, jsPattern.lastIndexOf("/"));
+
+    if (flagsStr.contains("i")) {
+      flags |= Pattern.CASE_INSENSITIVE;
+    }
+
+    if (flagsStr.contains("m")) {
+      flags |= Pattern.DOTALL;
+    }
+
+    if (flagsStr.contains("g")) {
+      global = true;
+    }
+
+    Pattern pattern = null;
+    try {
+      pattern = Pattern.compile(regExp, flags);
+    } catch (PatternSyntaxException e) {
+      WXLogUtils.w("WXInput", "Pattern syntax error: " + regExp);
+    }
+    if (pattern == null) {
+      return null;
+    }
+
+    PatternWrapper wrapper = new PatternWrapper();
+    wrapper.global = global;
+    wrapper.matcher = pattern;
+    wrapper.replace = replace;
+    return wrapper;
+  }
+
+  private interface ReturnTypes {
+    String DEFAULT = "default";
+    String GO = "go";
+    String NEXT = "next";
+    String SEARCH = "search";
+    String SEND = "send";
+    String DONE = "done";
+  }
+
+  private static class PatternWrapper {
+    private boolean global = false;
+    private Pattern matcher;
+    private String replace;
+  }
+
+  private static class TextFormatter {
+    private PatternWrapper format;
+    private PatternWrapper recover;
+
+    private TextFormatter(PatternWrapper format, PatternWrapper recover) {
+      this.format = format;
+      this.recover = recover;
+    }
+
+    private String format(String src) {
+      try {
+        if (format != null) {
+          if (format.global) {
+            return format.matcher.matcher(src).replaceAll(format.replace);
+          } else {
+            return format.matcher.matcher(src).replaceFirst(format.replace);
+          }
+        }
+      } catch (Throwable t) {
+        //maybe IndexOutOfBoundsException caused by illegal replace
+        WXLogUtils.w("WXInput", "[format] " + t.getMessage());
+      }
+      return src;
+    }
+
+    private String recover(String formatted) {
+      try {
+        if (recover != null) {
+          if (recover.global) {
+            return recover.matcher.matcher(formatted).replaceAll(recover.replace);
+          } else {
+            return recover.matcher.matcher(formatted).replaceFirst(recover.replace);
+          }
+        }
+      } catch (Throwable t) {
+        //same cause as format
+        WXLogUtils.w("WXInput", "[formatted] " + t.getMessage());
+      }
+      return formatted;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/AppearanceHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/AppearanceHelper.java
new file mode 100644
index 0000000..1668171
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/AppearanceHelper.java
@@ -0,0 +1,120 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.graphics.Rect;
+import android.view.View;
+
+
+/**
+ * Created by sospartan on 8/19/16.
+ */
+public class AppearanceHelper {
+
+  private final WXComponent mAwareChild;
+
+  private boolean mAppearStatus = false;
+  private boolean[] mWatchFlags = {false, false};
+
+  public static final int APPEAR = 0;
+  public static final int DISAPPEAR = 1;
+
+  public static final int RESULT_APPEAR = 1;
+  public static final int RESULT_DISAPPEAR = -1;
+  public static final int RESULT_NO_CHANGE = 0;
+
+  private Rect mVisibleRect = new Rect();
+
+  private int mCellPositionInScrollable;
+
+  /**
+   * @param awareChild child to notify when appearance changed.
+   */
+  public AppearanceHelper(WXComponent awareChild) {
+    this(awareChild, 0);
+  }
+
+  public AppearanceHelper(WXComponent awareChild, int cellPositionInScrollable) {
+    mAwareChild = awareChild;
+    mCellPositionInScrollable = cellPositionInScrollable;
+  }
+
+  public void setCellPosition(int pos){
+    mCellPositionInScrollable = pos;
+  }
+
+  public int getCellPositionINScollable() {
+    return mCellPositionInScrollable;
+  }
+
+  /**
+   * @param event  {@link #APPEAR} and {@link #DISAPPEAR}
+   * @param enable
+   */
+  public void setWatchEvent(int event, boolean enable) {
+    mWatchFlags[event] = enable;
+  }
+
+  /**
+   * @return
+   */
+  public boolean isWatch() {
+    return mWatchFlags[APPEAR] || mWatchFlags[DISAPPEAR];
+  }
+
+
+  public WXComponent getAwareChild() {
+    return mAwareChild;
+  }
+
+  public boolean isAppear() {
+    return mAppearStatus;
+  }
+
+  public int setAppearStatus(boolean newIsAppear) {
+    if (mAppearStatus != newIsAppear) {
+      mAppearStatus = newIsAppear;
+      return newIsAppear ? RESULT_APPEAR : RESULT_DISAPPEAR;
+    }
+
+    return RESULT_NO_CHANGE;
+  }
+
+  public boolean isViewVisible(boolean isList) {
+    View view = mAwareChild.getHostView();
+    if(isList){
+      if(view.getVisibility() == View.VISIBLE){
+        if(view.getMeasuredHeight()  == 0){
+          return  true;
+        }
+      }
+    }
+    return view != null && view.getLocalVisibleRect(mVisibleRect);
+
+  }
+
+  public boolean isViewVisible(View view) {
+    if(view.getVisibility() == View.VISIBLE){
+      if(view.getMeasuredHeight()  == 0){
+        return  true;
+      }
+    }
+    return view != null && view.getLocalVisibleRect(mVisibleRect);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/NestedContainer.java b/android/sdk/src/main/java/org/apache/weex/ui/component/NestedContainer.java
new file mode 100644
index 0000000..32637b7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/NestedContainer.java
@@ -0,0 +1,51 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.view.ViewGroup;
+import org.apache.weex.WXSDKInstance;
+
+/**
+ * Created by sospartan on 8/24/16.
+ */
+public interface NestedContainer {
+  void setOnNestEventListener(OnNestedInstanceEventListener listener);
+
+  ViewGroup getViewContainer();
+
+  void renderNewURL(String url);
+
+  void reload();
+
+  interface OnNestedInstanceEventListener {
+    void onException(NestedContainer comp, String errCode, String msg);
+
+    /**
+     *
+     * @param comp
+     * @param src
+     * @return true if keep load
+     */
+    boolean onPreCreate(NestedContainer comp, String src);
+
+    String transformUrl(String origin);
+
+    void onCreated(NestedContainer comp, WXSDKInstance nestedInstance);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/Scrollable.java b/android/sdk/src/main/java/org/apache/weex/ui/component/Scrollable.java
new file mode 100644
index 0000000..7a8299a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/Scrollable.java
@@ -0,0 +1,60 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.view.ViewGroup;
+
+import java.util.Map;
+import org.apache.weex.common.Constants.Orientation;
+
+/**
+ * Created by sospartan on 7/5/16.
+ */
+public interface Scrollable {
+
+  void bindStickStyle(WXComponent component);
+
+  void unbindStickStyle(WXComponent component);
+
+  void bindAppearEvent(WXComponent component);
+
+  void bindDisappearEvent(WXComponent component);
+
+  void unbindAppearEvent(WXComponent component);
+
+  void unbindDisappearEvent(WXComponent component);
+
+  ViewGroup getView();
+
+  void scrollTo(WXComponent component, Map<String, Object> options);
+
+  String getRef();
+
+  int getScrollY();
+
+  int getScrollX();
+
+  /**
+   *
+   * @return {@link Orientation#HORIZONTAL} or {@link Orientation#VERTICAL}
+   */
+  int getOrientation();
+
+  boolean isScrollable();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/Textarea.java b/android/sdk/src/main/java/org/apache/weex/ui/component/Textarea.java
new file mode 100644
index 0000000..06b0da5
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/Textarea.java
@@ -0,0 +1,120 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.text.TextUtils;
+import android.view.Gravity;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXEditText;
+import org.apache.weex.utils.WXUtils;
+
+/**
+ * Created by sospartan on 7/11/16.
+ */
+public class Textarea extends AbstractEditComponent {
+
+  public static final int DEFAULT_ROWS = 2;
+  private int mNumberOfLines = DEFAULT_ROWS;
+
+  public Textarea(
+      WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+    super(instance, parent, isLazy, basicComponentData);
+  }
+
+  @Override
+  protected void onHostViewInitialized(WXEditText host) {
+    host.setAllowDisableMovement(false);
+    super.onHostViewInitialized(host);
+  }
+
+  @Override
+  protected void appleStyleAfterCreated(WXEditText editText) {
+    super.appleStyleAfterCreated(editText);
+    String rowsStr = (String) getStyles().get(Constants.Name.ROWS);
+
+    int rows = DEFAULT_ROWS;
+    try{
+      if(!TextUtils.isEmpty(rowsStr)) {
+        rows = Integer.parseInt(rowsStr);
+      }
+    }catch (NumberFormatException e){
+      //ignore
+      e.printStackTrace();
+    }
+
+    editText.setLines(rows);
+    editText.setMinLines(rows);
+  }
+
+  @Override
+  protected int getVerticalGravity() {
+    return Gravity.TOP;
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.ROWS:
+        Integer rows = WXUtils.getInteger(param,null);
+        if (rows != null)
+          setRows(rows);
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @WXComponentProp(name = Constants.Name.ROWS)
+  public void setRows(int rows){
+    WXEditText text = getHostView();
+    if(text == null||rows <=0 ){
+      return;
+    }
+
+    text.setLines(rows);
+  }
+
+  @Override
+  protected float getMeasureHeight(){
+    return getMeasuredLineHeight() * mNumberOfLines;
+  }
+
+  @Override
+  protected void updateStyleAndAttrs() {
+    super.updateStyleAndAttrs();
+    Object raw = getAttrs().get(Constants.Name.ROWS);
+    if (raw == null) {
+      return;
+    } else if (raw instanceof String) {
+      String rowsStr = (String) raw;
+      try {
+        int lines = Integer.parseInt(rowsStr);
+        if (lines > 0) {
+          mNumberOfLines = lines;
+        }
+      } catch (NumberFormatException e) {
+        e.printStackTrace();
+      }
+    } else if (raw instanceof Integer) {
+      mNumberOfLines = (Integer) raw;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXA.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXA.java
new file mode 100644
index 0000000..f8d45bc
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXA.java
@@ -0,0 +1,64 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXFrameLayout;
+import org.apache.weex.utils.ATagUtil;
+
+@Component(lazyload = false)
+public class WXA extends WXDiv {
+
+  @Deprecated
+  public WXA(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, basicComponentData);
+  }
+
+  public WXA(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  @Override
+  protected void onHostViewInitialized(WXFrameLayout host) {
+    addClickListener(new OnClickListener() {
+      @Override
+      public void onHostViewClick() {
+        String href;
+        WXAttr attr = getAttrs();
+        if (attr !=null && (href = (String)attr.get("href")) != null) {
+          ATagUtil.onClick(null, getInstanceId(), href);
+        }
+      }
+    });
+    super.onHostViewInitialized(host);
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch(key){
+      case Constants.Name.HREF:
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXBaseRefresh.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXBaseRefresh.java
new file mode 100644
index 0000000..5ab59e6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXBaseRefresh.java
@@ -0,0 +1,65 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXFrameLayout;
+
+/**
+ * div component
+ */
+@Component(lazyload = false)
+
+public class WXBaseRefresh extends WXVContainer<WXFrameLayout> {
+
+  private WXLoadingIndicator mLoadingIndicator;
+
+  public WXBaseRefresh(
+      WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
+    super(instance, parent, lazy, basicComponentData);
+  }
+
+  @Override
+  public void addChild(WXComponent child) {
+    super.addChild(child);
+    this.checkLoadingIndicator(child);
+  }
+
+  @Override
+  protected WXFrameLayout initComponentHostView(@NonNull Context context) {
+    return new WXFrameLayout(context);
+  }
+
+  @Override
+  public void addChild(WXComponent child, int index) {
+    super.addChild(child, index);
+    this.checkLoadingIndicator(child);
+  }
+
+  private void checkLoadingIndicator(WXComponent child) {
+    if (child instanceof WXLoadingIndicator) {
+      mLoadingIndicator = (WXLoadingIndicator) child;
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXBasicComponentType.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXBasicComponentType.java
new file mode 100644
index 0000000..b6f7ccc
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXBasicComponentType.java
@@ -0,0 +1,59 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+/**
+ * basic Component types
+ */
+public class WXBasicComponentType {
+
+  public static final String TEXT = "text";
+  public static final String IMAGE = "image";
+  public static final String IMG = "img";
+  public static final String CONTAINER = "container";
+  public static final String DIV = "div";
+  public static final String SCROLLER = "scroller";
+  public static final String SLIDER = "slider";
+  public static final String SLIDER_NEIGHBOR = "slider-neighbor";
+  public static final String LIST = "list";
+  public static final String RECYCLER = "recycler";
+  public static final String WATERFALL = "waterfall";
+  public static final String VLIST = "vlist";
+  public static final String HLIST = "hlist";
+  public static final String CELL = "cell";
+  public static final String HEADER = "header";
+  public static final String FOOTER = "footer";
+  public static final String INDICATOR = "indicator";
+  public static final String VIDEO = "video";
+  public static final String INPUT = "input";
+  public static final String TEXTAREA = "textarea";
+  public static final String SWITCH = "switch";
+  public static final String A = "a";
+  public static final String EMBED = "embed";
+  public static final String WEB = "web";
+  public static final String REFRESH = "refresh";
+  public static final String LOADING = "loading";
+  public static final String LOADING_INDICATOR = "loading-indicator";
+  public static final String CYCLE_SLIDER = "cycleslider";
+  public static final String RICHTEXT = "richtext";
+
+  public static final String RECYCLE_LIST = "recycle-list";
+  public static final String CELL_SLOT = "cell-slot";
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponent.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponent.java
new file mode 100644
index 0000000..9bdee05
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponent.java
@@ -0,0 +1,2470 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.annotation.SuppressLint;
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.content.Intent;
+import android.content.res.ColorStateList;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.Path;
+import android.graphics.Point;
+import android.graphics.PointF;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.graphics.Shader;
+import android.graphics.drawable.ColorDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.LayerDrawable;
+import android.graphics.drawable.RippleDrawable;
+import android.os.Build;
+import android.support.annotation.CallSuper;
+import android.support.annotation.CheckResult;
+import android.support.annotation.IntDef;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.v4.view.AccessibilityDelegateCompat;
+import android.support.v4.view.ViewCompat;
+import android.support.v4.view.accessibility.AccessibilityNodeInfoCompat;
+import android.text.TextUtils;
+import android.util.Pair;
+import android.view.Gravity;
+import android.view.Menu;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewOverlay;
+import android.widget.FrameLayout;
+import com.alibaba.fastjson.JSONArray;
+import org.apache.weex.ComponentObserver;
+import org.apache.weex.IWXActivityStateListener;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXAccessibilityRoleAdapter;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.bridge.EventResult;
+import org.apache.weex.bridge.Invoker;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.IWXObject;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXPerformance;
+import org.apache.weex.common.WXRuntimeException;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.dom.CSSShorthand.CORNER;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.dom.transition.WXTransition;
+import org.apache.weex.layout.ContentBoxMeasurement;
+import org.apache.weex.performance.WXAnalyzerDataTransfer;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.tracing.Stopwatch;
+import org.apache.weex.tracing.WXTracing;
+import org.apache.weex.ui.IFComponentHolder;
+import org.apache.weex.ui.WXRenderManager;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.action.GraphicActionAnimation;
+import org.apache.weex.ui.action.GraphicActionUpdateStyle;
+import org.apache.weex.ui.action.GraphicPosition;
+import org.apache.weex.ui.action.GraphicSize;
+import org.apache.weex.ui.animation.WXAnimationBean;
+import org.apache.weex.ui.component.basic.WXBasicComponent;
+import org.apache.weex.ui.component.binding.Statements;
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
+import org.apache.weex.ui.component.pesudo.OnActivePseudoListner;
+import org.apache.weex.ui.component.pesudo.PesudoStatus;
+import org.apache.weex.ui.component.pesudo.TouchActivePseudoListener;
+import org.apache.weex.ui.flat.FlatComponent;
+import org.apache.weex.ui.flat.FlatGUIContext;
+import org.apache.weex.ui.flat.WidgetContainer;
+import org.apache.weex.ui.flat.widget.AndroidViewWidget;
+import org.apache.weex.ui.flat.widget.Widget;
+import org.apache.weex.ui.view.border.BorderDrawable;
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import org.apache.weex.ui.view.gesture.WXGestureType;
+import org.apache.weex.utils.BoxShadowUtil;
+import org.apache.weex.utils.WXDataStructureUtil;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXReflectionUtils;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+import java.lang.reflect.Type;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ConcurrentLinkedQueue;
+import java.util.concurrent.CountDownLatch;
+import java.util.concurrent.TimeUnit;
+import org.apache.weex.common.Constants.Event;
+import org.apache.weex.tracing.WXTracing.TraceInfo;
+import org.apache.weex.ui.animation.WXAnimationModule.AnimationHolder;
+
+/**
+ * abstract component
+ */
+public abstract class WXComponent<T extends View> extends WXBasicComponent implements IWXObject,
+    IWXActivityStateListener, OnActivePseudoListner {
+
+  public static final String PROP_FIXED_SIZE = "fixedSize";
+  public static final String PROP_FS_MATCH_PARENT = "m";
+  public static final String PROP_FS_WRAP_CONTENT = "w";
+  public static final String TYPE = "type";
+  public static final String ROOT = "_root";
+
+  private int mFixedProp = 0;
+  /** package **/ T mHost;
+
+  private volatile WXVContainer mParent;
+  private WXSDKInstance mInstance;
+  private Context mContext;
+
+  private int mAbsoluteY = 0;
+  private int mAbsoluteX = 0;
+  private boolean isLastLayoutDirectionRTL = false;
+  @Nullable
+  private Set<String> mGestureType;
+
+  private BorderDrawable mBackgroundDrawable;
+  private Drawable mRippleBackground;
+  private int mPreRealWidth = 0;
+  private int mPreRealHeight = 0;
+  private int mPreRealLeft = 0;
+  private int mPreRealRight = 0;
+  private int mPreRealTop = 0;
+  private int mStickyOffset = 0;
+  protected WXGesture mGesture;
+  private IFComponentHolder mHolder;
+  private boolean isUsing = false;
+  private List<OnClickListener> mHostClickListeners;
+  private List<OnFocusChangeListener> mFocusChangeListeners;
+  private Set<String> mAppendEvents;
+  private AnimationHolder mAnimationHolder;
+  private PesudoStatus mPesudoStatus;
+  private boolean mIsDestroyed = false;
+  private boolean mIsDisabled = false;
+  private int mType = TYPE_COMMON;
+  private boolean mNeedLayoutOnAnimation = false;
+  private String mLastBoxShadowId;
+  public int mDeepInComponentTree = 0;
+  public boolean mIsAddElementToTree = false;
+  //for fix element case
+  public int interactionAbsoluteX=0,interactionAbsoluteY=0;
+  //for fix slider case :cssLeft is not real left base parent;
+  protected int mChildrensWidth = 0;
+  private boolean mHasAddFocusListener = false;
+
+  public TraceInfo mTraceInfo = new TraceInfo();
+
+  public static final int TYPE_COMMON = 0;
+  public static final int TYPE_VIRTUAL = 1;
+
+  private boolean waste = false;
+  public boolean isIgnoreInteraction = false;
+
+  protected ContentBoxMeasurement contentBoxMeasurement;
+  private WXTransition mTransition;
+  private GraphicSize mPseudoResetGraphicSize;
+  @Nullable
+  private ConcurrentLinkedQueue<Pair<String, Map<String, Object>>> animations;
+
+  @Deprecated
+  public WXComponent(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+  @Deprecated
+  public WXComponent(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, basicComponentData);
+  }
+
+  public WXComponent(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    this(instance, parent, TYPE_COMMON, basicComponentData);
+  }
+
+  public WXComponent(WXSDKInstance instance, WXVContainer parent, int type, BasicComponentData basicComponentData) {
+    super(basicComponentData);
+    mInstance = instance;
+    mContext = mInstance.getContext();
+    mParent = parent;
+    mType = type;
+
+    if (instance != null)
+      setViewPortWidth(instance.getInstanceViewPortWidth());
+
+    onCreate();
+    ComponentObserver observer;
+    if ((observer = getInstance().getComponentObserver()) != null) {
+      observer.onCreate(this);
+    }
+  }
+
+
+
+  @Override
+  protected final void bindComponent(WXComponent component) {
+    super.bindComponent(component);
+    if (getInstance() != null) {
+      setViewPortWidth(getInstance().getInstanceViewPortWidth());
+    }
+    mParent = component.getParent();
+    mType = component.getType();
+  }
+
+  protected final void setContentBoxMeasurement(final ContentBoxMeasurement contentBoxMeasurement) {
+    this.contentBoxMeasurement = contentBoxMeasurement;
+    mInstance.addContentBoxMeasurement(getRenderObjectPtr(), contentBoxMeasurement);
+    WXBridgeManager.getInstance().bindMeasurementToRenderObject(getRenderObjectPtr());
+  }
+
+
+  @SuppressLint("RtlHardcoded")
+  public void setMarginsSupportRTL(ViewGroup.MarginLayoutParams lp, int left, int top, int right, int bottom) {
+      lp.setMargins(left, top, right, bottom);
+      if (lp instanceof FrameLayout.LayoutParams) {
+          FrameLayout.LayoutParams lp_frameLayout = (FrameLayout.LayoutParams) lp;
+          lp_frameLayout.gravity = Gravity.LEFT | Gravity.TOP;
+      }
+  }
+
+  public void updateStyles(WXComponent component) {
+    if (component != null) {
+      updateProperties(component.getStyles());
+      applyBorder(component);
+    }
+  }
+
+  public void updateStyles(Map<String, Object> styles) {
+    if (styles != null) {
+      updateProperties(styles);
+      applyBorder(this);
+    }
+  }
+
+  public void updateAttrs(WXComponent component) {
+    if (component != null) {
+      updateProperties(component.getAttrs());
+    }
+  }
+
+  public void updateAttrs(Map<String, Object> attrs) {
+    if (attrs != null) {
+      updateProperties(attrs);
+    }
+  }
+
+  private void applyBorder(WXComponent component) {
+    CSSShorthand border = component.getBorder();
+    float left = border.get(CSSShorthand.EDGE.LEFT);
+    float top = border.get(CSSShorthand.EDGE.TOP);
+    float right = border.get(CSSShorthand.EDGE.RIGHT);
+    float bottom = border.get(CSSShorthand.EDGE.BOTTOM);
+
+    if (mHost == null) {
+      return;
+    }
+
+    setBorderWidth(Constants.Name.BORDER_LEFT_WIDTH, left);
+    setBorderWidth(Constants.Name.BORDER_TOP_WIDTH, top);
+    setBorderWidth(Constants.Name.BORDER_RIGHT_WIDTH, right);
+    setBorderWidth(Constants.Name.BORDER_BOTTOM_WIDTH, bottom);
+  }
+
+  public void setPadding(CSSShorthand padding, CSSShorthand border) {
+    int left = (int) (padding.get(CSSShorthand.EDGE.LEFT) + border.get(CSSShorthand.EDGE.LEFT));
+    int top = (int) (padding.get(CSSShorthand.EDGE.TOP) + border.get(CSSShorthand.EDGE.TOP));
+    int right = (int) (padding.get(CSSShorthand.EDGE.RIGHT) + border.get(CSSShorthand.EDGE.RIGHT));
+    int bottom = (int) (padding.get(CSSShorthand.EDGE.BOTTOM) + border.get(CSSShorthand.EDGE.BOTTOM));
+
+    if (this instanceof FlatComponent && !((FlatComponent) this).promoteToView(true)) {
+      ((FlatComponent) this).getOrCreateFlatWidget().setContentBox(left, top, right, bottom);
+    } else if (mHost != null) {
+      mHost.setPadding(left, top, right, bottom);
+    }
+  }
+
+
+  public void applyComponentEvents(){
+       applyEvents();
+  }
+
+  private void applyEvents() {
+    if (getEvents() == null || getEvents().isEmpty())
+      return;
+    WXEvent event = getEvents();
+    int size = event.size();
+    for (int i=0; i<size; i++) {
+      if(i >= event.size()){
+        break;
+      }
+      String type = event.get(i);
+      addEvent(type);
+    }
+    setActiveTouchListener();
+  }
+
+  /**
+   * Do not use this method to add event, this only apply event already add to DomObject.
+   *
+   * @param type
+   */
+  public void addEvent(final String type) {
+    if (mAppendEvents == null) {
+      mAppendEvents = new HashSet<>();
+    }
+    if (TextUtils.isEmpty(type) || mAppendEvents.contains(type)) {
+      return;
+    }
+    final View view = getRealView();
+
+    if (type.equals(Constants.Event.LAYEROVERFLOW))
+      addLayerOverFlowListener(getRef());
+
+    if (type.equals(Constants.Event.CLICK)) {
+      if (view == null) {
+        // wait next time to add.
+        return;
+      }
+      if(mClickEventListener == null){
+        mClickEventListener = new OnClickListenerImp();
+      }
+      addClickListener(mClickEventListener);
+    } else if ((type.equals(Constants.Event.FOCUS) || type.equals(Constants.Event.BLUR))) {
+      if (!mHasAddFocusListener){
+        mHasAddFocusListener = true;
+        addFocusChangeListener(new OnFocusChangeListener() {
+        @Override
+        public void onFocusChange(boolean hasFocus) {
+          Map<String, Object> params = new HashMap<>();
+          params.put("timeStamp", System.currentTimeMillis());
+          fireEvent(hasFocus ? Constants.Event.FOCUS : Constants.Event.BLUR, params);
+        }
+      });
+      }
+    } else if (needGestureDetector(type)) {
+      if (null == view) {
+        // wait next time to add.
+        return;
+      }
+      if (view instanceof WXGestureObservable) {
+        if (mGesture == null) {
+          mGesture = new WXGesture(this, mContext);
+          boolean isPreventMove = WXUtils.getBoolean(getAttrs().get(Constants.Name.PREVENT_MOVE_EVENT), false);
+          mGesture.setPreventMoveEvent(isPreventMove);
+        }
+        if (mGestureType == null) {
+          mGestureType = new HashSet<>();
+        }
+        mGestureType.add(type);
+        ((WXGestureObservable)view).registerGestureListener(mGesture);
+      } else {
+        WXLogUtils.e(view.getClass().getSimpleName() + " don't implement " +
+            "WXGestureObservable, so no gesture is supported.");
+      }
+    } else {
+      final Scrollable scroller = getParentScroller();
+      if (scroller == null) {
+        // wait next time to add.
+        return;
+      }
+      if (type.equals(Constants.Event.APPEAR)) {
+        scroller.bindAppearEvent(this);
+      } else if (type.equals(Constants.Event.DISAPPEAR)) {
+        scroller.bindDisappearEvent(this);
+      }
+    }
+    // Final add to mAppendEvents.
+    mAppendEvents.add(type);
+  }
+
+  protected void onCreate() {
+
+  }
+
+  public void bindHolder(IFComponentHolder holder) {
+    mHolder = holder;
+  }
+
+
+  public WXSDKInstance getInstance() {
+    return mInstance;
+  }
+
+  public Context getContext() {
+    return mContext;
+  }
+
+  /**
+   * Find component by component reference.
+   *
+   * @param ref
+   * @return
+   */
+  protected final WXComponent findComponent(String ref) {
+    if (mInstance != null && ref != null) {
+      return WXSDKManager.getInstance()
+              .getWXRenderManager()
+              .getWXComponent(mInstance.getInstanceId(), ref);
+    }
+    return null;
+  }
+
+  public String getAttrByKey(String key) {
+    return "default";
+  }
+
+  //Holding the animation bean when component is uninitialized
+  public void postAnimation(AnimationHolder holder) {
+    this.mAnimationHolder = holder;
+  }
+
+  //This method will be removed once flatGUI is completed.
+  @RestrictTo(RestrictTo.Scope.LIBRARY)
+  public boolean isFlatUIEnabled() {
+    return mParent != null && mParent.isFlatUIEnabled();
+  }
+
+  private class OnClickListenerImp implements OnClickListener{
+    @Override
+    public void onHostViewClick() {
+      Map<String, Object> param = WXDataStructureUtil.newHashMapWithExpectedSize(1);
+      Map<String, Object> position = WXDataStructureUtil.newHashMapWithExpectedSize(4);
+      int[] location = new int[2];
+      mHost.getLocationOnScreen(location);
+      position.put("x", WXViewUtils.getWebPxByWidth(location[0], mInstance.getInstanceViewPortWidth()));
+      position.put("y", WXViewUtils.getWebPxByWidth(location[1], mInstance.getInstanceViewPortWidth()));
+      position.put("width", WXViewUtils.getWebPxByWidth(getLayoutWidth(), mInstance.getInstanceViewPortWidth()));
+      position.put("height", WXViewUtils.getWebPxByWidth(getLayoutHeight(), mInstance.getInstanceViewPortWidth()));
+      param.put(Constants.Name.POSITION, position);
+      fireEvent(Constants.Event.CLICK, param);
+    }
+  };
+  private OnClickListenerImp mClickEventListener;
+
+  public String getInstanceId() {
+    return mInstance.getInstanceId();
+  }
+
+  public Rect getComponentSize() {
+    Rect size = new Rect();
+    if (mHost != null) {
+      int[] location = new int[2];
+      int[] anchor = new int[2];
+      mHost.getLocationOnScreen(location);
+      mInstance.getContainerView().getLocationOnScreen(anchor);
+
+      int left = location[0] - anchor[0];
+      int top = (location[1] - mStickyOffset) - anchor[1];
+      int width = (int) getLayoutWidth();
+      int height = (int) getLayoutHeight();
+      size.set(left, top, left + width, top + height);
+    }
+    return size;
+  }
+
+  public final void invoke(String method, JSONArray args) {
+    final Invoker invoker = mHolder.getMethodInvoker(method);
+    if (invoker != null) {
+      try {
+        getInstance()
+                .getNativeInvokeHelper()
+                .invoke(this, invoker, args);
+
+      } catch (Exception e) {
+        WXLogUtils.e("[WXComponent] updateProperties :" + "class:" + getClass() + "method:" + invoker.toString() + " function " + WXLogUtils.getStackTrace(e));
+      }
+    } else {
+      onInvokeUnknownMethod(method, args);
+    }
+  }
+
+  /**
+   * Will be invoked when request method not found.
+   * Subclass should override this method, If you return hard-code method list in {@link IFComponentHolder#getMethods()}
+   *
+   * @param method
+   * @param args
+   */
+  protected void onInvokeUnknownMethod(String method, JSONArray args) {
+
+  }
+
+  public interface OnClickListener {
+    void onHostViewClick();
+  }
+
+  public interface OnFocusChangeListener{
+    void onFocusChange(boolean hasFocus);
+  }
+
+  public final void fireEvent(String type){
+    fireEvent(type,null);
+  }
+
+  public final void fireEvent(String type, Map<String, Object> params){
+    if(WXUtils.getBoolean(getAttrs().get("fireEventSyn"), false)){
+      fireEventWait(type, params);
+    }else{
+      fireEvent(type, params,null, null);
+    }
+  }
+
+  public final EventResult fireEventWait(String type, Map<String, Object> params){
+    final CountDownLatch waitLatch = new CountDownLatch(1);
+    EventResult callback = new EventResult(){
+      @Override
+      public void onCallback(Object result) {
+        super.onCallback(result);
+        waitLatch.countDown();
+      }
+    };
+    try{
+      fireEvent(type, params, null, callback);
+      waitLatch.await(50, TimeUnit.MILLISECONDS);
+      return  callback;
+    }catch (Exception e){
+      if(WXEnvironment.isApkDebugable()){
+        WXLogUtils.e("fireEventWait", e);
+      }
+      return  callback;
+    }
+  }
+
+  protected final void fireEvent(String type, Map<String, Object> params,Map<String, Object> domChanges){
+    fireEvent(type, params, domChanges, null);
+  }
+
+
+  private final void fireEvent(String type, Map<String, Object> params,Map<String, Object> domChanges, EventResult callback){
+    if(mInstance != null) {
+      List<Object> eventArgsValues = null;
+      if(getEvents() != null && getEvents().getEventBindingArgsValues() != null){
+        eventArgsValues = getEvents().getEventBindingArgsValues().get(type);
+      }
+      if(params != null){
+        String componentId = Statements.getComponentId(this);
+        if(componentId != null) {
+          params.put("componentId", componentId);
+        }
+      }
+      mInstance.fireEvent(getRef(), type, params,domChanges, eventArgsValues, callback);
+    }
+  }
+
+  /**
+   * find certain class type parent
+   * */
+  public  Object findTypeParent(WXComponent component, Class type){
+    if(component.getClass() == type){
+      return component;
+    }
+    if(component.getParent() != null) {
+      findTypeParent(component.getParent(), type);
+    }
+    return  null;
+  }
+
+  /**
+   * The view is created as needed
+   * @return true for lazy
+   */
+  public boolean isLazy() {
+    if(mLazy){
+      return true;
+    }
+    return mParent != null && mParent.isLazy();
+  }
+
+  protected final void addFocusChangeListener(OnFocusChangeListener l){
+    View view;
+    if(l != null && (view = getRealView()) != null) {
+      if( mFocusChangeListeners == null){
+        mFocusChangeListeners = new ArrayList<>();
+        view.setFocusable(true);
+        view.setOnFocusChangeListener(new View.OnFocusChangeListener() {
+          @Override
+          public void onFocusChange(View v, boolean hasFocus) {
+            for (OnFocusChangeListener listener : mFocusChangeListeners){
+              if(listener != null){
+                listener.onFocusChange(hasFocus);
+              }
+            }
+          }
+        });
+      }
+      mFocusChangeListeners.add(l);
+    }
+  }
+
+  protected final void addClickListener(OnClickListener l){
+    View view;
+    if(l != null && (view = getRealView()) != null) {
+      if(mHostClickListeners == null){
+        mHostClickListeners = new ArrayList<>();
+        view.setOnClickListener(new View.OnClickListener() {
+          @Override
+          public void onClick(View v) {
+            if(mGesture != null && mGesture.isTouchEventConsumedByAdvancedGesture()){
+              //event is already consumed by gesture
+              return;
+            }
+            for (OnClickListener listener : mHostClickListeners){
+              if(listener != null) {
+                listener.onHostViewClick();
+              }
+            }
+          }
+        });
+      }
+      mHostClickListeners.add(l);
+
+    }
+  }
+
+  protected final void removeClickListener(OnClickListener l) {
+    mHostClickListeners.remove(l);
+  }
+
+  public void bindData(WXComponent component) {
+    if (!isLazy()) {
+      if (component == null) {
+        component = this;
+      }
+      bindComponent(component);
+      updateStyles(component);
+      updateAttrs(component);
+      updateExtra(component.getExtra());
+    }
+  }
+
+  public void applyLayoutAndEvent(WXComponent component) {
+    if (!isLazy()) {
+      if (component == null) {
+        component = this;
+      }
+      bindComponent(component);
+      setSafeLayout(component);
+      setPadding(component.getPadding(), component.getBorder());
+      applyEvents();
+    }
+  }
+
+  public void setDemission(GraphicSize size, GraphicPosition position) {
+    setLayoutPosition(position);
+    setLayoutSize(size);
+  }
+
+  public void updateDemission(float top, float bottom, float left, float right, float height, float width) {
+    getLayoutPosition().update(top, bottom, left, right);
+    getLayoutSize().update(width, height);
+  }
+
+
+  public void applyLayoutOnly(){
+    if(!isLazy()) {
+      setSafeLayout(this);
+      setPadding(this.getPadding(), this.getBorder());
+    }
+  }
+
+
+  public void refreshData(WXComponent component) {
+
+  }
+
+  @Deprecated
+  public void updateProperties(Map<String, Object> props) {
+    if (props == null || (mHost == null && !isVirtualComponent())) {
+      return;
+    }
+
+    for (Map.Entry<String, Object> entry : props.entrySet()) {
+      Object key_obj = entry.getKey();
+      String key = WXUtils.getString(key_obj, null);
+      if ((key != null) && !(key_obj instanceof String)) {
+        Map<String, String> map = new HashMap<>();
+        map.put("componentType", getComponentType());
+        map.put("actual key", key == null ? "" : key);
+        WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),
+            WXErrorCode.WX_RENDER_ERR_COMPONENT_ATTR_KEY,
+            "WXComponent.updateProperties",
+            WXErrorCode.WX_RENDER_ERR_COMPONENT_ATTR_KEY.getErrorMsg(),
+            map);
+      }
+
+      Object param = entry.getValue();
+      String value = WXUtils.getString(param, null);
+
+      if (key == null) {
+        WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),
+                WXErrorCode.WX_RENDER_ERR_NULL_KEY, "updateProperties",
+                WXErrorCode.WX_RENDER_ERR_NULL_KEY.getErrorMsg(), null);
+      } else {
+        if (TextUtils.isEmpty(value)) {
+          param = convertEmptyProperty(key, value);
+        }
+        if (!setProperty(key, param)) {
+          if (mHolder == null) {
+            return;
+          }
+          Invoker invoker = mHolder.getPropertyInvoker(key);
+          if (invoker != null) {
+            try {
+              Type[] paramClazzs = invoker.getParameterTypes();
+              if (paramClazzs.length != 1) {
+                WXLogUtils.e("[WXComponent] setX method only one parameter：" + invoker);
+                return;
+              }
+              param = WXReflectionUtils.parseArgument(paramClazzs[0], param);
+              invoker.invoke(this, param);
+            } catch (Exception e) {
+              WXLogUtils.e("[WXComponent] updateProperties :" + "class:" + getClass() + "method:" + invoker.toString() + " function " + WXLogUtils.getStackTrace(e));
+            }
+          }
+        }
+      }
+    }
+    readyToRender();
+    if (this instanceof FlatComponent && mBackgroundDrawable != null) {
+      FlatComponent flatComponent = (FlatComponent) this;
+      if (!flatComponent.promoteToView(true) && !(flatComponent
+              .getOrCreateFlatWidget() instanceof AndroidViewWidget)) {
+        flatComponent.getOrCreateFlatWidget().setBackgroundAndBorder(mBackgroundDrawable);
+      }
+    }
+  }
+
+  /**
+   * Apply styles and attributes.
+   *
+   * @param key   name of argument
+   * @param param value of argument
+   * @return true means that the property is consumed
+   */
+  protected boolean setProperty(String key, Object param) {
+    if(key == null){
+      return true;
+    }
+    switch (key) {
+      case Constants.Name.PREVENT_MOVE_EVENT:
+        if (mGesture != null) {
+          mGesture.setPreventMoveEvent(WXUtils.getBoolean(param, false));
+        }
+        return true;
+      case Constants.Name.DISABLED:
+        Boolean disabled = WXUtils.getBoolean(param, null);
+        if (disabled != null) {
+          setDisabled(disabled);
+          setPseudoClassStatus(Constants.PSEUDO.DISABLED, disabled);
+        }
+        return true;
+      case Constants.Name.POSITION:
+        String position = WXUtils.getString(param, null);
+        if (position != null)
+          setSticky(position);
+        return true;
+      case Constants.Name.BACKGROUND_COLOR:
+        String bgColor = WXUtils.getString(param, null);
+        if (bgColor != null)
+          setBackgroundColor(bgColor);
+        return true;
+      case Constants.Name.BACKGROUND_IMAGE:
+        String bgImage = WXUtils.getString(param, null);
+        if (bgImage != null && mHost != null) {
+          setBackgroundImage(bgImage);
+        }
+        return true;
+      case Constants.Name.OPACITY:
+        Float opacity = WXUtils.getFloat(param, null);
+        if (opacity != null)
+          setOpacity(opacity);
+        return true;
+      case Constants.Name.BORDER_RADIUS:
+      case Constants.Name.BORDER_TOP_LEFT_RADIUS:
+      case Constants.Name.BORDER_TOP_RIGHT_RADIUS:
+      case Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS:
+      case Constants.Name.BORDER_BOTTOM_LEFT_RADIUS:
+        Float radius = WXUtils.getFloat(param, null);
+        if (radius != null)
+          setBorderRadius(key, radius);
+        return true;
+      case Constants.Name.BORDER_STYLE:
+      case Constants.Name.BORDER_RIGHT_STYLE:
+      case Constants.Name.BORDER_BOTTOM_STYLE:
+      case Constants.Name.BORDER_LEFT_STYLE:
+      case Constants.Name.BORDER_TOP_STYLE:
+        String border_style = WXUtils.getString(param, null);
+        if (border_style != null)
+          setBorderStyle(key, border_style);
+        return true;
+      case Constants.Name.BORDER_COLOR:
+      case Constants.Name.BORDER_TOP_COLOR:
+      case Constants.Name.BORDER_RIGHT_COLOR:
+      case Constants.Name.BORDER_BOTTOM_COLOR:
+      case Constants.Name.BORDER_LEFT_COLOR:
+        String border_color = WXUtils.getString(param, null);
+        if (border_color != null)
+          setBorderColor(key, border_color);
+        return true;
+      case Constants.Name.VISIBILITY:
+        String visibility = WXUtils.getString(param, null);
+        if (visibility != null)
+          setVisibility(visibility);
+        return true;
+      case Constants.Name.ELEVATION:
+        if (param != null) {
+          updateElevation();
+        }
+        return true;
+      case PROP_FIXED_SIZE:
+        String fixedSize = WXUtils.getString(param, PROP_FS_MATCH_PARENT);
+        setFixedSize(fixedSize);
+        return true;
+      case Constants.Name.ARIA_LABEL:
+        String label = WXUtils.getString(param, "");
+        setAriaLabel(label);
+        return true;
+      case Constants.Name.ARIA_HIDDEN:
+        boolean isHidden = WXUtils.getBoolean(param, false);
+        setAriaHidden(isHidden);
+        return true;
+      case Constants.Name.WIDTH:
+      case Constants.Name.MIN_WIDTH:
+      case Constants.Name.MAX_WIDTH:
+      case Constants.Name.HEIGHT:
+      case Constants.Name.MIN_HEIGHT:
+      case Constants.Name.MAX_HEIGHT:
+      case Constants.Name.ALIGN_ITEMS:
+      case Constants.Name.ALIGN_SELF:
+      case Constants.Name.FLEX:
+      case Constants.Name.FLEX_DIRECTION:
+      case Constants.Name.JUSTIFY_CONTENT:
+      case Constants.Name.FLEX_WRAP:
+      case Constants.Name.MARGIN:
+      case Constants.Name.MARGIN_TOP:
+      case Constants.Name.MARGIN_LEFT:
+      case Constants.Name.MARGIN_RIGHT:
+      case Constants.Name.MARGIN_BOTTOM:
+      case Constants.Name.PADDING:
+      case Constants.Name.PADDING_TOP:
+      case Constants.Name.PADDING_LEFT:
+      case Constants.Name.PADDING_RIGHT:
+      case Constants.Name.PADDING_BOTTOM:
+      case Constants.Name.BORDER_WIDTH:
+      case Constants.Name.BORDER_TOP_WIDTH:
+      case Constants.Name.BORDER_RIGHT_WIDTH:
+      case Constants.Name.BORDER_BOTTOM_WIDTH:
+      case Constants.Name.BORDER_LEFT_WIDTH:
+      case Constants.Name.LEFT:
+      case Constants.Name.TOP:
+      case Constants.Name.RIGHT:
+      case Constants.Name.BOTTOM:
+        return true;
+      case Constants.Name.BOX_SHADOW:
+        try {
+          updateBoxShadow();
+        } catch (Throwable t) {
+          t.printStackTrace();
+        }
+        return true;
+      case Constants.Name.ROLE:
+        setRole(WXUtils.getString(param, ""));
+        return true;
+      default:
+        return false;
+    }
+  }
+
+  protected BorderDrawable getOrCreateBorder() {
+    if (mBackgroundDrawable == null) {
+      mBackgroundDrawable = new BorderDrawable();
+      if (mHost != null) {
+        WXViewUtils.setBackGround(mHost, null, this);
+        if (mRippleBackground == null) {
+          WXViewUtils.setBackGround(mHost, mBackgroundDrawable, this);
+        } else {
+          //TODO Not strictly clip according to background-clip:border-box
+          WXViewUtils.setBackGround(mHost, new LayerDrawable(new Drawable[]{
+                  mRippleBackground, mBackgroundDrawable}), this);
+        }
+      }
+    }
+    return mBackgroundDrawable;
+  }
+
+  /**
+   * layout view
+   */
+  public void setSafeLayout(WXComponent component) {
+    if (TextUtils.isEmpty(component.getComponentType())
+            || TextUtils.isEmpty(component.getRef()) || component.getLayoutPosition() == null
+            || component.getLayoutSize() == null) {
+      return;
+    }
+    setLayout(component);
+  }
+
+  /**
+   * layout view
+   */
+  public void setLayout(WXComponent component) {
+    setLayoutSize(component.getLayoutSize());
+    setLayoutPosition(component.getLayoutPosition());
+    setPaddings(component.getPadding());
+    setMargins(component.getMargin());
+    setBorders(component.getBorder());
+
+    boolean isRTL = component.isLayoutRTL();
+    setIsLayoutRTL(isRTL);
+    if (isRTL != component.isLastLayoutDirectionRTL) {
+      component.isLastLayoutDirectionRTL = isRTL;
+      layoutDirectionDidChanged(isRTL);
+    }
+
+    parseAnimation();
+
+    boolean nullParent = mParent == null;//parent is nullable
+
+    //offset by sibling
+    int siblingOffset = nullParent ? 0 : mParent.getChildrenLayoutTopOffset();
+
+    CSSShorthand parentPadding = (nullParent ? new CSSShorthand() : mParent.getPadding());
+    CSSShorthand parentBorder = (nullParent ? new CSSShorthand() : mParent.getBorder());
+
+    int realWidth = (int) getLayoutSize().getWidth();
+    int realHeight = (int) getLayoutSize().getHeight();
+
+    int realLeft = 0;
+    int realTop = 0;
+    int realRight = 0;
+
+    if (isFixed()) {
+      realLeft = (int) (getLayoutPosition().getLeft() - getInstance().getRenderContainerPaddingLeft());
+      realTop = (int) (getLayoutPosition().getTop() - getInstance().getRenderContainerPaddingTop()) + siblingOffset;
+    } else {
+      realLeft = (int) (getLayoutPosition().getLeft() -
+              parentPadding.get(CSSShorthand.EDGE.LEFT) - parentBorder.get(CSSShorthand.EDGE.LEFT));
+      realTop = (int) (getLayoutPosition().getTop() -
+              parentPadding.get(CSSShorthand.EDGE.TOP) - parentBorder.get(CSSShorthand.EDGE.TOP)) + siblingOffset;
+    }
+
+    realRight = (int) getMargin().get(CSSShorthand.EDGE.RIGHT);
+    int realBottom = (int) getMargin().get(CSSShorthand.EDGE.BOTTOM);
+
+    Point rawOffset = new Point(
+            (int) getLayoutPosition().getLeft(),
+            (int) getLayoutPosition().getTop());
+
+    if (mPreRealWidth == realWidth && mPreRealHeight == realHeight && mPreRealLeft == realLeft && mPreRealRight == realRight && mPreRealTop == realTop) {
+      return;
+    }
+
+    if (this instanceof WXCell && realHeight >= WXPerformance.VIEW_LIMIT_HEIGHT && realWidth>=WXPerformance.VIEW_LIMIT_WIDTH){
+      mInstance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_CELL_EXCEED_NUM,1);
+      mInstance.getWXPerformance().cellExceedNum++;
+      if (WXAnalyzerDataTransfer.isOpenPerformance){
+        WXAnalyzerDataTransfer.transferPerformance(getInstanceId(),"details",WXInstanceApm.KEY_PAGE_STATS_CELL_EXCEED_NUM,
+            String.format(Locale.ROOT, "cell:ref:%s,[w:%d,h:%d],attrs:%s,styles:%s",getRef(),realWidth,realHeight,getAttrs(),getStyles())
+        );
+      }
+
+    }
+
+    mAbsoluteY = (int) (nullParent ? 0 : mParent.getAbsoluteY() + getCSSLayoutTop());
+    mAbsoluteX = (int) (nullParent ? 0 : mParent.getAbsoluteX() + getCSSLayoutLeft());
+
+    if (mHost == null) {
+      return;
+    }
+
+    //calculate first screen time
+    if (!(mHost instanceof ViewGroup) && mAbsoluteY + realHeight > mInstance.getWeexHeight() + 1) {
+      if (!mInstance.mEnd){
+        mInstance.onOldFsRenderTimeLogic();
+      }
+      if (!mInstance.isNewFsEnd){
+        mInstance.isNewFsEnd = true;
+        mInstance.getApmForInstance().arriveNewFsRenderTime();
+      }
+    }
+
+    MeasureOutput measureOutput = measure(realWidth, realHeight);
+    realWidth = measureOutput.width;
+    realHeight = measureOutput.height;
+
+    setComponentLayoutParams(realWidth, realHeight, realLeft, realTop, realRight, realBottom, rawOffset);
+  }
+
+  private void setComponentLayoutParams(int realWidth, int realHeight, int realLeft, int realTop,
+                                        int realRight, int realBottom, Point rawOffset) {
+    if(getInstance() == null || getInstance().isDestroy()){
+      return;
+    }
+
+    FlatGUIContext UIImp = getInstance().getFlatUIContext();
+    WidgetContainer ancestor;
+    Widget widget;
+    if (UIImp != null && (ancestor = UIImp.getFlatComponentAncestor(this)) != null) {
+      if (this instanceof FlatComponent && !((FlatComponent) this).promoteToView(true)) {
+        widget = ((FlatComponent) this).getOrCreateFlatWidget();
+      } else {
+        widget = UIImp.getAndroidViewWidget(this);
+      }
+      setWidgetParams(widget, UIImp, rawOffset, realWidth, realHeight, realLeft, realRight, realTop,
+              realBottom);
+    } else if (mHost != null) {
+      // clear box shadow before host's size changed
+      clearBoxShadow();
+      if (isFixed()) {
+        setFixedHostLayoutParams(mHost, realWidth, realHeight, realLeft, realRight, realTop,
+                realBottom);
+      } else {
+        setHostLayoutParams(mHost, realWidth, realHeight, realLeft, realRight, realTop, realBottom);
+      }
+      recordInteraction(realWidth,realHeight);
+      mPreRealWidth = realWidth;
+      mPreRealHeight = realHeight;
+      mPreRealLeft = realLeft;
+      mPreRealRight = realRight;
+      mPreRealTop = realTop;
+      onFinishLayout();
+      // restore box shadow
+      updateBoxShadow();
+    }
+  }
+
+  /**
+   * layout direction is changed
+   * basic class is a empty implementation
+   * subclass can override this method do some RTL necessary things
+   * such as WXText
+   */
+  protected void layoutDirectionDidChanged(boolean isRTL) {
+
+  }
+
+  private void recordInteraction(int realWidth,int realHeight){
+    if (!mIsAddElementToTree){
+      return;
+    }
+    mIsAddElementToTree = false;
+    if (null == mParent){
+      interactionAbsoluteX = 0;
+      interactionAbsoluteY = 0;
+    }else {
+      float cssTop = getCSSLayoutTop();
+      float cssLeft = getCSSLayoutLeft();
+      interactionAbsoluteX = (int)(this.isFixed() ? cssLeft : mParent.interactionAbsoluteX + mParent.mChildrensWidth + cssLeft);
+      interactionAbsoluteY = (int)(this.isFixed() ? cssTop  : mParent.interactionAbsoluteY + cssTop);
+      //fix for slider impl ,and interactionTime calculate if component is out screen
+      if (WXBasicComponentType.SLIDER.equalsIgnoreCase(mParent.getComponentType()) || WXBasicComponentType.CYCLE_SLIDER.equalsIgnoreCase(mParent.getComponentType())){
+        if (!WXBasicComponentType.INDICATOR.equalsIgnoreCase(getComponentType())){
+          mParent.mChildrensWidth += (int)(realWidth + cssLeft);
+        }
+      }
+    }
+
+    if (null == getInstance().getApmForInstance().instanceRect){
+      getInstance().getApmForInstance().instanceRect = new Rect();
+    }
+    Rect instanceRect = getInstance().getApmForInstance().instanceRect;
+    instanceRect.set(0,0,mInstance.getWeexWidth(),mInstance.getWeexHeight());
+    boolean inScreen =
+          instanceRect.contains(interactionAbsoluteX,interactionAbsoluteY) //leftTop
+              || instanceRect.contains(interactionAbsoluteX+realWidth,interactionAbsoluteY)//rightTop
+              || instanceRect.contains(interactionAbsoluteX,interactionAbsoluteY+realHeight)//leftBottom
+              || instanceRect.contains(interactionAbsoluteX+realWidth,interactionAbsoluteY+realHeight);//rightBottom
+    mInstance.onChangeElement(this,!inScreen);
+  }
+
+  private void setWidgetParams(Widget widget, FlatGUIContext UIImp, Point rawoffset,
+                               int width, int height, int left, int right, int top, int bottom) {
+    Point childOffset = new Point();
+    if (mParent != null) {
+      if (mParent instanceof FlatComponent &&
+              UIImp.getFlatComponentAncestor(mParent) != null &&
+              UIImp.getAndroidViewWidget(mParent) == null) {
+        childOffset.set(rawoffset.x, rawoffset.y);
+      }
+      else{
+        childOffset.set(left, top);
+      }
+
+      if (mParent instanceof FlatComponent &&
+              UIImp.getFlatComponentAncestor(mParent) != null &&
+              UIImp.getAndroidViewWidget(mParent) == null) {
+        Point parentLayoutOffset = ((FlatComponent) mParent).getOrCreateFlatWidget().getLocInFlatContainer();
+        childOffset.offset(parentLayoutOffset.x, parentLayoutOffset.y);
+      }
+      ViewGroup.LayoutParams lp = mParent
+              .getChildLayoutParams(this, mHost, width, height, left, right, top, bottom);
+      if (lp instanceof ViewGroup.MarginLayoutParams) {
+        width = lp.width;
+        height = lp.height;
+        left = ((ViewGroup.MarginLayoutParams) lp).leftMargin;
+        right = ((ViewGroup.MarginLayoutParams) lp).rightMargin;
+        top = ((ViewGroup.MarginLayoutParams) lp).topMargin;
+        bottom = ((ViewGroup.MarginLayoutParams) lp).bottomMargin;
+      }
+    }
+    widget.setLayout(width, height, left, right, top, bottom, childOffset);
+
+    if (widget instanceof AndroidViewWidget && ((AndroidViewWidget) widget).getView()!=null) {
+      //TODO generic method if ever possible
+      setHostLayoutParams((T) ((AndroidViewWidget) widget).getView(),
+              width, height, childOffset.x, right, childOffset.y, bottom);
+    }
+  }
+
+  public int getLayoutTopOffsetForSibling() {
+    return 0;
+  }
+
+  protected void setHostLayoutParams(T host, int width, int height, int left, int right, int top, int bottom) {
+    ViewGroup.LayoutParams lp;
+    if (mParent == null) {
+        FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(width, height);
+        this.setMarginsSupportRTL(params, left, top, right, bottom);
+        lp = params;
+    } else {
+        lp = mParent.getChildLayoutParams(this, host, width, height, left, right, top, bottom);
+    }
+    if (lp != null) {
+        host.setLayoutParams(lp);
+    }
+  }
+
+  private void setFixedHostLayoutParams(T host, int width, int height, int left, int right, int top, int bottom){
+    FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
+
+    params.width = width;
+    params.height = height;
+
+    this.setMarginsSupportRTL(params, left, top, right, bottom);
+
+    host.setLayoutParams(params);
+    mInstance.moveFixedView(host);
+
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("Weex_Fixed_Style", "WXComponent:setLayout :" + left + " " + top + " " + width + " " + height);
+      WXLogUtils.d("Weex_Fixed_Style", "WXComponent:setLayout Left:" + getStyles().getLeft() + " " + (int) getStyles().getTop());
+    }
+  }
+
+  protected void updateBoxShadow() {
+    if (!BoxShadowUtil.isBoxShadowEnabled()) {
+//      WXLogUtils.w("BoxShadow", "box-shadow disabled");
+      return;
+    }
+
+    if (getStyles() != null) {
+      Object boxShadow = getStyles().get(Constants.Name.BOX_SHADOW);
+      Object shadowQuality = getAttrs().get(Constants.Name.SHADOW_QUALITY);
+      if (boxShadow == null) {
+        return;
+      }
+
+      View target = mHost;
+      if (this instanceof WXVContainer) {
+        target = ((WXVContainer) this).getBoxShadowHost(false);
+      }
+
+      if (target == null) {
+        return;
+      }
+
+      float quality = WXUtils.getFloat(shadowQuality, 0.5f);
+      int viewPort = getInstance().getInstanceViewPortWidth();
+      String token = new StringBuilder(boxShadow.toString()).append(" / [")
+              .append(target.getMeasuredWidth()).append(",")
+              .append(target.getMeasuredHeight()).append("] / ")
+              .append(quality).toString();
+
+      if (mLastBoxShadowId != null && mLastBoxShadowId.equals(token)) {
+        WXLogUtils.d("BoxShadow", "box-shadow style was not modified. " + token);
+        return;
+      }
+
+      float[] radii = new float[]{0, 0, 0, 0, 0, 0, 0, 0};
+      WXStyle style = getStyles();
+      if (style != null) {
+        float tl = WXUtils.getFloat(style.get(Constants.Name.BORDER_TOP_LEFT_RADIUS), 0f);
+        radii[0] = tl;
+        radii[1] = tl;
+
+        float tr = WXUtils.getFloat(style.get(Constants.Name.BORDER_TOP_RIGHT_RADIUS), 0f);
+        radii[2] = tr;
+        radii[3] = tr;
+
+        float br = WXUtils.getFloat(style.get(Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS), 0f);
+        radii[4] = br;
+        radii[5] = br;
+
+        float bl = WXUtils.getFloat(style.get(Constants.Name.BORDER_BOTTOM_LEFT_RADIUS), 0f);
+        radii[6] = bl;
+        radii[7] = bl;
+
+        if (style.containsKey(Constants.Name.BORDER_RADIUS)) {
+          float radius = WXUtils.getFloat(style.get(Constants.Name.BORDER_RADIUS), 0f);
+          for (int i = 0; i < radii.length; i++) {
+            radii[i] = radius;
+          }
+        }
+      }
+
+      BoxShadowUtil.setBoxShadow(target, boxShadow.toString(), radii, viewPort, quality);
+      mLastBoxShadowId = token;
+    } else {
+      WXLogUtils.w("Can not resolve styles");
+    }
+  }
+
+  protected void clearBoxShadow() {
+    if (!BoxShadowUtil.isBoxShadowEnabled()) {
+//      WXLogUtils.w("BoxShadow", "box-shadow disabled");
+      return;
+    }
+
+    if (getStyles() != null) {
+      Object obj = getStyles().get(Constants.Name.BOX_SHADOW);
+      if (obj == null) {
+        return;
+      }
+    }
+
+    View target = mHost;
+    if (this instanceof WXVContainer) {
+      target = ((WXVContainer) this).getBoxShadowHost(true);
+    }
+
+    if (target != null && Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
+      ViewOverlay overlay = target.getOverlay();
+      if (overlay != null) {
+        overlay.clear();
+      }
+    }
+    mLastBoxShadowId = null;
+  }
+
+  /**
+   * After component's layout result is apply to view. May be invoke multiple times since
+   * DOM can be changed in js runtime.
+   */
+  protected void onFinishLayout() {
+    Object param = getStyles() != null ? getStyles().get(Constants.Name.BACKGROUND_IMAGE) : null;
+    if (param != null) {
+      setBackgroundImage(param.toString());
+    }
+  }
+
+  /**
+   * measure
+   */
+  protected MeasureOutput measure(int width, int height) {
+    MeasureOutput measureOutput = new MeasureOutput();
+
+    if (mFixedProp != 0) {
+      measureOutput.width = mFixedProp;
+      measureOutput.height = mFixedProp;
+    } else {
+      measureOutput.width = width;
+      measureOutput.height = height;
+    }
+    return measureOutput;
+  }
+
+  @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
+  protected void setAriaHidden(boolean isHidden) {
+    View host = getHostView();
+    if (host != null && Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+      host.setImportantForAccessibility(isHidden ? View.IMPORTANT_FOR_ACCESSIBILITY_NO : View.IMPORTANT_FOR_ACCESSIBILITY_YES);
+    }
+  }
+
+  protected void setAriaLabel(String label) {
+    View host = getHostView();
+    if (host != null) {
+      host.setContentDescription(label);
+    }
+  }
+
+  protected void setRole(String roleKey) {
+    View host = getHostView();
+    String role = roleKey;
+    if (host != null && !TextUtils.isEmpty(roleKey)) {
+      IWXAccessibilityRoleAdapter roleAdapter = WXSDKManager.getInstance().getAccessibilityRoleAdapter();
+      if (roleAdapter != null) {
+        role = roleAdapter.getRole(roleKey);
+      }
+      final String finalRole = role;
+      AccessibilityDelegateCompat delegate = new AccessibilityDelegateCompat() {
+        @Override
+        public void onInitializeAccessibilityNodeInfo(View host, AccessibilityNodeInfoCompat info) {
+          try {
+            super.onInitializeAccessibilityNodeInfo(host, info);
+            info.setRoleDescription(finalRole);
+          } catch (Throwable e) {
+            WXLogUtils.e("SetRole failed!");
+          }
+        }
+      };
+      ViewCompat.setAccessibilityDelegate(host, delegate);
+    }
+  }
+
+  /**
+   * Avoid large size view fail in GPU-Animation.
+   *
+   * @param fixedSize
+   */
+  private void setFixedSize(String fixedSize) {
+    if (PROP_FS_MATCH_PARENT.equals(fixedSize)) {
+      mFixedProp = ViewGroup.LayoutParams.MATCH_PARENT;
+    } else if (PROP_FS_WRAP_CONTENT.equals(fixedSize)) {
+      mFixedProp = ViewGroup.LayoutParams.WRAP_CONTENT;
+    } else {
+      mFixedProp = 0;
+      return;
+    }
+    if (mHost != null) {
+      ViewGroup.LayoutParams layoutParams = mHost.getLayoutParams();
+      if (layoutParams != null) {
+        layoutParams.height = mFixedProp;
+        layoutParams.width = mFixedProp;
+        mHost.setLayoutParams(layoutParams);
+      }
+    }
+  }
+
+  /**
+   * Add new event to component,this will post a task to DOM thread to add event.
+   *
+   * @param type
+   */
+  protected void appendEventToDOM(String type) {
+//    WXSDKManager.getInstance().getWXDomManager().postAction(getInstanceId(), Actions.getAddEvent(getRef(), type), false);
+  }
+
+  public View getRealView() {
+    return mHost;
+  }
+
+  /**
+   * Judge whether need to set an onTouchListener.<br>
+   * As there is only one onTouchListener in each view, so all the gesture that use onTouchListener should put there.
+   *
+   * @param type eventType {@link Event}
+   * @return true for set an onTouchListener, otherwise false
+   */
+  private boolean needGestureDetector(String type) {
+    if (mHost != null) {
+      for (WXGestureType gesture : WXGestureType.LowLevelGesture.values()) {
+        if (type.equals(gesture.toString())) {
+          return true;
+        }
+      }
+      for (WXGestureType gesture : WXGestureType.HighLevelGesture.values()) {
+        if (type.equals(gesture.toString())) {
+          return true;
+        }
+      }
+    }
+    if(WXGesture.isStopPropagation(type)){
+      return  true;
+    }
+    return false;
+  }
+
+  /**
+   * get Scroller components
+   */
+  public Scrollable getParentScroller() {
+    WXComponent component = this;
+    WXVContainer container;
+    Scrollable scroller;
+    for (; ; ) {
+      container = component.getParent();
+      if (container == null) {
+        return null;
+      }
+      if (container instanceof Scrollable) {
+        scroller = (Scrollable) container;
+        return scroller;
+      }
+      if (container.getRef().equals(ROOT)) {
+        return null;
+      }
+      component = container;
+    }
+  }
+
+  /**
+   * get Scroller components
+   */
+  @Nullable
+  public Scrollable getFirstScroller() {
+    if (this instanceof Scrollable) {
+      return (Scrollable) this;
+    }
+    return null;
+  }
+
+  public WXVContainer getParent() {
+    return mParent;
+  }
+
+  /**
+   * create view
+   */
+  public final void createView() {
+    if (!isLazy()) {
+      createViewImpl();
+    }
+  }
+
+  protected void createViewImpl() {
+    if (mContext != null) {
+      mHost = initComponentHostView(mContext);
+      if (mHost == null && !isVirtualComponent()) {
+        //compatible
+        initView();
+      }
+      if (mHost != null) {
+        if(mHost.getId() == View.NO_ID)
+          mHost.setId(WXViewUtils.generateViewId());
+        if(TextUtils.isEmpty(mHost.getContentDescription()) && WXEnvironment.isApkDebugable()){
+          mHost.setContentDescription(getRef());
+        }
+        ComponentObserver observer;
+        if ((observer = getInstance().getComponentObserver()) != null) {
+          observer.onViewCreated(this, mHost);
+        }
+      }
+      onHostViewInitialized(mHost);
+    } else {
+      WXLogUtils.e("createViewImpl", "Context is null");
+    }
+  }
+
+  /**
+   * Use {@link #initComponentHostView(Context context)} instead.
+   */
+  @Deprecated
+  protected void initView() {
+    if (mContext != null)
+      mHost = initComponentHostView(mContext);
+  }
+
+
+  /**
+   * Create corresponding view for this component.
+   *
+   * @param context
+   * @return
+   */
+  protected T initComponentHostView(@NonNull Context context) {
+    /**
+     * compatible old initView
+     */
+    return null;
+  }
+
+  /**
+   * Called after host view init. <br>
+   * Any overriding methods should invoke this method at the right time, to ensure the cached animation can be triggered correctly.
+   * (the animation will be cached when {@link #isLazy()} is true)
+   *
+   * @param host the host view
+   */
+  @CallSuper
+  protected void onHostViewInitialized(T host) {
+    if (mAnimationHolder != null) {
+//      Performs cached animation
+      mAnimationHolder.execute(mInstance, this);
+    }
+    setActiveTouchListener();
+  }
+
+  public T getHostView() {
+    return mHost;
+  }
+
+  /**
+   * use {@link #getHostView()} instead
+   *
+   * @return
+   */
+  @Deprecated
+  public View getView() {
+    return mHost;
+  }
+
+  public int getAbsoluteY() {
+    return mAbsoluteY;
+  }
+
+  public int getAbsoluteX() {
+    return mAbsoluteX;
+  }
+
+  public void removeEvent(String type) {
+    if (TextUtils.isEmpty(type)) {
+      return;
+    }
+
+    if (type.equals(Constants.Event.LAYEROVERFLOW))
+      removeLayerOverFlowListener(getRef());
+
+    if(getEvents() != null){
+      getEvents().remove(type);
+    }
+    if(mAppendEvents != null) {
+      mAppendEvents.remove(type);//only clean append events, not dom's events.
+    }
+    if(mGestureType != null){
+      mGestureType.remove(type);
+    }
+    removeEventFromView(type);
+  }
+
+  protected void removeEventFromView(String type) {
+    if (type.equals(Constants.Event.CLICK) && getRealView() != null && mHostClickListeners != null) {
+      if(mClickEventListener == null){
+        mClickEventListener = new OnClickListenerImp();
+      }
+      mHostClickListeners.remove(mClickEventListener);
+      //click event only remove from listener array
+    }
+    Scrollable scroller = getParentScroller();
+    if (type.equals(Constants.Event.APPEAR) && scroller != null) {
+      scroller.unbindAppearEvent(this);
+    }
+    if (type.equals(Constants.Event.DISAPPEAR) && scroller != null) {
+      scroller.unbindDisappearEvent(this);
+    }
+  }
+
+  public void removeAllEvent() {
+    if (getEvents().size() < 1) {
+      return;
+    }
+    WXEvent events = getEvents();
+    int size = events.size();
+    for (int i=0; i<size; i++) {
+      if(i >= events.size()){
+        break;
+      }
+      String event = events.get(i);
+      if (event == null) {
+        continue;
+      }
+      removeEventFromView(event);
+    }
+    if(mAppendEvents!=null) {
+      mAppendEvents.clear();//only clean append events, not dom's events.
+    }
+    if(mGestureType != null){
+      mGestureType.clear();
+    }
+    mGesture = null;
+    if (getRealView() != null &&
+            getRealView() instanceof WXGestureObservable) {
+      ((WXGestureObservable) getRealView()).registerGestureListener(null);
+    }
+    if (mHost != null) {
+      mHost.setOnFocusChangeListener(null);
+      if (mHostClickListeners != null && mHostClickListeners.size() > 0) {
+        mHostClickListeners.clear();
+        mHost.setOnClickListener(null);
+      }
+    }
+  }
+
+  public final void removeStickyStyle() {
+    if (isSticky()) {
+      Scrollable scroller = getParentScroller();
+      if (scroller != null) {
+        scroller.unbindStickStyle(this);
+      }
+    }
+  }
+
+  public boolean isSticky() {
+    return getStyles().isSticky();
+  }
+
+  public boolean isFixed() {
+    return getStyles().isFixed();
+  }
+
+  public void setDisabled(boolean disabled) {
+    mIsDisabled = disabled;
+    if (mHost == null) {
+      return;
+    }
+    mHost.setEnabled(!disabled);
+  }
+
+  public boolean isDisabled() {
+    return mIsDisabled;
+  }
+
+  public void setSticky(String sticky) {
+    if (!TextUtils.isEmpty(sticky) && sticky.equals(Constants.Value.STICKY)) {
+      Scrollable waScroller = getParentScroller();
+      if (waScroller != null) {
+        waScroller.bindStickStyle(this);
+      }
+    }
+  }
+
+  public void setBackgroundColor(String color) {
+    if (!TextUtils.isEmpty(color)) {
+      int colorInt = WXResourceUtils.getColor(color);
+      if (isRippleEnabled() && Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
+        mRippleBackground = prepareBackgroundRipple();
+        if (mRippleBackground != null) {
+          if (mBackgroundDrawable == null) {
+            WXViewUtils.setBackGround(mHost, mRippleBackground, this);
+          } else {
+            LayerDrawable layerDrawable = new LayerDrawable(new Drawable[]{mRippleBackground, mBackgroundDrawable});
+            WXViewUtils.setBackGround(mHost, layerDrawable, this);
+          }
+          return;
+        }
+      }
+      if (!(colorInt == Color.TRANSPARENT && mBackgroundDrawable == null)) {
+        getOrCreateBorder().setColor(colorInt);
+      }
+    }
+  }
+
+  private Drawable prepareBackgroundRipple() {
+    try {
+      if (getStyles() != null && getStyles().getPesudoResetStyles() != null) {
+        Map<String, Object> resetStyles = getStyles().getPesudoResetStyles();
+
+        Object bgColor = resetStyles.get(Constants.Name.BACKGROUND_COLOR);
+        int colorInt = Color.TRANSPARENT;
+        if (bgColor != null) {
+          colorInt = WXResourceUtils.getColor(bgColor.toString(), Color.TRANSPARENT);
+          if (colorInt == Color.TRANSPARENT) {
+            return null;
+          }
+        }
+
+        Object bg = resetStyles.get(Constants.Name.BACKGROUND_COLOR + Constants.PSEUDO.ACTIVE);
+        if (bg == null) {
+          return null;
+        }
+        int rippleColor = WXResourceUtils.getColor(bg.toString(), colorInt);
+        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
+          ColorStateList colorStateList = new ColorStateList(
+                  new int[][]{new int[]{}},
+                  new int[]{rippleColor});
+          return new RippleDrawable(colorStateList, new ColorDrawable(colorInt), null) {
+            @Override
+            @SuppressLint("CanvasSize")
+            public void draw(@NonNull Canvas canvas) {
+              if (mBackgroundDrawable != null) {
+                Path border = mBackgroundDrawable.getContentPath(new RectF(0, 0, canvas.getWidth(), canvas.getHeight()));
+                canvas.clipPath(border);
+              }
+              super.draw(canvas);
+            }
+          };
+        }
+      }
+    } catch (Throwable t) {
+      WXLogUtils.w("Exception on create ripple: ", t);
+    }
+    return null;
+  }
+
+  public void setBackgroundImage(@NonNull String bgImage) {
+    if ("".equals(bgImage.trim())) {
+      getOrCreateBorder().setImage(null);
+    } else {
+      Shader shader = WXResourceUtils.getShader(bgImage, getLayoutSize().getWidth(), getLayoutSize().getHeight());
+      getOrCreateBorder().setImage(shader);
+    }
+  }
+  private boolean shouldCancelHardwareAccelerate() {
+    IWXConfigAdapter adapter = WXSDKManager.getInstance().getWxConfigAdapter();
+    boolean cancel_hardware_accelerate = true;
+    if (adapter != null) {
+      try {
+        cancel_hardware_accelerate = Boolean.parseBoolean(adapter
+                .getConfig("android_weex_test_gpu",
+                        "cancel_hardware_accelerate",
+                        "true"));
+      }catch (Exception e){
+        WXLogUtils.e(WXLogUtils.getStackTrace(e));
+      }
+      WXLogUtils.i("cancel_hardware_accelerate : " + cancel_hardware_accelerate);
+    }
+    return cancel_hardware_accelerate;
+  }
+
+  public void setOpacity(float opacity) {
+    if (opacity >= 0 && opacity <= 1 && mHost.getAlpha() != opacity) {
+      int limit = WXRenderManager.getOpenGLRenderLimitValue();
+      if (isLayerTypeEnabled()) {
+        mHost.setLayerType(View.LAYER_TYPE_HARDWARE, null);
+      }
+      if(isLayerTypeEnabled() && shouldCancelHardwareAccelerate() && limit > 0 && (getLayoutHeight() > limit ||
+              getLayoutWidth() > limit)){
+        mHost.setLayerType(View.LAYER_TYPE_NONE,null);
+      }
+      mHost.setAlpha(opacity);
+    }
+  }
+
+  public void setBorderRadius(String key, float borderRadius) {
+    if (borderRadius >= 0) {
+      switch (key) {
+        case Constants.Name.BORDER_RADIUS:
+          getOrCreateBorder().setBorderRadius(
+              CORNER.ALL, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
+          break;
+        case Constants.Name.BORDER_TOP_LEFT_RADIUS:
+          getOrCreateBorder().setBorderRadius(CORNER.BORDER_TOP_LEFT, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
+          break;
+        case Constants.Name.BORDER_TOP_RIGHT_RADIUS:
+          getOrCreateBorder().setBorderRadius(CORNER.BORDER_TOP_RIGHT, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
+          break;
+        case Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS:
+          getOrCreateBorder().setBorderRadius(CORNER.BORDER_BOTTOM_RIGHT, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
+          break;
+        case Constants.Name.BORDER_BOTTOM_LEFT_RADIUS:
+          getOrCreateBorder().setBorderRadius(CORNER.BORDER_BOTTOM_LEFT, WXViewUtils.getRealSubPxByWidth(borderRadius, mInstance.getInstanceViewPortWidth()));
+          break;
+      }
+    }
+  }
+
+  public void setBorderWidth(String key, float borderWidth) {
+    if (borderWidth >= 0) {
+      switch (key) {
+        case Constants.Name.BORDER_WIDTH:
+          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.ALL, borderWidth);
+          break;
+        case Constants.Name.BORDER_TOP_WIDTH:
+          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.TOP, borderWidth);
+          break;
+        case Constants.Name.BORDER_RIGHT_WIDTH:
+          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.RIGHT, borderWidth);
+          break;
+        case Constants.Name.BORDER_BOTTOM_WIDTH:
+          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.BOTTOM, borderWidth);
+          break;
+        case Constants.Name.BORDER_LEFT_WIDTH:
+          getOrCreateBorder().setBorderWidth(CSSShorthand.EDGE.LEFT, borderWidth);
+          break;
+        default:
+          break;
+      }
+    }
+  }
+
+  public void setBorderStyle(String key, String borderStyle) {
+    if (!TextUtils.isEmpty(borderStyle)) {
+      switch (key) {
+        case Constants.Name.BORDER_STYLE:
+          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.ALL, borderStyle);
+          break;
+        case Constants.Name.BORDER_RIGHT_STYLE:
+          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.RIGHT, borderStyle);
+          break;
+        case Constants.Name.BORDER_BOTTOM_STYLE:
+          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.BOTTOM, borderStyle);
+          break;
+        case Constants.Name.BORDER_LEFT_STYLE:
+          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.LEFT, borderStyle);
+          break;
+        case Constants.Name.BORDER_TOP_STYLE:
+          getOrCreateBorder().setBorderStyle(CSSShorthand.EDGE.TOP, borderStyle);
+          break;
+      }
+    }
+  }
+
+  public void setBorderColor(String key, String borderColor) {
+    if (!TextUtils.isEmpty(borderColor)) {
+      int colorInt = WXResourceUtils.getColor(borderColor);
+      if (colorInt != Integer.MIN_VALUE) {
+        switch (key) {
+          case Constants.Name.BORDER_COLOR:
+            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.ALL, colorInt);
+            break;
+          case Constants.Name.BORDER_TOP_COLOR:
+            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.TOP, colorInt);
+            break;
+          case Constants.Name.BORDER_RIGHT_COLOR:
+            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.RIGHT, colorInt);
+            break;
+          case Constants.Name.BORDER_BOTTOM_COLOR:
+            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.BOTTOM, colorInt);
+            break;
+          case Constants.Name.BORDER_LEFT_COLOR:
+            getOrCreateBorder().setBorderColor(CSSShorthand.EDGE.LEFT, colorInt);
+            break;
+        }
+      }
+    }
+  }
+
+  public
+  @Nullable
+  String getVisibility() {
+    try {
+      return (String) getStyles().get(Constants.Name.VISIBILITY);
+    } catch (Exception e) {
+      return Constants.Value.VISIBLE;
+    }
+  }
+
+  public void setVisibility(String visibility) {
+    View view;
+    if ((view = getRealView()) != null) {
+      if (TextUtils.equals(visibility, Constants.Value.VISIBLE)) {
+        view.setVisibility(View.VISIBLE);
+      } else if (TextUtils.equals(visibility, Constants.Value.HIDDEN)) {
+        view.setVisibility(View.GONE);
+      }
+    }
+  }
+
+  /**
+   * This is an experimental feature for elevation of material design.
+   */
+  private void updateElevation() {
+    float elevation = getAttrs().getElevation(getInstance().getInstanceViewPortWidth());
+    if (!Float.isNaN(elevation)) {
+      ViewCompat.setElevation(getHostView(), elevation);
+    }
+  }
+
+  @Deprecated
+  public void registerActivityStateListener() {
+
+  }
+
+
+  /********************************
+   *  begin hook Activity life cycle callback
+   ********************************************************/
+  public void onActivityCreate() {
+
+  }
+
+  public void onActivityStart() {
+
+  }
+
+  public void onActivityPause() {
+
+  }
+
+  public void onActivityResume() {
+
+  }
+
+  public void onActivityStop() {
+
+  }
+
+  public void onActivityDestroy() {
+
+  }
+
+  public boolean onActivityBack() {
+    return false;
+  }
+
+  public void onActivityResult(int requestCode, int resultCode, Intent data) {
+
+  }
+
+  public boolean onCreateOptionsMenu(Menu menu) {
+    return false;
+  }
+
+  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
+
+  }
+
+  /********************************
+   *  end hook Activity life cycle callback
+   ********************************************************/
+  public void recycled() {
+    if (isFixed())
+      return;
+    clearBoxShadow();
+  }
+
+  public void destroy() {
+    ComponentObserver observer;
+    if ((observer = getInstance().getComponentObserver()) != null) {
+      observer.onPreDestory(this);
+    }
+
+    if (WXEnvironment.isApkDebugable() && !WXUtils.isUiThread()) {
+      throw new WXRuntimeException("[WXComponent] destroy can only be called in main thread");
+    }
+    if (mHost != null && mHost.getLayerType() == View.LAYER_TYPE_HARDWARE && isLayerTypeEnabled()) {
+      mHost.setLayerType(View.LAYER_TYPE_NONE, null);
+    }
+    removeAllEvent();
+    removeStickyStyle();
+
+    View view;
+    if (isFixed() && (view = getHostView()) != null) {
+      getInstance().removeFixedView(view);
+    }
+
+    if(contentBoxMeasurement!=null){
+      contentBoxMeasurement.destroy();
+      contentBoxMeasurement = null;
+    }
+    mIsDestroyed = true;
+    if(animations!=null) {
+      animations.clear();
+    }
+  }
+
+  public boolean isDestoryed() {
+    return mIsDestroyed;
+  }
+
+  /**
+   * Detach view from its component. Components,
+   * which have difference between getHostView and getRealView or have temp calculation results,
+   * must<strong> override</strong>  this method with their own implementation.
+   *
+   * @return the original View
+   */
+  public View detachViewAndClearPreInfo() {
+    View original = mHost;
+    mPreRealLeft = 0;
+    mPreRealRight = 0;
+    mPreRealWidth = 0;
+    mPreRealHeight = 0;
+    mPreRealTop = 0;
+//    mHost = null;
+    return original;
+  }
+
+  public void clearPreLayout() {
+    mPreRealLeft = 0;
+    mPreRealRight = 0;
+    mPreRealWidth = 0;
+    mPreRealHeight = 0;
+    mPreRealTop = 0;
+  }
+
+  /**
+   * This method computes user visible left-top point in view's coordinate.
+   * The default implementation uses the scrollX and scrollY of the view as the result,
+   * and put the value in the parameter pointer.
+   * Components with different computation algorithm
+   * <strong> should override </strong> this method.
+   *
+   * @param pointF the user visible left-top point in view's coordinate.
+   */
+  public void computeVisiblePointInViewCoordinate(PointF pointF) {
+    View view = getRealView();
+    pointF.set(view.getScrollX(), view.getScrollY());
+  }
+
+  public boolean containsGesture(WXGestureType WXGestureType) {
+    return mGestureType != null && mGestureType.contains(WXGestureType.toString());
+  }
+
+  public boolean containsEvent(String event) {
+    return getEvents().contains(event) || (mAppendEvents!=null && mAppendEvents.contains(event));
+  }
+
+  public void notifyAppearStateChange(String wxEventType, String direction) {
+    if (containsEvent(Constants.Event.APPEAR) || containsEvent(Constants.Event.DISAPPEAR)) {
+      Map<String, Object> params = new HashMap<>();
+      params.put("direction", direction);
+      fireEvent(wxEventType, params);
+    }
+  }
+
+  public boolean isUsing() {
+    return isUsing;
+  }
+
+  public void setUsing(boolean using) {
+    isUsing = using;
+  }
+
+  public void readyToRender() {
+    if (mParent != null && getInstance().isTrackComponent()) {
+      mParent.readyToRender();
+    }
+  }
+
+  public static class MeasureOutput {
+    public int width;
+    public int height;
+  }
+
+  /**
+   * Determine whether the current component needs to be placed in the real View tree
+   *
+   * @return false component add subview
+   */
+  public boolean isVirtualComponent() {
+    return mType == TYPE_VIRTUAL;
+  }
+
+  public void removeVirtualComponent() {
+  }
+
+  public int getType() {
+    return mType;
+  }
+
+  public boolean hasScrollParent(WXComponent component) {
+    if (component.getParent() == null) {
+      return true;
+    } else if (component.getParent() instanceof WXScroller) {
+      return false;
+    } else {
+      return hasScrollParent(component.getParent());
+    }
+  }
+
+  /**
+   * Called when property has empty value
+   *
+   * @param propName
+   */
+  @CheckResult
+  protected Object convertEmptyProperty(String propName, Object originalValue) {
+    switch (propName) {
+      case Constants.Name.BACKGROUND_COLOR:
+        return "transparent";
+      case Constants.Name.BORDER_RADIUS:
+      case Constants.Name.BORDER_BOTTOM_LEFT_RADIUS:
+      case Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS:
+      case Constants.Name.BORDER_TOP_LEFT_RADIUS:
+      case Constants.Name.BORDER_TOP_RIGHT_RADIUS:
+        return 0;
+      case Constants.Name.BORDER_WIDTH:
+      case Constants.Name.BORDER_TOP_WIDTH:
+      case Constants.Name.BORDER_LEFT_WIDTH:
+      case Constants.Name.BORDER_RIGHT_WIDTH:
+      case Constants.Name.BORDER_BOTTOM_WIDTH:
+        return 0;
+      case Constants.Name.BORDER_COLOR:
+      case Constants.Name.BORDER_TOP_COLOR:
+      case Constants.Name.BORDER_LEFT_COLOR:
+      case Constants.Name.BORDER_RIGHT_COLOR:
+      case Constants.Name.BORDER_BOTTOM_COLOR:
+        return "black";
+    }
+    return originalValue;
+  }
+
+  private void setActiveTouchListener() {
+    boolean hasActivePesudo = getStyles().getPesudoStyles().containsKey(Constants.PSEUDO.ACTIVE);
+    View view;
+    if (hasActivePesudo && (view = getRealView()) != null) {
+      boolean hasTouchConsumer = isConsumeTouch();
+      view.setOnTouchListener(new TouchActivePseudoListener(this, !hasTouchConsumer));
+    }
+  }
+
+  protected boolean isConsumeTouch() {
+    return (mHostClickListeners != null && mHostClickListeners.size() > 0) || mGesture != null;
+  }
+
+  @Override
+  public void updateActivePseudo(boolean isSet) {
+    setPseudoClassStatus(Constants.PSEUDO.ACTIVE, isSet);
+  }
+
+  /**
+   * @param clzName like ':active' or ':active:enabled'
+   * @param status
+   */
+  protected void setPseudoClassStatus(String clzName, boolean status) {
+    WXStyle styles = getStyles();
+    Map<String, Map<String, Object>> pesudoStyles = styles.getPesudoStyles();
+
+    if (pesudoStyles == null || pesudoStyles.size() == 0) {
+      return;
+    }
+    if(mPesudoStatus == null){
+      mPesudoStatus = new PesudoStatus();
+    }
+    Map<String, Object> resultStyles = mPesudoStatus.updateStatusAndGetUpdateStyles(
+            clzName,
+            status,
+            pesudoStyles,
+            styles.getPesudoResetStyles());
+
+    if (null != resultStyles) {
+      if (status) {
+        mPseudoResetGraphicSize = new GraphicSize(getLayoutSize().getWidth(), getLayoutSize().getHeight());
+        if (resultStyles.keySet().contains(Constants.Name.WIDTH)) {
+          getLayoutSize().setWidth(WXViewUtils.getRealPxByWidth(WXUtils.parseFloat(styles.getPesudoResetStyles().get(Constants.Name.WIDTH + Constants.PSEUDO.ACTIVE)), getViewPortWidth()));
+        } else if (resultStyles.keySet().contains(Constants.Name.HEIGHT)){
+          getLayoutSize().setHeight(WXViewUtils.getRealPxByWidth(WXUtils.parseFloat(styles.getPesudoResetStyles().get(Constants.Name.HEIGHT + Constants.PSEUDO.ACTIVE)), getViewPortWidth()));
+        }
+      } else {
+        if (null != mPseudoResetGraphicSize) {
+          setLayoutSize(mPseudoResetGraphicSize);
+        }
+      }
+    }
+
+    updateStyleByPesudo(resultStyles);
+  }
+
+  private void updateStyleByPesudo(Map<String, Object> styles) {
+    new GraphicActionUpdateStyle(getInstance(), getRef(), styles, getPadding(), getMargin(), getBorder(), true)
+            .executeActionOnRender();
+    if (getLayoutWidth() == 0 && getLayoutWidth() == 0) {
+    } else {
+      WXBridgeManager.getInstance().setStyleWidth(getInstanceId(), getRef(), getLayoutWidth());
+      WXBridgeManager.getInstance().setStyleHeight(getInstanceId(), getRef(), getLayoutHeight());
+//      WXBridgeManager.getInstance().calculateLayout(getInstanceId(), getRef(), false);
+    }
+  }
+
+  public int getStickyOffset() {
+    return mStickyOffset;
+  }
+
+  public boolean canRecycled() {
+    return (!isFixed() || !isSticky()) && getAttrs().canRecycled();
+  }
+
+  /**
+   * Sets the offset for the sticky
+   *
+   * @param stickyOffset child[y]-parent[y]
+   */
+  public void setStickyOffset(int stickyOffset) {
+    mStickyOffset = stickyOffset;
+  }
+
+  /**
+   * For now, this method respect the result of {@link WXSDKInstance#isLayerTypeEnabled()}
+   *
+   * @return Refer {@link WXSDKInstance#isLayerTypeEnabled()}
+   */
+  public boolean isLayerTypeEnabled() {
+    return getInstance().isLayerTypeEnabled();
+  }
+
+  /**
+   * Sets whether or not to relayout page during animation, default is false
+   */
+  public void setNeedLayoutOnAnimation(boolean need) {
+    this.mNeedLayoutOnAnimation = need;
+  }
+
+  /**
+   * Trigger a updateStyles invoke to relayout current page
+   */
+  public void notifyNativeSizeChanged(int w, int h) {
+    if (!mNeedLayoutOnAnimation) {
+      return;
+    }
+
+    final WXBridgeManager manager = WXBridgeManager.getInstance();
+    manager.setStyleWidth(getInstanceId(), getRef(), w);
+    manager.setStyleHeight(getInstanceId(), getRef(), h);
+  }
+
+  public static final int STATE_DOM_FINISH = 0;
+  public static final int STATE_UI_FINISH = 1;
+  public static final int STATE_ALL_FINISH = 2;
+  @IntDef({STATE_DOM_FINISH, STATE_UI_FINISH, STATE_ALL_FINISH})
+  @Retention(RetentionPolicy.SOURCE)
+  @Target(ElementType.PARAMETER)
+  public @interface RenderState {
+  }
+
+  @CallSuper
+  public void onRenderFinish(@RenderState int state) {
+    if (WXTracing.isAvailable()) {
+      double uiTime = Stopwatch.nanosToMillis(mTraceInfo.uiThreadNanos);
+      if (state == STATE_ALL_FINISH || state == STATE_DOM_FINISH) {
+        WXTracing.TraceEvent domEvent = WXTracing.newEvent("DomExecute", getInstanceId(), mTraceInfo.rootEventId);
+        domEvent.ph = "X";
+        domEvent.ts = mTraceInfo.domThreadStart;
+        domEvent.tname = "DOMThread";
+        domEvent.name = getComponentType();
+        domEvent.classname = getClass().getSimpleName();
+        if (getParent() != null) {
+          domEvent.parentRef = getParent().getRef();
+        }
+        domEvent.submit();
+      }
+
+      if (state == STATE_ALL_FINISH || state == STATE_UI_FINISH) {
+        if (mTraceInfo.uiThreadStart != -1) {
+          WXTracing.TraceEvent uiEvent = WXTracing.newEvent("UIExecute", getInstanceId(), mTraceInfo.rootEventId);
+          uiEvent.ph = "X";
+          uiEvent.duration = uiTime;
+          uiEvent.ts = mTraceInfo.uiThreadStart;
+          uiEvent.name = getComponentType();
+          uiEvent.classname = getClass().getSimpleName();
+          if (getParent() != null) {
+            uiEvent.parentRef = getParent().getRef();
+          }
+          uiEvent.submit();
+        } else {
+          if (WXEnvironment.isApkDebugable() && !isLazy()) {
+//            WXLogUtils.w("onRenderFinish", "createView() not called");
+          }
+        }
+      }
+    }
+  }
+
+  protected boolean isRippleEnabled() {
+    try {
+      Object obj = getAttrs().get(Constants.Name.RIPPLE_ENABLED);
+      return WXUtils.getBoolean(obj, false);
+    } catch (Throwable t) {
+      //ignore
+    }
+    return false;
+  }
+
+  public boolean isWaste() {
+    return waste;
+  }
+
+  /**
+   * mark node waste,
+   * if node is waster should hidden, and dom tree should allow not show
+   * */
+  public void setWaste(boolean waste) {
+    if(this.waste != waste){
+      this.waste = waste;
+      if(!WXBasicComponentType.RECYCLE_LIST.equals(getParent().getComponentType())){
+          NativeRenderObjectUtils.nativeRenderObjectChildWaste(getRenderObjectPtr(), waste);
+      }
+
+     if(waste){
+        //update dom not show, and put style to hidden
+        getStyles().put(Constants.Name.VISIBILITY, Constants.Value.HIDDEN);
+        //if component not init, mark lazy init when use, reduce view count
+        if(getHostView() == null){
+          if(!mLazy){
+            lazy(true);
+          }
+        }else{
+          getHostView().setVisibility(View.GONE);
+        }
+      }else{
+       getStyles().put(Constants.Name.VISIBILITY, Constants.Value.VISIBLE);
+        if(getHostView() == null){
+          if(mLazy) { // when parent is lazy just mark node lazy false
+            if(mParent != null && mParent.isLazy()){
+              lazy(false);
+            }else{
+              Statements.initLazyComponent(this, mParent);
+            }
+          }
+        }else{
+          getHostView().setVisibility(View.VISIBLE);
+        }
+      }
+    }
+  }
+
+
+  /** component uniquie key id in native for recycle-list,
+   *  should be unique for every native component differ with ref
+   *  */
+  public  String getViewTreeKey(){
+    if(mViewTreeKey == null){
+      if(getParent() == null){
+        mViewTreeKey = hashCode() + "_" + getRef();
+      }else{
+        mViewTreeKey = hashCode() + "_" + getRef() + "_" + getParent().indexOf(this);
+      }
+    }
+    return mViewTreeKey;
+  }
+
+  private String mViewTreeKey;
+
+  public WXTransition getTransition() {
+    return mTransition;
+  }
+
+  public void setTransition(WXTransition transition) {
+    this.mTransition = transition;
+  }
+
+  public void addAnimationForElement(Map<String, Object> animMap) {
+    if(animMap!=null && !animMap.isEmpty()){
+      if(animations == null){
+        animations = new ConcurrentLinkedQueue<>();
+      }
+      animations.add(new Pair<>(getRef(),animMap));
+    }
+  }
+
+  private void parseAnimation() {
+    if (null == animations) {
+      return;
+    }
+    for (final Pair<String, Map<String, Object>> pair : animations) {
+      if (!TextUtils.isEmpty(pair.first)) {
+        final WXAnimationBean animationBean = createAnimationBean(pair.first, pair.second);
+        if (animationBean != null) {
+          GraphicActionAnimation action = new GraphicActionAnimation(getInstance(), getRef(), animationBean);
+          action.executeAction();
+        }
+      }
+    }
+    animations.clear();
+  }
+
+
+  private WXAnimationBean createAnimationBean(String ref,Map<String, Object> style){
+    if (style != null) {
+      try {
+        Object transform = style.get(Constants.Name.TRANSFORM);
+        if (transform instanceof String && !TextUtils.isEmpty((String) transform)) {
+          String transformOrigin = (String) style.get(Constants.Name.TRANSFORM_ORIGIN);
+          WXAnimationBean animationBean = new WXAnimationBean();
+          int width = (int) getLayoutWidth();
+          int height = (int) getLayoutHeight();
+          animationBean.styles = new WXAnimationBean.Style();
+          animationBean.styles.init(transformOrigin, (String) transform, width, height,WXSDKManager.getInstanceViewPortWidth(getInstanceId()),
+                  getInstance());
+          return animationBean;
+        }
+      }catch (RuntimeException e){
+        WXLogUtils.e("", e);
+        return null;
+      }
+    }
+    return null;
+  }
+
+  /**
+   * node is lazy
+   * */
+  private boolean mLazy = false;
+
+  /***/
+  public void lazy(boolean lazy) {
+    mLazy = lazy;
+  }
+
+  public long getRenderObjectPtr(){
+    if(getBasicComponentData().isRenderPtrEmpty()){
+      getBasicComponentData().setRenderObjectPr(NativeRenderObjectUtils.nativeGetRenderObject(getInstanceId(), getRef()));
+    }
+    return getBasicComponentData().getRenderObjectPr();
+  }
+
+
+  public void updateNativeAttr(String key, Object value){
+    if(key == null){
+      return;
+    }
+    if(value == null){
+      value  = "";
+    }
+    getBasicComponentData().getAttrs().put(key, value);
+    NativeRenderObjectUtils.nativeUpdateRenderObjectAttr(getRenderObjectPtr(), key, value.toString());
+  }
+
+  public  void  nativeUpdateAttrs(Map<String, Object> dynamic){
+    Set<Map.Entry<String, Object>> entries = dynamic.entrySet();
+    /**
+     * diff attrs, see attrs has update, remove none update attrs
+     * */
+    Iterator<Map.Entry<String, Object>> iterator = entries.iterator();
+    while (iterator.hasNext()){
+      Map.Entry<String, Object> objectEntry = iterator.next();
+      if(objectEntry.getKey() == null){
+        continue;
+      }
+      updateNativeAttr(objectEntry.getKey(), objectEntry.getValue());
+    }
+  }
+
+
+  public void updateNativeStyle(String key, Object value){
+    if(key == null){
+      return;
+    }
+    if(value == null){
+      value  = "";
+    }
+    getBasicComponentData().getStyles().put(key, value);
+    NativeRenderObjectUtils.nativeUpdateRenderObjectStyle(getRenderObjectPtr(), key, value.toString());
+  }
+
+  public  void  updateNativeStyles(Map<String, Object> dynamic){
+    Set<Map.Entry<String, Object>> entries = dynamic.entrySet();
+    /**
+     * diff attrs, see attrs has update, remove none update attrs
+     * */
+    Iterator<Map.Entry<String, Object>> iterator = entries.iterator();
+    while (iterator.hasNext()){
+      Map.Entry<String, Object> objectEntry = iterator.next();
+      if(objectEntry.getKey() == null){
+        continue;
+      }
+      updateNativeStyle(objectEntry.getKey(), objectEntry.getValue());
+    }
+  }
+
+  public void addLayerOverFlowListener(String ref) {
+    if (getInstance() != null)
+      getInstance().addLayerOverFlowListener(ref);
+  }
+
+  public void removeLayerOverFlowListener(String ref) {
+    if (getInstance() != null)
+      getInstance().removeLayerOverFlowListener(ref);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponentFactory.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponentFactory.java
new file mode 100644
index 0000000..7a4290c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponentFactory.java
@@ -0,0 +1,67 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.text.TextUtils;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.ui.IFComponentHolder;
+import org.apache.weex.ui.WXComponentRegistry;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+
+/**
+ * Component factory
+ */
+public class WXComponentFactory {
+
+  public static WXComponent newInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    if (instance == null || TextUtils.isEmpty(basicComponentData.mComponentType)) {
+      return null;
+    }
+
+    IFComponentHolder holder = WXComponentRegistry.getComponent(basicComponentData.mComponentType);
+    if (holder == null) {
+      if (WXEnvironment.isApkDebugable()) {
+        String tag = "WXComponentFactory error type:[" +
+                basicComponentData.mComponentType + "]" + " class not found";
+        WXLogUtils.e(tag);
+      }
+      //For compatible reason of JS framework, unregistered type will be treated as container.
+      holder = WXComponentRegistry.getComponent(WXBasicComponentType.CONTAINER);
+      if (holder == null) {
+        WXExceptionUtils.commitCriticalExceptionRT(instance.getInstanceId(),
+                WXErrorCode.WX_RENDER_ERR_COMPONENT_NOT_REGISTER, "createComponent",
+                basicComponentData.mComponentType + " not registered", null);
+        return null;
+      }
+    }
+
+    try {
+      return holder.createInstance(instance, parent, basicComponentData);
+    } catch (Throwable e) {
+      WXLogUtils.e("WXComponentFactory Exception type:[" + basicComponentData.mComponentType + "] ", e);
+    }
+
+    return null;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponentProp.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponentProp.java
new file mode 100644
index 0000000..d2a8fbf
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXComponentProp.java
@@ -0,0 +1,31 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.METHOD)
+public @interface WXComponentProp {
+
+  String name();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXDiv.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXDiv.java
new file mode 100644
index 0000000..e22acd7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXDiv.java
@@ -0,0 +1,122 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.flat.FlatComponent;
+import org.apache.weex.ui.flat.WidgetContainer;
+import org.apache.weex.ui.flat.widget.WidgetGroup;
+import org.apache.weex.ui.view.WXFrameLayout;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.LinkedList;
+
+/**
+ * div component
+ */
+@Component(lazyload = false)
+public class WXDiv extends WidgetContainer<WXFrameLayout> implements FlatComponent<WidgetGroup> {
+
+  private WidgetGroup mWidgetGroup;
+
+  public static class Ceator implements ComponentCreator {
+    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+      return new WXDiv(instance, parent, basicComponentData);
+    }
+  }
+
+  @Deprecated
+  public WXDiv(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, basicComponentData);
+  }
+
+  public WXDiv(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  @Override
+  protected WXFrameLayout initComponentHostView(@NonNull Context context) {
+    WXFrameLayout frameLayout = new WXFrameLayout(context);
+    frameLayout.holdComponent(this);
+    return frameLayout;
+  }
+
+  @Override
+  public boolean promoteToView(boolean checkAncestor) {
+    if (null != getInstance().getFlatUIContext()) {
+      return !intendToBeFlatContainer() ||
+            getInstance().getFlatUIContext().promoteToView(this, checkAncestor, WXDiv.class);
+    }
+    return false;
+  }
+
+  /**
+   * Create View tree there. Either this method or {@link #createViewImpl()} get called.
+   * If this object will be promoted to view, then getOrCreateFlatWidget() should never be called.
+   */
+  @Override
+  @NonNull
+  public WidgetGroup getOrCreateFlatWidget() {
+    if (mWidgetGroup == null) {
+      mWidgetGroup = new WidgetGroup(getInstance().getFlatUIContext());
+      for (int i = 0; i < getChildCount(); i++) {
+        createChildViewAt(i);
+      }
+      mountFlatGUI();
+    }
+    return mWidgetGroup;
+  }
+
+  @Override
+  protected void mountFlatGUI() {
+    if(widgets == null){
+      widgets = new LinkedList<>();
+    }
+    if (promoteToView(true)) {
+      if(getHostView()!=null) {
+        getHostView().mountFlatGUI(widgets);
+      }
+    } else {
+      mWidgetGroup.replaceAll(widgets);
+    }
+  }
+
+  @Override
+  public void unmountFlatGUI() {
+    if (getHostView() != null) {
+      getHostView().unmountFlatGUI();
+    }
+  }
+
+  @Override
+  public boolean intendToBeFlatContainer() {
+    return getInstance().getFlatUIContext().isFlatUIEnabled(this) && WXDiv.class.equals(getClass());
+  }
+
+  @Override
+  public boolean isVirtualComponent() {
+    return !promoteToView(true);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXEmbed.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXEmbed.java
new file mode 100644
index 0000000..2687095
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXEmbed.java
@@ -0,0 +1,646 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.annotation.SuppressLint;
+import android.text.TextUtils;
+import android.view.Gravity;
+import android.view.View;
+import android.view.ViewGroup;
+import android.webkit.WebView;
+import android.widget.FrameLayout;
+import android.widget.ImageView;
+
+import org.apache.weex.R;
+import org.apache.weex.IWXRenderListener;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.OnWXScrollListener;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXRenderStrategy;
+import org.apache.weex.instance.InstanceOnFireEventInterceptor;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.ArrayDeque;
+import java.util.Comparator;
+import java.util.Map;
+import java.util.PriorityQueue;
+import java.util.Queue;
+import org.apache.weex.WXSDKInstance.OnInstanceVisibleListener;
+
+@Component(lazyload = false)
+public class WXEmbed extends WXDiv implements OnInstanceVisibleListener,NestedContainer {
+
+  public static final  String STRATEGY_NONE =  "none";
+  public static final  String STRATEGY_NORMAL =  "normal";
+  public static final  String STRATEGY_HIGH =  "high";
+
+
+  public static final  String PRIORITY_LOW =  "low";
+  public static final  String PRIORITY_NORMAL =  "normal";
+  public static final  String PRIORITY_HIGH =  "high";
+
+  public static final String ITEM_ID = "itemId";
+
+  private String src;
+  protected WXSDKInstance mNestedInstance;
+  private static int ERROR_IMG_WIDTH = (int) WXViewUtils.getRealPxByWidth(270,750);
+  private static int ERROR_IMG_HEIGHT = (int) WXViewUtils.getRealPxByWidth(260,750);
+
+  private boolean mIsVisible = true;
+  private EmbedRenderListener mListener;
+  private EmbedInstanceOnScrollFireEventInterceptor mInstanceOnScrollFireEventInterceptor;
+
+
+  private String priority = PRIORITY_NORMAL;
+
+  private String strategy = "normal";  //none, normal, high(ignore priority)
+
+  private long hiddenTime;
+
+
+
+  public interface EmbedManager {
+    WXEmbed getEmbed(String itemId);
+    void putEmbed(String itemId,WXEmbed comp);
+  }
+
+  public static class FailToH5Listener extends ClickToReloadListener {
+    @SuppressLint("SetJavaScriptEnabled")
+    @Override
+    public void onException(NestedContainer comp, String errCode, String msg) {
+      //downgrade embed
+      if( errCode != null && comp instanceof WXEmbed && errCode.startsWith("1|")) {
+        ViewGroup container = comp.getViewContainer();
+        WebView webView = new WebView(container.getContext());
+        ViewGroup.LayoutParams params = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
+        webView.setLayoutParams(params);
+        webView.getSettings().setJavaScriptEnabled(true);
+
+        //WebView Remote Code Execution Vulnerability
+        webView.removeJavascriptInterface("searchBoxJavaBridge_");
+        webView.removeJavascriptInterface("accessibility");
+        webView.removeJavascriptInterface("accessibilityTraversal");
+        webView.getSettings().setSavePassword(false);
+
+        container.removeAllViews();
+        container.addView(webView);
+        webView.loadUrl(((WXEmbed) comp).src);
+      }else{
+        super.onException(comp,errCode,msg);
+      }
+    }
+  }
+
+  /**
+   * Default event listener.
+   */
+  public static class ClickToReloadListener implements OnNestedInstanceEventListener {
+    @Override
+    public void onException(NestedContainer container, String errCode, String msg) {
+      if (TextUtils.equals(errCode, WXErrorCode.
+              WX_DEGRAD_ERR_NETWORK_BUNDLE_DOWNLOAD_FAILED.getErrorCode()) && container instanceof WXEmbed) {
+        final WXEmbed comp = ((WXEmbed)container);
+        final ImageView imageView = new ImageView(comp.getContext());
+        imageView.setImageResource(R.drawable.weex_error);
+        FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(ERROR_IMG_WIDTH, ERROR_IMG_HEIGHT);
+        layoutParams.gravity = Gravity.CENTER;
+        imageView.setLayoutParams(layoutParams);
+        imageView.setScaleType(ImageView.ScaleType.FIT_XY);
+        imageView.setAdjustViewBounds(true);
+        imageView.setOnClickListener(new View.OnClickListener() {
+          @Override
+          public void onClick(View v) {
+            imageView.setOnClickListener(null);
+            imageView.setEnabled(false);
+            comp.loadContent();
+          }
+        });
+        FrameLayout hostView = comp.getHostView();
+        hostView.removeAllViews();
+        hostView.addView(imageView);
+        WXLogUtils.e("WXEmbed", "NetWork failure :" + errCode + ",\n error message :" + msg);
+      }
+    }
+
+    @Override
+    public boolean onPreCreate(NestedContainer comp, String src) {
+      return true;
+    }
+
+    @Override
+    public String transformUrl(String origin) {
+      return origin;
+    }
+
+    @Override
+    public void onCreated(NestedContainer comp, WXSDKInstance nestedInstance) {
+
+    }
+  }
+
+  static class EmbedRenderListener implements IWXRenderListener {
+    WXEmbed mComponent;
+    OnNestedInstanceEventListener mEventListener;
+
+    EmbedRenderListener(WXEmbed comp) {
+      mComponent = comp;
+      mEventListener = new ClickToReloadListener();
+    }
+
+    @Override
+    public void onViewCreated(WXSDKInstance instance, View view) {
+      FrameLayout hostView = mComponent.getHostView();
+      hostView.removeAllViews();
+      hostView.addView(view);
+    }
+
+    @Override
+    public void onRenderSuccess(WXSDKInstance instance, int width, int height) {
+
+    }
+
+    @Override
+    public void onRefreshSuccess(WXSDKInstance instance, int width, int height) {
+
+    }
+
+    @Override
+    public void onException(WXSDKInstance instance, String errCode, String msg) {
+      if (mEventListener != null) {
+        mEventListener.onException(mComponent, errCode, msg);
+      }
+    }
+  }
+
+  @Deprecated
+  public WXEmbed(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, basicComponentData);
+  }
+
+  public WXEmbed(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+    mListener = new EmbedRenderListener(this);
+    mInstanceOnScrollFireEventInterceptor = new EmbedInstanceOnScrollFireEventInterceptor(this);
+
+    ERROR_IMG_WIDTH = (int) WXViewUtils.getRealPxByWidth(270, instance.getInstanceViewPortWidth());
+    ERROR_IMG_HEIGHT = (int) WXViewUtils.getRealPxByWidth(260, instance.getInstanceViewPortWidth());
+    if (instance instanceof EmbedManager) {
+      Object itemId = getAttrs().get(ITEM_ID);
+      if (itemId != null) {
+        ((EmbedManager) instance).putEmbed(itemId.toString(), this);
+      }
+    }
+    this.priority = WXUtils.getString(getAttrs().get(Constants.Name.PRIORITY), PRIORITY_NORMAL);
+    this.strategy = WXUtils.getString(getAttrs().get(Constants.Name.STRATEGY), STRATEGY_NONE);
+    instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_EMBED_COUNT,1);
+  }
+
+  @Override
+  public void setOnNestEventListener(OnNestedInstanceEventListener listener){
+    mListener.mEventListener = listener;
+  }
+
+  @Override
+  public ViewGroup getViewContainer() {
+    return getHostView();
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.SRC:
+        String src = WXUtils.getString(param, null);
+        if (src != null)
+          setSrc(src);
+        return true;
+      case Constants.Name.PRIORITY:
+        String priority = WXUtils.getString(param, null);
+        if (priority != null) {
+          setPriority(priority);
+        }
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @Override
+  public void renderNewURL(String url) {
+    src = url;
+    loadContent();
+  }
+
+  @Override
+  public void reload() {
+    if (!TextUtils.isEmpty(src)) {
+      loadContent();
+    }
+  }
+
+  public String getOriginUrl() {
+    return originUrl;
+  }
+
+  public void setOriginUrl(String originUrl) {
+    this.originUrl = originUrl;
+  }
+
+  private String originUrl;
+
+
+  @Override
+  public void addEvent(String type) {
+    super.addEvent(type);
+    if(Constants.Event.SCROLL_START.equals(type)){
+      mInstanceOnScrollFireEventInterceptor.addInterceptEvent(type);
+    }else if(Constants.Event.SCROLL_END.equals(type)){
+      mInstanceOnScrollFireEventInterceptor.addInterceptEvent(type);
+    }else if(Constants.Event.SCROLL.equals(type)){
+      mInstanceOnScrollFireEventInterceptor.addInterceptEvent(type);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.SRC)
+  public void setSrc(String src) {
+    originUrl=src;
+    this.src = src;
+    if (mNestedInstance != null) {
+      mNestedInstance.destroy();
+      mNestedInstance = null;
+    }
+    if (mIsVisible && !TextUtils.isEmpty(this.src)) {
+      loadContent();
+    }
+  }
+  public String getSrc() {
+    return src;
+  }
+
+
+  @WXComponentProp(name = Constants.Name.PRIORITY)
+  public void setPriority(String priority) {
+    if(TextUtils.isEmpty(priority)){
+      return;
+    }
+    this.priority = priority;
+  }
+
+  /**
+   * Load embed content, default behavior is create a nested instance.
+   */
+  protected void loadContent(){
+    if(mNestedInstance != null){
+      mNestedInstance.destroy();
+    }
+    mNestedInstance = createInstance();
+    if(mListener != null && mListener.mEventListener != null){
+      if(!mListener.mEventListener.onPreCreate(this,src)){
+        //cancel render
+        mListener.mEventListener.onCreated(this, mNestedInstance);
+      }
+    }
+  }
+
+  private static final int getLevel(WXEmbed embed){
+    String priority = embed.priority;
+    String strategy = embed.strategy;
+    int level  = 5;
+    if(!STRATEGY_HIGH.equals(strategy)) {
+      if (TextUtils.equals(priority, PRIORITY_LOW)) {
+        level = 0;
+      } else if (TextUtils.equals(priority, PRIORITY_HIGH)) {
+        level = 10;
+      }
+    }
+    return  level;
+  }
+
+  private WXSDKInstance createInstance() {
+    WXSDKInstance sdkInstance = getInstance().createNestedInstance(this);
+    sdkInstance.setParentInstance(getInstance());
+    boolean needsAdd = !getAttrs().containsKey("disableInstanceVisibleListener");
+    if(needsAdd){ //prevent switch off fire viewappear event twice
+        getInstance().addOnInstanceVisibleListener(this);
+    }
+    sdkInstance.registerRenderListener(mListener);
+    mInstanceOnScrollFireEventInterceptor.resetFirstLaterScroller();;
+    sdkInstance.addInstanceOnFireEventInterceptor(mInstanceOnScrollFireEventInterceptor);
+    sdkInstance.registerOnWXScrollListener(mInstanceOnScrollFireEventInterceptor);
+
+    String url=src;
+    if(mListener != null && mListener.mEventListener != null){
+      url=mListener.mEventListener.transformUrl(src);
+      if(!mListener.mEventListener.onPreCreate(this,src)){
+        //cancel render
+        return null;
+      }
+    }
+
+    if(TextUtils.isEmpty(url)){
+      mListener.mEventListener.onException(this,
+              WXErrorCode.WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR.getErrorCode(),
+              WXErrorCode.WX_DEGRAD_ERR_BUNDLE_CONTENTTYPE_ERROR.getErrorMsg() + "!!wx embed src url is null"
+      );
+      return sdkInstance;
+    }
+    sdkInstance.setContainerInfo(WXInstanceApm.KEY_PAGE_PROPERTIES_INSTANCE_TYPE,"embed");
+    sdkInstance.setContainerInfo(WXInstanceApm.KEY_PAGE_PROPERTIES_PARENT_PAGE,getInstance().getWXPerformance().pageName);
+    sdkInstance.renderByUrl(url,
+            url,
+            null, null,
+            WXRenderStrategy.APPEND_ASYNC);
+
+    return sdkInstance;
+  }
+
+  @Override
+  public void setVisibility(String visibility) {
+    super.setVisibility(visibility);
+    boolean visible = TextUtils.equals(visibility, Constants.Value.VISIBLE);
+    if(mIsVisible != visible){
+
+      if (!TextUtils.isEmpty(src) && visible) {
+        if (mNestedInstance == null) {
+          loadContent();
+        } else {
+          mNestedInstance.onViewAppear();
+        }
+      }
+
+      if (!visible) {
+        if (mNestedInstance != null) {
+          mNestedInstance.onViewDisappear();
+        }
+      }
+      mIsVisible = visible;
+      doAutoEmbedMemoryStrategy();
+    }
+  }
+
+  @Override
+  public void destroy() {
+    super.destroy();
+    destoryNestInstance();
+    src = null;
+    if (getInstance() != null) {
+      getInstance().removeOnInstanceVisibleListener(this);
+    }
+  }
+
+  private void  doAutoEmbedMemoryStrategy(){
+    /**
+     * auto manage embed amount in current instance, save memory
+     * */
+    if(!STRATEGY_NONE.equals(this.strategy)){
+      if(!mIsVisible && mNestedInstance != null){
+        if(PRIORITY_LOW.equals(this.priority)){
+          destoryNestInstance();
+        }else{
+          if(getInstance().hiddenEmbeds == null){ // low is in front, when priority is same, hidden time pre in first
+            getInstance().hiddenEmbeds = new PriorityQueue<>(8, new Comparator<WXEmbed>() {
+              @Override
+              public int compare(WXEmbed o1, WXEmbed o2) {
+                int level =  getLevel(o1) - getLevel(o2);
+                if(level != 0){
+                  return  level;
+                }
+                return (int) (o1.hiddenTime - o2.hiddenTime);
+              }
+            });
+          }
+          //getInstance().hiddenEmbeds.remove(this);
+          if(!getInstance().hiddenEmbeds.contains(this)) {
+            this.hiddenTime = System.currentTimeMillis();
+            getInstance().hiddenEmbeds.add(this);
+          }
+          if(getInstance().hiddenEmbeds != null && getInstance().getMaxHiddenEmbedsNum() >= 0){
+            while (getInstance().hiddenEmbeds.size() > getInstance().getMaxHiddenEmbedsNum()){
+              WXEmbed embed = getInstance().hiddenEmbeds.poll();
+              if(embed.mIsVisible){
+                continue;
+              }
+              if(embed != null) {
+                embed.destoryNestInstance();
+              }
+            }
+          }
+        }
+      }
+      if(mIsVisible && mNestedInstance != null){
+        if(getInstance().hiddenEmbeds != null && getInstance().hiddenEmbeds.contains(this)){
+          getInstance().hiddenEmbeds.remove(this);
+        }
+      }
+    }
+
+  }
+
+  @Override
+  public void onAppear() {
+    //appear event from root instance will not trigger visibility change
+    if(mIsVisible && mNestedInstance != null){
+      WXComponent comp = mNestedInstance.getRootComponent();
+      if(comp != null)
+        comp.fireEvent(Constants.Event.VIEWAPPEAR);
+    }
+  }
+
+  @Override
+  public void onDisappear() {
+    //appear event from root instance will not trigger visibility change
+    if(mIsVisible && mNestedInstance != null){
+      WXComponent comp = mNestedInstance.getRootComponent();
+      if(comp != null)
+        comp.fireEvent(Constants.Event.VIEWDISAPPEAR);
+    }
+  }
+
+  @Override
+  public void onActivityStart() {
+    super.onActivityStart();
+    if (mNestedInstance != null) {
+      mNestedInstance.onActivityStart();
+    }
+  }
+
+  @Override
+  public void onActivityResume() {
+    super.onActivityResume();
+    if (mNestedInstance != null) {
+      mNestedInstance.onActivityResume();
+    }
+  }
+
+  @Override
+  public void onActivityPause() {
+    super.onActivityPause();
+    if (mNestedInstance != null) {
+      mNestedInstance.onActivityPause();
+    }
+  }
+
+  @Override
+  public void onActivityStop() {
+    super.onActivityStop();
+    if (mNestedInstance != null) {
+      mNestedInstance.onActivityStop();
+    }
+  }
+
+  @Override
+  public void onActivityDestroy() {
+    super.onActivityDestroy();
+    if (mNestedInstance != null) {
+      mNestedInstance.onActivityDestroy();
+    }
+  }
+
+  public void setStrategy(String strategy) {
+    this.strategy = strategy;
+  }
+
+  private void destoryNestInstance(){
+    if(getInstance().hiddenEmbeds != null && getInstance().hiddenEmbeds.contains(this)){
+      getInstance().hiddenEmbeds.remove(this);
+    }
+    if (mNestedInstance != null) {
+      mNestedInstance.destroy();
+      mNestedInstance = null;
+    }
+    if(WXEnvironment.isApkDebugable()){
+      WXLogUtils.w("WXEmbed destoryNestInstance priority " + priority + " index " + getAttrs().get("index")
+              + "  " + hiddenTime  + " embeds size " + (getInstance().hiddenEmbeds == null ?  0 : getInstance().hiddenEmbeds.size())
+              + " strategy " + this.strategy);
+    }
+  }
+
+  @Override
+  public void addLayerOverFlowListener(String ref) {
+    if (mNestedInstance != null)
+      mNestedInstance.addLayerOverFlowListener(getRef());
+  }
+
+  @Override
+  public void removeLayerOverFlowListener(String ref) {
+    if (mNestedInstance != null)
+      mNestedInstance.removeLayerOverFlowListener(ref);
+  }
+
+  static class EmbedInstanceOnScrollFireEventInterceptor extends
+      InstanceOnFireEventInterceptor implements OnWXScrollListener {
+
+    private WXEmbed mEmbed;
+    private WXComponent firstLayerScroller;
+
+    public EmbedInstanceOnScrollFireEventInterceptor(WXEmbed embed) {
+      this.mEmbed = embed;
+    }
+
+    public void resetFirstLaterScroller(){
+      firstLayerScroller = null;
+    }
+
+    @Override
+    public void onFireEvent(String instanceId, String elementRef, String type, Map<String, Object> params, Map<String, Object> domChanges) {
+      if(mEmbed == null
+              || mEmbed.mNestedInstance == null
+              || !mEmbed.mNestedInstance.getInstanceId().equals(instanceId)){
+        return;
+      }
+      if(firstLayerScroller == null){
+          initFirstLayerScroller();
+      }
+      if(firstLayerScroller == null){
+        return;
+      }
+      if(firstLayerScroller.getRef().equals(elementRef)){
+         mEmbed.getInstance().fireEvent(mEmbed.getRef(), type, params, domChanges);
+      }
+    }
+
+
+    private void initFirstLayerScroller(){
+      if(firstLayerScroller == null){
+          firstLayerScroller = findFirstLayerScroller();
+          if(firstLayerScroller != null){
+            for(String event : getListenEvents()){
+              if(!firstLayerScroller.containsEvent(event)){
+                  firstLayerScroller.getEvents().add(event);
+                  firstLayerScroller.addEvent(event);
+              }
+            }
+          }
+      }
+    }
+
+    /**
+     * get first layer scroller ref
+     * */
+    private WXComponent findFirstLayerScroller(){
+         if(mEmbed.mNestedInstance == null){
+           return null;
+         }
+         WXComponent rootComponent = mEmbed.mNestedInstance.getRootComponent();
+        if(rootComponent instanceof  Scrollable){
+          return rootComponent;
+        }
+        Queue<WXComponent> queues = new ArrayDeque<>();
+        queues.offer(rootComponent);
+        while (!queues.isEmpty()){
+             WXComponent component = queues.poll();
+             if(component == null){
+               break;
+             }
+             if(component instanceof  Scrollable){
+                return  component;
+             }
+             if(component instanceof WXVContainer){
+               WXVContainer container = (WXVContainer) component;
+               for(int i=0; i<container.getChildCount(); i++){
+                  queues.offer(container.getChild(i));
+               }
+             }
+        }
+        return null;
+    }
+
+
+    @Override
+    public void onScrolled(View view, int x, int y) {
+      if(firstLayerScroller != null){
+        return;
+      }
+      if(getListenEvents().size() > 0){
+        initFirstLayerScroller();
+      }
+    }
+
+    @Override
+    public void onScrollStateChanged(View view, int x, int y, int newState) {
+
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXHeader.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXHeader.java
new file mode 100644
index 0000000..4172cfa
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXHeader.java
@@ -0,0 +1,57 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.list.WXCell;
+
+/**
+ * The same as sticky cell
+ */
+@Component(lazyload = false)
+public class WXHeader extends WXCell {
+
+  @Deprecated
+  public WXHeader(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+  public WXHeader(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
+    super(instance, parent, lazy, basicComponentData);
+    String parantType = parent.getComponentType();
+    if(WXBasicComponentType.LIST.equals(parantType)
+            || WXBasicComponentType.RECYCLE_LIST.equals(parantType)){
+      getStyles().put(Constants.Name.POSITION, Constants.Value.STICKY);
+      setSticky(Constants.Value.STICKY);
+    }
+  }
+
+  @Override
+  public boolean isLazy() {
+    return false;
+  }
+
+  @Override
+  public boolean canRecycled() {
+    return !isSticky();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXImage.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXImage.java
new file mode 100644
index 0000000..dbb70d3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXImage.java
@@ -0,0 +1,549 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import org.apache.weex.dom.WXImageQuality;
+
+import java.lang.ref.WeakReference;
+import java.lang.reflect.InvocationTargetException;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+
+import android.Manifest;
+import android.app.Activity;
+import android.content.Context;
+import android.content.pm.PackageManager;
+import android.graphics.RectF;
+import android.graphics.drawable.Drawable;
+import android.net.Uri;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v4.app.ActivityCompat;
+import android.support.v4.content.ContextCompat;
+import android.text.TextUtils;
+import android.view.ViewGroup;
+import android.widget.ImageView;
+import android.widget.ImageView.ScaleType;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.adapter.IWXImgLoaderAdapter;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXImageSharpen;
+import org.apache.weex.common.WXImageStrategy;
+import org.apache.weex.common.WXRuntimeException;
+import org.apache.weex.performance.WXAnalyzerDataTransfer;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXImageView;
+import org.apache.weex.ui.view.border.BorderDrawable;
+import org.apache.weex.utils.ImageDrawable;
+import org.apache.weex.utils.ImgURIUtil;
+import org.apache.weex.utils.SingleFunctionParser;
+import org.apache.weex.utils.WXDomUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewToImageUtil;
+import org.apache.weex.utils.WXViewUtils;
+
+/**
+ * Image component
+ */
+@Component(lazyload = false)
+public class WXImage extends WXComponent<ImageView> {
+
+  public static final String SUCCEED = "success";
+  public static final String ERRORDESC = "errorDesc";
+  private static final int WRITE_EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE = 0x2;
+
+  private String mSrc;
+  private int mBlurRadius;
+  private boolean mAutoRecycle = true;
+
+  private static SingleFunctionParser.FlatMapper<Integer> BLUR_RADIUS_MAPPER = new SingleFunctionParser.FlatMapper<Integer>() {
+    @Override
+    public Integer map(String raw) {
+      return WXUtils.getInteger(raw,0);
+    }
+  };
+
+  public static class Creator implements ComponentCreator {
+    @Override
+    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+      return new WXImage(instance, parent, basicComponentData);
+    }
+  }
+
+  @Deprecated
+  public WXImage(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, basicComponentData);
+  }
+
+  public WXImage(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  @Override
+  protected ImageView initComponentHostView(@NonNull Context context) {
+    WXImageView view = new WXImageView(context);
+    view.setScaleType(ScaleType.FIT_XY);
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+      view.setCropToPadding(true);
+    }
+    view.holdComponent(this);
+    return view;
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.RESIZE_MODE:
+        String resizeMode = WXUtils.getString(param, null);
+        if (resizeMode != null) { setResizeMode(resizeMode); }
+        return true;
+      case Constants.Name.RESIZE:
+        String resize = WXUtils.getString(param, null);
+        if (resize != null) { setResize(resize); }
+        return true;
+      case Constants.Name.SRC:
+        String src = WXUtils.getString(param, null);
+        if (src != null) { setSrc(src); }
+        return true;
+      case Constants.Name.IMAGE_QUALITY:
+        return true;
+      case Constants.Name.AUTO_RECYCLE:
+        mAutoRecycle = WXUtils.getBoolean(param, mAutoRecycle);
+        if (!mAutoRecycle && null != getInstance()){
+          getInstance().getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_IMG_UN_RECYCLE_NUM,1);
+        }
+        return true;
+      case Constants.Name.FILTER:
+        int blurRadius = 0;
+        if (param != null && param instanceof String) {
+          blurRadius = parseBlurRadius((String)param);
+        }
+        if (!TextUtils.isEmpty(this.mSrc)) {
+          setBlurRadius(this.mSrc, blurRadius);
+        }
+        return true;
+      default:
+        return super.setProperty(key, param);
+    }
+  }
+
+  @Override
+  public void refreshData(WXComponent component) {
+    super.refreshData(component);
+    if (component instanceof WXImage) {
+      setSrc(component.getAttrs().getImageSrc());
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.RESIZE_MODE)
+  public void setResizeMode(String resizeMode) {
+    (getHostView()).setScaleType(getResizeMode(resizeMode));
+    getHostView().setImageDrawable(getHostView().getDrawable());
+  }
+
+  @RestrictTo(Scope.LIBRARY_GROUP)
+  protected ScaleType getResizeMode(String resizeMode) {
+    ScaleType scaleType = ScaleType.FIT_XY;
+    if (TextUtils.isEmpty(resizeMode)) {
+      return scaleType;
+    }
+
+    switch (resizeMode) {
+      case "cover":
+        scaleType = ScaleType.CENTER_CROP;
+        break;
+      case "contain":
+        scaleType = ScaleType.FIT_CENTER;
+        break;
+      case "stretch":
+        scaleType = ScaleType.FIT_XY;
+        break;
+      default:
+        break;
+    }
+    return scaleType;
+  }
+
+  @WXComponentProp(name = Constants.Name.RESIZE)
+  public void setResize(String resize) {
+    setResizeMode(resize);
+  }
+
+  /**
+   * Process local scheme, load drawable.
+   * @param rewrited
+   */
+  private void setLocalSrc(Uri rewrited) {
+    ImageView imageView;
+    Drawable localDrawable = ImgURIUtil.getDrawableFromLoaclSrc(getContext(), rewrited);
+    if (localDrawable != null && (imageView = getHostView()) != null) {
+      imageView.setImageDrawable(localDrawable);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.SRC)
+  public void setSrc(String src) {
+
+    if (getInstance().getImageNetworkHandler() != null) {
+      String localUrl = getInstance().getImageNetworkHandler().fetchLocal(src);
+      if (!TextUtils.isEmpty(localUrl)) {
+        src = localUrl;
+      }
+    }
+
+    if (src == null) {
+      return;
+    }
+
+    ImageView image = getHostView();
+    if("".equals(src) && image != null){
+      image.setImageDrawable(null);
+      return;
+    }
+
+    if(image != null){
+      if(image.getDrawable() != null && !TextUtils.equals(mSrc, src)){
+        image.setImageDrawable(null);
+      }
+    }
+
+
+    this.mSrc = src;
+    WXSDKInstance instance = getInstance();
+    Uri rewrited = instance.rewriteUri(Uri.parse(src), URIAdapter.IMAGE);
+
+    if (Constants.Scheme.LOCAL.equals(rewrited.getScheme())) {
+      setLocalSrc(rewrited);
+    } else {
+      int blur = 0;
+      String blurStr = getStyles().getBlur();
+      blur = parseBlurRadius(blurStr);
+      setRemoteSrc(rewrited, blur);
+    }
+  }
+
+  private void setBlurRadius(@NonNull String src, int blurRadius) {
+    if(getInstance() != null && blurRadius != mBlurRadius) {
+      Uri parsedUri = getInstance().rewriteUri(Uri.parse(src), URIAdapter.IMAGE);
+      if(!Constants.Scheme.LOCAL.equals(parsedUri.getScheme())) {
+        setRemoteSrc(parsedUri,blurRadius);
+      }
+    }
+  }
+
+  private int parseBlurRadius(@Nullable String rawRadius) {
+    if(rawRadius == null) {
+      return 0;
+    }
+    SingleFunctionParser<Integer> parser = new SingleFunctionParser<Integer>(rawRadius,BLUR_RADIUS_MAPPER);
+    List<Integer> list = null;
+    try {
+      list = parser.parse("blur");
+    }catch (Exception e) {
+      return 0;
+    }
+    if(list == null || list.isEmpty()) {
+      return 0;
+    }
+    return list.get(0);
+  }
+
+  @Override
+  public void recycled() {
+    super.recycled();
+
+    if (getInstance().getImgLoaderAdapter() != null) {
+      getInstance().getImgLoaderAdapter().setImage(null, mHost,
+              null, null);
+    } else {
+      if (WXEnvironment.isApkDebugable()) {
+        throw new WXRuntimeException("getImgLoaderAdapter() == null");
+      }
+      WXLogUtils.e("Error getImgLoaderAdapter() == null");
+    }
+  }
+
+  public void autoReleaseImage(){
+    if(mAutoRecycle){
+      if(getHostView() != null){
+        if (getInstance().getImgLoaderAdapter() != null) {
+          getInstance().getImgLoaderAdapter().setImage(null, mHost, null, null);
+        }
+      }
+    }
+  }
+
+  public void autoRecoverImage() {
+    if(mAutoRecycle) {
+      setSrc(mSrc);
+    }
+  }
+
+  private void setRemoteSrc(Uri rewrited, int blurRadius) {
+
+    WXImageStrategy imageStrategy = new WXImageStrategy(getInstanceId());
+    imageStrategy.isClipping = true;
+
+    WXImageSharpen imageSharpen = getAttrs().getImageSharpen();
+    imageStrategy.isSharpen = imageSharpen == WXImageSharpen.SHARPEN;
+
+    imageStrategy.blurRadius = Math.max(0, blurRadius);
+    this.mBlurRadius = blurRadius;
+
+    final String rewritedStr = rewrited.toString();
+    imageStrategy.setImageListener(new MyImageListener(this,rewritedStr));
+
+    String placeholder=null;
+    if(getAttrs().containsKey(Constants.Name.PLACEHOLDER)){
+      placeholder= (String) getAttrs().get(Constants.Name.PLACEHOLDER);
+    }else if(getAttrs().containsKey(Constants.Name.PLACE_HOLDER)){
+      placeholder=(String)getAttrs().get(Constants.Name.PLACE_HOLDER);
+    }
+    if(placeholder!=null){
+      imageStrategy.placeHolder = getInstance().rewriteUri(Uri.parse(placeholder),URIAdapter.IMAGE).toString();
+    }
+
+    imageStrategy.instanceId = getInstanceId();
+    IWXImgLoaderAdapter imgLoaderAdapter = getInstance().getImgLoaderAdapter();
+    if (imgLoaderAdapter != null) {
+      imgLoaderAdapter.setImage(rewritedStr, getHostView(),
+          getImageQuality(), imageStrategy);
+    }
+  }
+
+  @RestrictTo(Scope.LIBRARY_GROUP)
+  protected WXImageQuality getImageQuality(){
+    return getAttrs().getImageQuality();
+  }
+
+  @Override
+  protected void onFinishLayout() {
+    super.onFinishLayout();
+    updateBorderRadius();
+  }
+
+  @Override
+  public void updateProperties(Map<String, Object> props) {
+    super.updateProperties(props);
+    updateBorderRadius();
+  }
+
+  private void updateBorderRadius() {
+    if (getHostView() instanceof WXImageView) {
+      final WXImageView imageView = (WXImageView)getHostView();
+      BorderDrawable borderDrawable = WXViewUtils.getBorderDrawable(getHostView());
+      float[] borderRadius;
+      if (borderDrawable != null) {
+        RectF borderBox = new RectF(0, 0, WXDomUtils.getContentWidth(this), WXDomUtils.getContentHeight(this));
+        borderRadius = borderDrawable.getBorderInnerRadius(borderBox);
+      } else {
+        borderRadius = new float[] {0, 0, 0, 0, 0, 0, 0, 0};
+      }
+      imageView.setBorderRadius(borderRadius);
+
+      if (imageView.getDrawable() instanceof ImageDrawable) {
+        ImageDrawable imageDrawable = (ImageDrawable)imageView.getDrawable();
+        float[] previousRadius = imageDrawable.getCornerRadii();
+        if (!Arrays.equals(previousRadius, borderRadius)) {
+          imageDrawable.setCornerRadii(borderRadius);
+        }
+      }
+    }
+  }
+
+  /**
+   * Need permission {android.permission.WRITE_EXTERNAL_STORAGE}
+   */
+  @JSMethod(uiThread = false)
+  public void save(final JSCallback saveStatuCallback) {
+
+    if (ContextCompat.checkSelfPermission(getContext(), Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
+      if (getContext() instanceof Activity) {
+        ActivityCompat.requestPermissions((Activity) getContext(),
+                new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, WRITE_EXTERNAL_STORAGE_PERMISSION_REQUEST_CODE);
+      }
+    }
+
+    if (ContextCompat.checkSelfPermission(getContext(), Manifest.permission.WRITE_EXTERNAL_STORAGE) != PackageManager.PERMISSION_GRANTED) {
+      if (saveStatuCallback != null) {
+        Map<String, Object> result = new HashMap<>();
+        result.put(SUCCEED, false);
+        result.put(ERRORDESC,"Permission denied: android.permission.WRITE_EXTERNAL_STORAGE");
+        saveStatuCallback.invoke(result);
+      }
+      return;
+    }
+
+    if (mHost == null) {
+      if (saveStatuCallback != null) {
+        Map<String, Object> result = new HashMap<>();
+        result.put(SUCCEED, false);
+        result.put(ERRORDESC,"Image component not initialized");
+        saveStatuCallback.invoke(result);
+      }
+      return;
+    }
+
+    if (mSrc == null || mSrc.equals("")) {
+      if (saveStatuCallback != null) {
+        Map<String, Object> result = new HashMap<>();
+        result.put(SUCCEED, false);
+        result.put(ERRORDESC,"Image does not have the correct src");
+        saveStatuCallback.invoke(result);
+      }
+      return;
+    }
+
+    WXViewToImageUtil.generateImage(mHost, 0, 0xfff8f8f8, new WXViewToImageUtil.OnImageSavedCallback() {
+      @Override
+      public void onSaveSucceed(String path) {
+        if (saveStatuCallback != null) {
+          Map<String, Object> result = new HashMap<>();
+          result.put(SUCCEED, true);
+          saveStatuCallback.invoke(result);
+        }
+      }
+
+      @Override
+      public void onSaveFailed(String errorDesc) {
+        if (saveStatuCallback != null) {
+          Map<String, Object> result = new HashMap<>();
+          result.put(SUCCEED, false);
+          result.put(ERRORDESC,errorDesc);
+          saveStatuCallback.invoke(result);
+        }
+      }
+    });
+  }
+
+  private String preImgUrlStr = "";
+  private void monitorImgSize(ImageView imageView,String currentImgUrlStr){
+    if (null == imageView){
+      return;
+    }
+    WXSDKInstance instance = getInstance();
+    if (null == instance){
+      return;
+    }
+    ViewGroup.LayoutParams params =imageView.getLayoutParams();
+    Drawable img = imageView.getDrawable();
+    if (null == params || null ==img){
+      return;
+    }
+    int imgHeight = img.getIntrinsicHeight();
+    int imgWidth = img.getIntrinsicWidth();
+    if (!preImgUrlStr.equals(currentImgUrlStr)){
+      preImgUrlStr = currentImgUrlStr;
+      if (imgHeight > 1081 && imgWidth > 721){
+        instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_LARGE_IMG_COUNT,1);
+        if (WXAnalyzerDataTransfer.isOpenPerformance){
+          WXAnalyzerDataTransfer.transferPerformance(getInstanceId(),"details",WXInstanceApm.KEY_PAGE_STATS_LARGE_IMG_COUNT,
+              imgWidth+"*"+imgHeight+","+currentImgUrlStr
+              );
+        }
+      }
+      long imgSize = imgHeight * imgWidth;
+      long viewSize = imageView.getMeasuredHeight() * imageView.getMeasuredWidth();
+      if (viewSize == 0){
+          return;
+      }
+      double scaleSize =  imgSize/(double)viewSize;
+      //max diff 40*40
+      if (scaleSize >1.2 && imgSize-viewSize > 1600){
+        instance.getWXPerformance().wrongImgSizeCount++;
+        instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_WRONG_IMG_SIZE_COUNT,1);
+
+        if (WXAnalyzerDataTransfer.isOpenPerformance){
+          WXAnalyzerDataTransfer.transferPerformance(getInstanceId(),"details",WXInstanceApm.KEY_PAGE_STATS_WRONG_IMG_SIZE_COUNT,
+              String.format(Locale.ROOT, "imgSize:[%d,%d],viewSize:[%d,%d],urL:%s",imgWidth,imgHeight,imageView.getMeasuredWidth(),imageView.getMeasuredHeight()
+              ,currentImgUrlStr)
+          );
+        }
+      }
+    }
+
+  }
+
+  @Override
+  public void destroy() {
+    if(getHostView() instanceof WXImageView){
+      if (getInstance().getImgLoaderAdapter() != null) {
+        getInstance().getImgLoaderAdapter().setImage(null, mHost, null, null);
+      }
+    }
+    super.destroy();
+  }
+
+  public interface Measurable {
+    int getNaturalWidth();
+    int getNaturalHeight();
+  }
+
+  public  static class MyImageListener implements WXImageStrategy.ImageListener {
+
+    private WeakReference<WXImage> wxImageWeakReference;
+
+    private String rewritedStr;
+
+    MyImageListener(WXImage image,String rewritedStr) {
+      this.wxImageWeakReference = new WeakReference<WXImage>(image);
+      this.rewritedStr = rewritedStr;
+    }
+
+    @Override
+    public void onImageFinish(String url, ImageView imageView, boolean result, Map extra) {
+      WXImage image = wxImageWeakReference.get();
+
+      if(image == null)
+        return;
+
+      if (image.getEvents().contains(Constants.Event.ONLOAD)) {
+        Map<String, Object> params = new HashMap<String, Object>();
+        Map<String, Object> size = new HashMap<>(2);
+        if (imageView != null && imageView instanceof Measurable) {
+          size.put("naturalWidth", ((Measurable) imageView).getNaturalWidth());
+          size.put("naturalHeight", ((Measurable) imageView).getNaturalHeight());
+        } else {
+          size.put("naturalWidth", 0);
+          size.put("naturalHeight", 0);
+        }
+        if (image.containsEvent(Constants.Event.ONLOAD)) {
+          params.put("success", result);
+          params.put("size", size);
+          image.fireEvent(Constants.Event.ONLOAD, params);
+        }
+      }
+      image.monitorImgSize(imageView,rewritedStr);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXIndicator.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXIndicator.java
new file mode 100644
index 0000000..c5688e2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXIndicator.java
@@ -0,0 +1,167 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+import android.view.View;
+import android.widget.FrameLayout;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXRuntimeException;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXCircleIndicator;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+/**
+ *
+ * Slider indicator
+ */
+@Component(lazyload = false)
+public class WXIndicator extends WXComponent<WXCircleIndicator> {
+
+  @Deprecated
+  public WXIndicator(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+  public WXIndicator(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+    super(instance, parent, isLazy, basicComponentData);
+  }
+
+  @Override
+  protected void setHostLayoutParams(WXCircleIndicator host, int width, int height, int left, int right, int top, int bottom) {
+      FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(width, height);
+      this.setMarginsSupportRTL(params, left, top, right, bottom);
+      host.setLayoutParams(params);
+  }
+
+  @Override
+  protected WXCircleIndicator initComponentHostView(@NonNull Context context) {
+    WXCircleIndicator view = new WXCircleIndicator(context);
+    if (getParent() instanceof WXSlider) {
+      return view;
+    } else {
+      if (WXEnvironment.isApkDebugable()) {
+        throw new WXRuntimeException("WXIndicator initView error.");
+      }
+    }
+    return null;
+  }
+
+  @Override
+  protected void onHostViewInitialized(WXCircleIndicator host) {
+    super.onHostViewInitialized(host);
+    if (getParent() instanceof WXSlider) {
+      ((WXSlider) getParent()).addIndicator(this);
+    }
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.ITEM_COLOR:
+        String item_color = WXUtils.getString(param,null);
+        if (item_color != null)
+          setItemColor(item_color);
+        return true;
+      case Constants.Name.ITEM_SELECTED_COLOR:
+        String selected_color = WXUtils.getString(param,null);
+        if (selected_color != null)
+          setItemSelectedColor(selected_color);
+        return true;
+      case Constants.Name.ITEM_SIZE:
+        Integer item_size = WXUtils.getInteger(param,null);
+        if (item_size != null)
+          setItemSize(item_size);
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+
+  @WXComponentProp(name = Constants.Name.ITEM_COLOR)
+  public void setItemColor(String itemColor) {
+    if (!TextUtils.isEmpty(itemColor)) {
+      int colorInt = WXResourceUtils.getColor(itemColor);
+      if (colorInt != Integer.MIN_VALUE) {
+        getHostView().setPageColor(colorInt);
+        getHostView().forceLayout();
+        getHostView().requestLayout();
+      }
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.ITEM_SELECTED_COLOR)
+  public void setItemSelectedColor(String itemSelectedColor) {
+    if (!TextUtils.isEmpty(itemSelectedColor)) {
+      int colorInt = WXResourceUtils.getColor(itemSelectedColor);
+      if (colorInt != Integer.MIN_VALUE) {
+        getHostView().setFillColor(colorInt);
+        getHostView().forceLayout();
+        getHostView().requestLayout();
+      }
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.ITEM_SIZE)
+  public void setItemSize(int itemSize) {
+    if (itemSize < 0) {
+      return;
+    }
+    getHostView().setRadius(WXViewUtils.getRealPxByWidth(itemSize,getInstance().getInstanceViewPortWidth()) / 2.0f);
+    getHostView().forceLayout();
+    getHostView().requestLayout();
+  }
+
+  public void setShowIndicators(boolean show) {
+    if (getHostView() == null) {
+      return;
+    }
+    if (show) {
+      getHostView().setVisibility(View.VISIBLE);
+    } else {
+      getHostView().setVisibility(View.GONE);
+    }
+  }
+
+  // TODO
+//  public static class IndicatorDomNode extends WXDomObject{
+//    public IndicatorDomNode(){
+//      super();
+//    }
+//
+//    @Override
+//    protected Map<String, String> getDefaultStyle() {
+//      WXStyle pendingStyles = getStyles();
+//      Map<String,String> map = new HashMap<>();
+//      if(!pendingStyles.containsKey(Constants.Name.RIGHT))
+//        map.put(Constants.Name.LEFT,"0");
+//      if(!pendingStyles.containsKey(Constants.Name.BOTTOM))
+//        map.put(Constants.Name.TOP,"0");
+//      return map;
+//    }
+//  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXInput.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXInput.java
new file mode 100644
index 0000000..51cc895
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXInput.java
@@ -0,0 +1,47 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXEditText;
+
+/**
+ *
+ * Input component
+ */
+@Component(lazyload = false)
+public class WXInput extends AbstractEditComponent{
+
+  @Deprecated
+  public WXInput(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+  public WXInput(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+    super(instance, parent, isLazy, basicComponentData);
+  }
+
+  @Override
+  protected void appleStyleAfterCreated(WXEditText editText) {
+    super.appleStyleAfterCreated(editText);
+    editText.setSingleLine();//default use single line , same to ios
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXLoading.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXLoading.java
new file mode 100644
index 0000000..f83349c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXLoading.java
@@ -0,0 +1,115 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.list.WXListComponent;
+import org.apache.weex.ui.view.WXFrameLayout;
+import org.apache.weex.ui.view.WXLoadingLayout;
+import org.apache.weex.ui.view.refresh.wrapper.BaseBounceView;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.HashMap;
+import java.util.Map;
+import org.apache.weex.ui.view.refresh.core.WXSwipeLayout.WXOnLoadingListener;
+
+/**
+ * div component
+ */
+@Component(lazyload = false)
+public class WXLoading extends WXBaseRefresh implements WXOnLoadingListener {
+
+  public static final String HIDE = "hide";
+
+  public WXLoading(
+      WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
+    super(instance, parent, lazy, basicComponentData);
+  }
+
+  @Override
+  protected WXFrameLayout initComponentHostView(@NonNull Context context) {
+    return new WXLoadingLayout(context);
+  }
+
+  @Override
+  public void onLoading() {
+    if (getEvents().contains(Constants.Event.ONLOADING)) {
+      fireEvent(Constants.Event.ONLOADING);
+    }
+  }
+
+  @Override
+  protected void setHostLayoutParams(WXFrameLayout host, int width, int height,
+                                     int left, int right, int top, int bottom) {
+    // The view of WXLoading will always be wrapped by a WXRefreshView at some point
+    // which is unknowable for front-end so the margins should always be 0 in LayoutParams,
+    // otherwise it will bring visible layout errors. This means WXLoading do not
+    // support margin.
+    super.setHostLayoutParams(host, width, height, 0, 0, 0, 0);
+  }
+
+  @Override
+  public void onPullingUp(float dy, int pullOutDistance, float viewHeight) {
+    if (getEvents().contains(Constants.Event.ONPULLING_UP)) {
+      Map<String, Object> data = new HashMap<>();
+      data.put(Constants.Name.DISTANCE_Y, dy);
+      data.put(Constants.Name.PULLING_DISTANCE, pullOutDistance);
+      data.put(Constants.Name.VIEW_HEIGHT, viewHeight);
+      fireEvent(Constants.Event.ONPULLING_UP, data);
+    }
+  }
+
+  @Override
+  public boolean canRecycled() {
+    return false;
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.DISPLAY:
+        String display = WXUtils.getString(param,null);
+        if (display != null)
+          setDisplay(display);
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @WXComponentProp(name = Constants.Name.DISPLAY)
+  public void setDisplay(String display) {
+    if (!TextUtils.isEmpty(display)) {
+      if (display.equals(HIDE)) {
+        if (getParent() instanceof WXListComponent || getParent() instanceof WXScroller) {
+          if (((BaseBounceView)getParent().getHostView()).getSwipeLayout().isRefreshing()) {
+            ((BaseBounceView) getParent().getHostView()).finishPullLoad();
+            ((BaseBounceView) getParent().getHostView()).onLoadmoreComplete();
+          }
+        }
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXLoadingIndicator.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXLoadingIndicator.java
new file mode 100644
index 0000000..25e4682
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXLoadingIndicator.java
@@ -0,0 +1,81 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.graphics.Color;
+
+import android.support.annotation.NonNull;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.refresh.circlebar.CircleProgressBar;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXUtils;
+
+@Component(lazyload = false)
+
+public class WXLoadingIndicator extends WXComponent<CircleProgressBar> {
+
+
+    public WXLoadingIndicator(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+        super(instance, parent, isLazy, basicComponentData);
+    }
+
+    @Override
+    protected CircleProgressBar initComponentHostView(@NonNull Context context) {
+        return new CircleProgressBar(context);
+    }
+
+    @Override
+    protected boolean setProperty(String key, Object param) {
+        switch (key) {
+            case Constants.Name.COLOR:
+                String color = WXUtils.getString(param,null);
+                if (color != null)
+                    setColor(color);
+                return true;
+            case Constants.Name.ANIMATING:
+                Boolean result = WXUtils.getBoolean(param, null);
+                if (result != null) {
+                    setAnimating(result);
+                }
+                return true;
+        }
+        return super.setProperty(key, param);
+    }
+
+    @WXComponentProp(name = Constants.Name.COLOR)
+    public void setColor(String color) {
+        if (color != null && !color.equals("")) {
+            int parseColor = WXResourceUtils.getColor(color, Color.RED);
+            getHostView().setColorSchemeColors(parseColor);
+        }
+    }
+
+    @WXComponentProp(name = Constants.Name.ANIMATING)
+    public void setAnimating(boolean animating) {
+        if (animating) {
+            getHostView().start();
+        } else {
+            getHostView().stop();
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXRefresh.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXRefresh.java
new file mode 100644
index 0000000..7a9cd79
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXRefresh.java
@@ -0,0 +1,119 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.list.WXListComponent;
+import org.apache.weex.ui.view.WXFrameLayout;
+import org.apache.weex.ui.view.WXRefreshLayout;
+import org.apache.weex.ui.view.refresh.wrapper.BaseBounceView;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.HashMap;
+import java.util.Map;
+import org.apache.weex.ui.view.refresh.core.WXSwipeLayout.WXOnRefreshListener;
+
+/**
+ * div component
+ */
+@Component(lazyload = false)
+public class WXRefresh extends WXBaseRefresh implements WXOnRefreshListener {
+
+  public static final String HIDE = "hide";
+
+  @Deprecated
+  public WXRefresh(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+  public WXRefresh(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
+    super(instance, parent, lazy, basicComponentData);
+  }
+
+  @Override
+  protected WXFrameLayout initComponentHostView(@NonNull Context context) {
+    return new WXRefreshLayout(context);
+  }
+
+  @Override
+  public boolean canRecycled() {
+    return false;
+  }
+
+  @Override
+  public void onRefresh() {
+    if(isDestoryed()){
+      return;
+    }
+    
+    if (getEvents().contains(Constants.Event.ONREFRESH)) {
+      fireEvent(Constants.Event.ONREFRESH);
+    }
+  }
+
+  @Override
+  public int getLayoutTopOffsetForSibling() {
+    //offset siblings
+    return getParent() instanceof Scrollable ? -Math.round(getLayoutHeight()) : 0;
+  }
+
+  @Override
+  public void onPullingDown(float dy, int pullOutDistance, float viewHeight) {
+    if (getEvents() != null && getEvents().contains(Constants.Event.ONPULLING_DOWN)) {
+      Map<String, Object> data = new HashMap<>();
+      data.put(Constants.Name.DISTANCE_Y, dy);
+      data.put(Constants.Name.PULLING_DISTANCE, pullOutDistance);
+      data.put(Constants.Name.VIEW_HEIGHT, viewHeight);
+      fireEvent(Constants.Event.ONPULLING_DOWN, data);
+    }
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.DISPLAY:
+        String display = WXUtils.getString(param,null);
+        if (display != null)
+          setDisplay(display);
+        return true;
+    }
+    return super.setProperty(key,param);
+  }
+
+  @WXComponentProp(name = Constants.Name.DISPLAY)
+  public void setDisplay(String display) {
+    if (!TextUtils.isEmpty(display)) {
+      if (display.equals(HIDE)) {
+        if (getParent() instanceof WXListComponent || getParent() instanceof WXScroller) {
+          if (((BaseBounceView)getParent().getHostView()).getSwipeLayout().isRefreshing()) {
+            ((BaseBounceView) getParent().getHostView()).finishPullRefresh();
+            ((BaseBounceView) getParent().getHostView()).onRefreshingComplete();
+          }
+        }
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXScroller.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXScroller.java
new file mode 100644
index 0000000..52d5c36
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXScroller.java
@@ -0,0 +1,1060 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.annotation.SuppressLint;
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.graphics.Point;
+import android.graphics.Rect;
+import android.os.Build;
+import android.os.Handler;
+import android.os.Looper;
+import android.support.annotation.NonNull;
+import android.support.v4.view.ViewCompat;
+import android.text.TextUtils;
+import android.view.GestureDetector;
+import android.view.Gravity;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewTreeObserver;
+import android.widget.FrameLayout;
+import android.widget.FrameLayout.LayoutParams;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.ICheckBindingScroller;
+import org.apache.weex.common.OnWXScrollListener;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.helper.ScrollStartEndHelper;
+import org.apache.weex.ui.component.helper.WXStickyHelper;
+import org.apache.weex.ui.view.IWXScroller;
+import org.apache.weex.ui.view.WXBaseRefreshLayout;
+import org.apache.weex.ui.view.WXHorizontalScrollView;
+import org.apache.weex.ui.view.WXScrollView;
+import org.apache.weex.ui.view.WXScrollView.WXScrollViewListener;
+import org.apache.weex.ui.view.refresh.wrapper.BaseBounceView;
+import org.apache.weex.ui.view.refresh.wrapper.BounceScrollerView;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import java.lang.reflect.InvocationTargetException;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Map.Entry;
+
+/**
+ * Component for scroller. It also support features like
+ * "appear", "disappear" and "sticky"
+ */
+@Component(lazyload = false)
+
+public class WXScroller extends WXVContainer<ViewGroup> implements WXScrollViewListener,Scrollable {
+
+  public static final String DIRECTION = "direction";
+  protected int mOrientation = Constants.Orientation.VERTICAL;
+  private List<WXComponent> mRefreshs=new ArrayList<>();
+  /** Use for offset children layout */
+  private int mChildrenLayoutOffset = 0;
+  private boolean mForceLoadmoreNextTime = false;
+  private int mOffsetAccuracy = 10;
+  private Point mLastReport = new Point(-1, -1);
+  private boolean mHasAddScrollEvent = false;
+  private Boolean mIslastDirectionRTL;
+
+  private static final int SWIPE_MIN_DISTANCE = 5;
+  private static final int SWIPE_THRESHOLD_VELOCITY = 300;
+  private int mActiveFeature = 0;
+  /**
+   * scroll start and scroll end event
+   * */
+  private ScrollStartEndHelper mScrollStartEndHelper;
+
+  private GestureDetector mGestureDetector;
+
+  private int pageSize = 0;
+  private boolean pageEnable = false;
+  private boolean mIsHostAttachedToWindow = false;
+  private View.OnAttachStateChangeListener mOnAttachStateChangeListener;
+
+  private boolean mlastDirectionRTL = false;
+
+  public static class Creator implements ComponentCreator {
+    @Override
+    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+      // For performance message collection
+      instance.setUseScroller(true);
+      return new WXScroller(instance, parent, basicComponentData);
+    }
+  }
+  /**
+   * Map for storing appear information
+   **/
+  private Map<String,AppearanceHelper> mAppearanceComponents = new HashMap<>();
+
+  /**
+   * Map for storing component that is sticky.
+   **/
+  private Map<String, Map<String, WXComponent>> mStickyMap = new HashMap<>();
+  private FrameLayout mRealView;
+  private FrameLayout mScrollerView;
+
+  private int mContentHeight = 0;
+  private int mContentWidth = 0;
+
+  private WXStickyHelper stickyHelper;
+  private Handler handler=new Handler(Looper.getMainLooper());
+
+  private boolean isScrollable = true;
+
+  @Deprecated
+  public WXScroller(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, basicComponentData);
+  }
+
+  public WXScroller(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+    stickyHelper = new WXStickyHelper(this);
+    instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_SCROLLER_NUM,1);
+  }
+
+  /**
+   * @return FrameLayout inner ScrollView
+   */
+  @Override
+  public ViewGroup getRealView() {
+    return mScrollerView;
+  }
+
+
+  @Override
+  public void createViewImpl() {
+    super.createViewImpl();
+    for (int i = 0; i < mRefreshs.size(); i++) {
+      WXComponent component = mRefreshs.get(i);
+      component.createViewImpl();
+      checkRefreshOrLoading(component);
+    }
+  }
+
+  /**
+   * @return ScrollView
+   */
+  public ViewGroup getInnerView() {
+    if(getHostView() == null) {
+      return null;
+    }
+    if (getHostView() instanceof BounceScrollerView) {
+      return ((BounceScrollerView) getHostView()).getInnerView();
+    } else {
+      return getHostView();
+    }
+  }
+
+  @Override
+  public void addEvent(String type) {
+    super.addEvent(type);
+    if (ScrollStartEndHelper.isScrollEvent(type)
+            && getInnerView() != null && !mHasAddScrollEvent) {
+      mHasAddScrollEvent = true;
+      if (getInnerView() instanceof WXScrollView) {
+        ((WXScrollView) getInnerView()).addScrollViewListener(new WXScrollViewListener() {
+          @Override
+          public void onScrollChanged(WXScrollView scrollView, int x, int y, int oldx, int oldy) {
+            getScrollStartEndHelper().onScrolled(x, y);
+            if(!getEvents().contains(Constants.Event.SCROLL)){
+              return;
+            }
+            if (shouldReport(x, y)) {
+              fireScrollEvent(scrollView.getContentFrame(), x, y, oldx, oldy);
+            }
+          }
+
+          @Override
+          public void onScrollToBottom(WXScrollView scrollView, int x, int y) {
+            //ignore
+          }
+
+          @Override
+          public void onScrollStopped(WXScrollView scrollView, int x, int y) {
+            //ignore
+          }
+
+          @Override
+          public void onScroll(WXScrollView scrollView, int x, int y) {
+            //ignore
+          }
+        });
+      } else if (getInnerView() instanceof WXHorizontalScrollView) {
+        ((WXHorizontalScrollView) getInnerView()).addScrollViewListener(new WXHorizontalScrollView.ScrollViewListener() {
+          @Override
+          public void onScrollChanged(WXHorizontalScrollView scrollView, int x, int y, int oldx, int oldy) {
+            getScrollStartEndHelper().onScrolled(x, y);
+            if(!getEvents().contains(Constants.Event.SCROLL)){
+              return;
+            }
+            if (shouldReport(x, y)) {
+              fireScrollEvent(scrollView.getContentFrame(), x, y, oldx, oldy);
+            }
+          }
+        });
+      }
+    }
+  }
+
+  private void fireScrollEvent(Rect contentFrame, int x, int y, int oldx, int oldy) {
+    fireEvent(Constants.Event.SCROLL, getScrollEvent(x, y));
+  }
+
+  public Map<String, Object> getScrollEvent(int x, int y){
+    Rect contentFrame =  new Rect();
+    if (getInnerView() instanceof WXScrollView) {
+      contentFrame = ((WXScrollView) getInnerView()).getContentFrame();
+    }else if (getInnerView() instanceof WXHorizontalScrollView) {
+      contentFrame = ((WXHorizontalScrollView) getInnerView()).getContentFrame();
+    }
+    Map<String, Object> event = new HashMap<>(2);
+    Map<String, Object> contentSize = new HashMap<>(2);
+    Map<String, Object> contentOffset = new HashMap<>(2);
+
+    int viewport = getInstance().getInstanceViewPortWidth();
+
+    contentSize.put(Constants.Name.WIDTH, WXViewUtils.getWebPxByWidth(contentFrame.width(), viewport));
+    contentSize.put(Constants.Name.HEIGHT, WXViewUtils.getWebPxByWidth(contentFrame.height(), viewport));
+
+    contentOffset.put(Constants.Name.X, -WXViewUtils.getWebPxByWidth(x, viewport));
+    contentOffset.put(Constants.Name.Y, -WXViewUtils.getWebPxByWidth(y, viewport));
+
+    event.put(Constants.Name.CONTENT_SIZE, contentSize);
+    event.put(Constants.Name.CONTENT_OFFSET, contentOffset);
+    return  event;
+  }
+
+  private boolean shouldReport(int x, int y) {
+    if (mLastReport.x == -1 && mLastReport.y == -1) {
+      mLastReport.x = x;
+      mLastReport.y = y;
+      return true;
+    }
+
+    if (mOrientation == Constants.Orientation.HORIZONTAL
+            && Math.abs(x - mLastReport.x) >= mOffsetAccuracy) {
+      mLastReport.x = x;
+      mLastReport.y = y;
+      return true;
+    }
+
+    if (mOrientation == Constants.Orientation.VERTICAL
+            && Math.abs(y - mLastReport.y) >= mOffsetAccuracy) {
+      mLastReport.x = x;
+      mLastReport.y = y;
+      return true;
+    }
+
+    return false;
+  }
+
+  /**
+   * Intercept refresh view and loading view
+   */
+  @Override
+  public void addSubView(View child, int index) {
+    if (child == null || mRealView == null) {
+      return;
+    }
+
+    if (child instanceof WXBaseRefreshLayout) {
+      return;
+    }
+
+    int count = mRealView.getChildCount();
+    index = index >= count ? -1 : index;
+    if (index == -1) {
+      mRealView.addView(child);
+    } else {
+      mRealView.addView(child, index);
+    }
+  }
+
+  @Override
+  protected int getChildrenLayoutTopOffset() {
+    if (mChildrenLayoutOffset == 0) {
+      // Child LayoutSize data set after call Layout. So init mChildrenLayoutOffset here
+      final int listSize = mRefreshs.size();
+      if (listSize > 0) {
+        for (int i = 0; i < listSize; i++) {
+          WXComponent child = mRefreshs.get(i);
+          mChildrenLayoutOffset += child.getLayoutTopOffsetForSibling();
+        }
+      }
+    }
+    return mChildrenLayoutOffset;
+  }
+
+  /**
+   * Intercept refresh view and loading view
+   */
+  @Override
+  public void addChild(WXComponent child, int index) {
+    if (child instanceof WXBaseRefresh) {
+      if (checkRefreshOrLoading(child)) {
+        mRefreshs.add(child);
+      }
+    }
+    super.addChild(child, index);
+  }
+
+  /**
+   * Setting refresh view and loading view
+   * @param child the refresh_view or loading_view
+   */
+
+  private boolean checkRefreshOrLoading(final WXComponent child) {
+    boolean result = false;
+    if (child instanceof WXRefresh && getHostView() != null) {
+      ((BaseBounceView) getHostView()).setOnRefreshListener((WXRefresh) child);
+      Runnable runnable = WXThread.secure(new Runnable(){
+        @Override
+        public void run() {
+          ((BaseBounceView) getHostView()).setHeaderView(child);
+        }
+      });
+      handler.postDelayed(runnable,100);
+      result = true;
+    }
+
+    if (child instanceof WXLoading && getHostView() !=null) {
+      ((BaseBounceView) getHostView()).setOnLoadingListener((WXLoading)child);
+      Runnable runnable= WXThread.secure(new Runnable(){
+        @Override
+        public void run() {
+          ((BaseBounceView) getHostView()).setFooterView(child);
+        }
+      });
+      handler.postDelayed(runnable, 100);
+      result = true;
+    }
+    return result;
+  }
+
+  @Override
+  public void remove(WXComponent child,boolean destory) {
+    super.remove(child,destory);
+    if(child instanceof WXLoading){
+      ((BaseBounceView)getHostView()).removeFooterView(child);
+    }else if(child instanceof WXRefresh){
+      ((BaseBounceView)getHostView()).removeHeaderView(child);
+    }
+  }
+
+  @Override
+  public void destroy() {
+    super.destroy();
+    if (mAppearanceComponents != null) {
+      mAppearanceComponents.clear();
+    }
+    if (mStickyMap != null) {
+      mStickyMap.clear();
+    }
+    if (mOnAttachStateChangeListener != null && getInnerView() != null) {
+      getInnerView().removeOnAttachStateChangeListener(mOnAttachStateChangeListener);
+    }
+    if (getInnerView() != null && getInnerView() instanceof IWXScroller) {
+      ((IWXScroller) getInnerView()).destroy();
+    }
+  }
+
+  @SuppressLint("RtlHardcoded")
+  @Override
+  public void setMarginsSupportRTL(ViewGroup.MarginLayoutParams lp, int left, int top, int right, int bottom) {
+    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR1) {
+      lp.setMargins(left, top, right, bottom);
+      lp.setMarginStart(left);
+      lp.setMarginEnd(right);
+    } else {
+      if (lp instanceof FrameLayout.LayoutParams) {
+        FrameLayout.LayoutParams lp_frameLayout = (FrameLayout.LayoutParams) lp;
+        if (isLayoutRTL()) {
+          lp_frameLayout.gravity = Gravity.RIGHT | Gravity.TOP;
+          lp.setMargins(right, top, left, bottom);
+        } else {
+          lp_frameLayout.gravity = Gravity.LEFT | Gravity.TOP;
+          lp.setMargins(left, top, right, bottom);
+        }
+      } else {
+        lp.setMargins(left, top, right, bottom);
+      }
+    }
+  }
+
+  @Override
+  public void setLayout(WXComponent component) {
+    if (TextUtils.isEmpty(component.getComponentType())
+            || TextUtils.isEmpty(component.getRef()) || component.getLayoutPosition() == null
+            || component.getLayoutSize() == null) {
+      return;
+    }
+    if (component.getHostView() != null) {
+      int layoutDirection = component.isLayoutRTL() ? ViewCompat.LAYOUT_DIRECTION_RTL : ViewCompat.LAYOUT_DIRECTION_LTR;
+      ViewCompat.setLayoutDirection(component.getHostView(), layoutDirection);
+    }
+    super.setLayout(component);
+  }
+
+  @Override
+  protected MeasureOutput measure(int width, int height) {
+    MeasureOutput measureOutput = new MeasureOutput();
+    if (this.mOrientation == Constants.Orientation.HORIZONTAL) {
+      int screenW = WXViewUtils.getScreenWidth(WXEnvironment.sApplication);
+      int weexW = WXViewUtils.getWeexWidth(getInstanceId());
+      measureOutput.width = width > (weexW >= screenW ? screenW : weexW) ? FrameLayout.LayoutParams.MATCH_PARENT
+              : width;
+      measureOutput.height = height;
+    } else {
+      int screenH = WXViewUtils.getScreenHeight(WXEnvironment.sApplication);
+      int weexH = WXViewUtils.getWeexHeight(getInstanceId());
+      measureOutput.height = height > (weexH >= screenH ? screenH : weexH) ? FrameLayout.LayoutParams.MATCH_PARENT
+              : height;
+      measureOutput.width = width;
+    }
+    return measureOutput;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  protected ViewGroup initComponentHostView(@NonNull Context context) {
+    String scroll;
+    if (getAttrs().isEmpty()) {
+      scroll = "vertical";
+    } else {
+      scroll = getAttrs().getScrollDirection();
+
+      Object o = getAttrs().get(Constants.Name.PAGE_ENABLED);
+
+      pageEnable = o != null && Boolean.parseBoolean(o.toString());
+
+      Object pageSize = getAttrs().get(Constants.Name.PAGE_SIZE);
+      if (pageSize != null) {
+        float aFloat = WXUtils.getFloat(pageSize);
+
+
+        float realPxByWidth = WXViewUtils.getRealPxByWidth(aFloat, getInstance().getInstanceViewPortWidth());
+        if (realPxByWidth != 0) {
+          this.pageSize = (int) realPxByWidth;
+        }
+      }
+
+    }
+
+    ViewGroup host;
+    if(("horizontal").equals(scroll)){
+      mOrientation = Constants.Orientation.HORIZONTAL;
+      final WXHorizontalScrollView scrollView = new WXHorizontalScrollView(context);
+      mRealView = new FrameLayout(context);
+      scrollView.setScrollViewListener(new WXHorizontalScrollView.ScrollViewListener() {
+        @Override
+        public void onScrollChanged(WXHorizontalScrollView scrollView, int x, int y, int oldx, int oldy) {
+          procAppear(x,y,oldx,oldy);
+          onLoadMore(scrollView,x,y);
+        }
+      });
+      FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(
+              LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
+      scrollView.addView(mRealView, layoutParams);
+      scrollView.setHorizontalScrollBarEnabled(false);
+      mScrollerView = scrollView;
+      final WXScroller component = this;
+      final View.OnLayoutChangeListener listener = new View.OnLayoutChangeListener() {
+        @Override
+        public void onLayoutChange(View view, final int left, int top, final int right, int bottom, final int oldLeft, int oldTop, final int oldRight, int oldBottom) {
+          final View frameLayout = view;
+          scrollView.post(new Runnable() {
+            @Override
+            public void run() {
+              if (mIslastDirectionRTL != null && isLayoutRTL() != mIslastDirectionRTL) {
+                // when layout direction changed we need convert x to RTL x for scroll to the same item
+                int currentX = getScrollX();
+                int totalWidth = getInnerView().getChildAt(0).getWidth();
+                int displayWidth = getInnerView().getMeasuredWidth();
+                scrollView.scrollTo(totalWidth - currentX - displayWidth, component.getScrollY());
+              } else if (isLayoutRTL()) {
+                // if layout direction not changed, but width changede, we need keep RTL offset
+                int oldWidth = oldRight - oldLeft;
+                int width = right - left;
+                int changedWidth = width - oldWidth;
+                if (changedWidth != 0) {
+                  scrollView.scrollBy(changedWidth, component.getScrollY());
+                }
+              }
+              mIslastDirectionRTL = isLayoutRTL();
+            }
+          });
+        }
+      };
+      mRealView.addOnAttachStateChangeListener(new View.OnAttachStateChangeListener() {
+        @Override
+        public void onViewAttachedToWindow(View view) {
+          view.addOnLayoutChangeListener(listener);
+        }
+
+        @Override
+        public void onViewDetachedFromWindow(View view) {
+          view.removeOnLayoutChangeListener(listener);
+        }
+      });
+
+
+      if(pageEnable) {
+        mGestureDetector = new GestureDetector(new MyGestureDetector(scrollView));
+        scrollView.setOnTouchListener(new View.OnTouchListener() {
+          @Override
+          public boolean onTouch(View v, MotionEvent event) {
+            if (pageSize == 0)  {
+              pageSize = v.getMeasuredWidth();
+            }
+
+            if (mGestureDetector.onTouchEvent(event)) {
+              return true;
+            }
+            else if(event.getAction() == MotionEvent.ACTION_UP || event.getAction() == MotionEvent.ACTION_CANCEL ){
+              int scrollX = getScrollX();
+              int featureWidth = pageSize;
+              mActiveFeature = ((scrollX + (featureWidth/2))/featureWidth);
+              int scrollTo = mActiveFeature*featureWidth;
+              scrollView.smoothScrollTo(scrollTo, 0);
+              return true;
+            }
+            else{
+              return false;
+            }
+          }
+        });
+      }
+
+
+      host = scrollView;
+    }else{
+      mOrientation = Constants.Orientation.VERTICAL;
+      BounceScrollerView scrollerView = new BounceScrollerView(context, mOrientation, this);
+      mRealView = new FrameLayout(context);
+      WXScrollView innerView = scrollerView.getInnerView();
+      innerView.addScrollViewListener(this);
+      FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(
+              LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
+      mScrollerView = innerView;
+      innerView.addView(mRealView, layoutParams);
+      innerView.setVerticalScrollBarEnabled(true);
+      innerView.setNestedScrollingEnabled(WXUtils.getBoolean(getAttrs().get(Constants.Name.NEST_SCROLLING_ENABLED), true));
+      innerView.addScrollViewListener(new WXScrollViewListener() {
+        @Override
+        public void onScrollChanged(WXScrollView scrollView, int x, int y, int oldx, int oldy) {
+
+        }
+
+        @Override
+        public void onScrollToBottom(WXScrollView scrollView, int x, int y) {
+
+        }
+
+        @Override
+        public void onScrollStopped(WXScrollView scrollView, int x, int y) {
+          List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
+          if(listeners!=null && listeners.size()>0){
+            for (OnWXScrollListener listener : listeners) {
+              if (listener != null) {
+                listener.onScrollStateChanged(scrollView,x,y,OnWXScrollListener.IDLE);
+              }
+            }
+          }
+          getScrollStartEndHelper().onScrollStateChanged(OnWXScrollListener.IDLE);
+        }
+
+        @Override
+        public void onScroll(WXScrollView scrollView, int x, int y) {
+          List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
+          if(listeners!=null && listeners.size()>0){
+            for (OnWXScrollListener listener : listeners) {
+              if (listener != null) {
+                if(listener instanceof ICheckBindingScroller){
+                  if(((ICheckBindingScroller) listener).isNeedScroller(getRef(),null)){
+                    listener.onScrolled(scrollView, x, y);
+                  }
+                }else {
+                  listener.onScrolled(scrollView, x, y);
+                }
+              }
+            }
+          }
+        }
+      });
+      host = scrollerView;
+    }
+
+    host.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
+      @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
+      @Override
+      public void onGlobalLayout() {
+        procAppear(0,0,0,0);
+        View view;
+        if( (view = getHostView()) == null){
+          return;
+        }
+        if(Build.VERSION.SDK_INT >=  Build.VERSION_CODES.JELLY_BEAN) {
+          view.getViewTreeObserver().removeOnGlobalLayoutListener(this);
+        }else{
+          view.getViewTreeObserver().removeGlobalOnLayoutListener(this);
+        }
+      }
+    });
+    mOnAttachStateChangeListener = new View.OnAttachStateChangeListener() {
+      @Override
+      public void onViewAttachedToWindow(View v) {
+        mIsHostAttachedToWindow = true;
+        procAppear(getScrollX(), getScrollY(), getScrollX(), getScrollY());
+      }
+
+      @Override
+      public void onViewDetachedFromWindow(View v) {
+        mIsHostAttachedToWindow = false;
+        dispatchDisappearEvent();
+      }
+    };
+    host.addOnAttachStateChangeListener(mOnAttachStateChangeListener);
+    return host;
+  }
+
+  @Override
+  public int getScrollY() {
+    return getInnerView() == null ? 0 : getInnerView().getScrollY();
+  }
+
+  @Override
+  public int getScrollX() {
+    return getInnerView() == null ? 0 : getInnerView().getScrollX();
+  }
+
+  @Override
+  public int getOrientation() {
+    return mOrientation;
+  }
+
+  public Map<String, Map<String, WXComponent>> getStickMap() {
+    return mStickyMap;
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.SHOW_SCROLLBAR:
+        Boolean result = WXUtils.getBoolean(param,null);
+        if (result != null) {
+          setShowScrollbar(result);
+        }
+        return true;
+      case Constants.Name.SCROLLABLE:
+        boolean scrollable = WXUtils.getBoolean(param, true);
+        setScrollable(scrollable);
+        return true;
+      case Constants.Name.OFFSET_ACCURACY:
+        int accuracy = WXUtils.getInteger(param, 10);
+        setOffsetAccuracy(accuracy);
+        return true;
+        default:
+          break;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @WXComponentProp(name = Constants.Name.SHOW_SCROLLBAR)
+  public void setShowScrollbar(boolean show) {
+    if(getInnerView()==null){
+      return;
+    }
+    if (mOrientation == Constants.Orientation.VERTICAL) {
+      getInnerView().setVerticalScrollBarEnabled(show);
+    } else {
+      getInnerView().setHorizontalScrollBarEnabled(show);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.SCROLLABLE)
+  public void setScrollable(boolean scrollable) {
+    this.isScrollable = scrollable;
+    View hostView = getInnerView();
+    if(hostView instanceof WXHorizontalScrollView) {
+      ((WXHorizontalScrollView)hostView).setScrollable(scrollable);
+    }else if(hostView instanceof WXScrollView) {
+      ((WXScrollView)hostView).setScrollable(scrollable);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.OFFSET_ACCURACY)
+  public void setOffsetAccuracy(int accuracy) {
+    float realPx = WXViewUtils.getRealPxByWidth(accuracy, getInstance().getInstanceViewPortWidth());
+    this.mOffsetAccuracy = (int) realPx;
+  }
+
+  @Override
+  public boolean isScrollable() {
+    return isScrollable;
+  }
+
+
+  @Override
+  public void bindStickStyle(WXComponent component) {
+    stickyHelper.bindStickStyle(component,mStickyMap);
+  }
+
+  @Override
+  public void unbindStickStyle(WXComponent component) {
+    stickyHelper.unbindStickStyle(component,mStickyMap);
+  }
+
+  /**
+   * Bind appear event
+   */
+  @Override
+  public void bindAppearEvent(WXComponent component) {
+    setWatch(AppearanceHelper.APPEAR,component,true);
+  }
+
+  private void setWatch(int event,WXComponent component,boolean isWatch){
+    AppearanceHelper item = mAppearanceComponents.get(component.getRef());
+    if (item == null) {
+      item = new AppearanceHelper(component);
+      mAppearanceComponents.put(component.getRef(),item);
+    }
+
+    item.setWatchEvent(event,isWatch);
+
+    //check current components appearance status.
+    procAppear(0,0,0,0);
+  }
+
+  /**
+   * Bind disappear event
+   */
+  @Override
+  public void bindDisappearEvent(WXComponent component) {
+    setWatch(AppearanceHelper.DISAPPEAR,component,true);
+  }
+
+  /**
+   * Remove appear event
+   */
+  @Override
+  public void unbindAppearEvent(WXComponent component) {
+    setWatch(AppearanceHelper.APPEAR,component,false);
+  }
+
+  /**
+   * Remove disappear event
+   */
+  @Override
+  public void unbindDisappearEvent(WXComponent component) {
+    setWatch(AppearanceHelper.DISAPPEAR,component,false);
+  }
+
+  @Override
+  public void scrollTo(WXComponent component, Map<String, Object> options) {
+    float offsetFloat = 0;
+    boolean smooth = true;
+
+    if (options != null) {
+      String offset = options.get(Constants.Name.OFFSET) == null ? "0" : options.get(Constants.Name.OFFSET).toString();
+      smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
+      if (offset != null) {
+        try {
+          offsetFloat = WXViewUtils.getRealPxByWidth(Float.parseFloat(offset), getInstance().getInstanceViewPortWidth());
+        }catch (Exception e ){
+          WXLogUtils.e("Float parseFloat error :"+e.getMessage());
+        }
+      }
+    }
+
+    if(pageEnable) {
+      mActiveFeature = mChildren.indexOf(component);
+    }
+
+    int viewYInScroller = component.getAbsoluteY() - getAbsoluteY();
+    int viewXInScroller = 0;
+    if (this.isLayoutRTL()) {
+      // if layout direction is rtl, we need calculate rtl scroll x;
+      if (component.getParent() != null && component.getParent() == this) {
+        if (getInnerView().getChildCount() > 0) {
+          int totalWidth = getInnerView().getChildAt(0).getWidth();
+          int displayWidth = getInnerView().getMeasuredWidth();
+          viewXInScroller = totalWidth - (component.getAbsoluteX() - getAbsoluteX()) - displayWidth;
+        } else {
+          viewXInScroller = component.getAbsoluteX() - getAbsoluteX();
+        }
+      } else {
+        int displayWidth = getInnerView().getMeasuredWidth();
+        viewXInScroller = component.getAbsoluteX() - getAbsoluteX() - displayWidth + (int)component.getLayoutWidth();
+      }
+      offsetFloat = -offsetFloat;
+    } else {
+      viewXInScroller = component.getAbsoluteX() - getAbsoluteX();
+    }
+    scrollBy(viewXInScroller - getScrollX() + (int) offsetFloat, viewYInScroller - getScrollY() + (int) offsetFloat, smooth);
+
+  }
+
+  /**
+   * Scroll by specified distance. Horizontal scroll is not supported now.
+   * @param x horizontal distance, not support
+   * @param y vertical distance. Negative for scroll to top
+   */
+  public void scrollBy(final int x, final int y) {
+    scrollBy(x, y, false);
+  }
+
+  public void scrollBy(final int x, final int y, final boolean smooth) {
+    if (getInnerView() == null) {
+      return;
+    }
+
+    getInnerView().postDelayed(new Runnable() {
+      @Override
+      public void run() {
+        if (mOrientation == Constants.Orientation.VERTICAL) {
+          if (smooth) {
+            ((WXScrollView) getInnerView()).smoothScrollBy(0, y);
+          } else {
+            ((WXScrollView) getInnerView()).scrollBy(0, y);
+          }
+        } else {
+          if (smooth) {
+            ((WXHorizontalScrollView) getInnerView()).smoothScrollBy(x, 0);
+          } else {
+            ((WXHorizontalScrollView) getInnerView()).scrollBy(x, 0);
+          }
+        }
+        getInnerView().invalidate();
+      }
+    }, 16);
+  }
+
+  @Override
+  public void onScrollChanged(WXScrollView scrollView, int x, int y,
+                              int oldx, int oldy) {
+    procAppear( x, y, oldx, oldy);
+  }
+
+  @Override
+  public void notifyAppearStateChange(String wxEventType, String direction) {
+    if (containsEvent(Constants.Event.APPEAR) || containsEvent(Constants.Event.DISAPPEAR)) {
+      Map<String, Object> params = new HashMap<>();
+      params.put("direction", direction);
+      fireEvent(wxEventType, params);
+    }
+    // No-op. The moment to notify children is decided by the time when scroller is attached
+    // or detached to window. Do not call super as scrollview has different disposal.
+  }
+
+  /**
+   * Process event like appear and disappear
+   *
+   * This method will be invoked in several situation below.
+   *    1. bind or unbind event
+   *    2. host view is attached to window
+   *    3. when scrollview is scrolling
+   */
+  private void procAppear(int x, int y, int oldx,
+                          int oldy) {
+    if (!mIsHostAttachedToWindow) return;
+    int moveY = y - oldy;
+    int moveX = x - oldx;
+    String direction = moveY > 0 ? Constants.Value.DIRECTION_UP :
+            moveY < 0 ? Constants.Value.DIRECTION_DOWN : null;
+    if (mOrientation == Constants.Orientation.HORIZONTAL && moveX != 0) {
+      direction = moveX > 0 ? Constants.Value.DIRECTION_RIGHT : Constants.Value.DIRECTION_LEFT;
+    }
+
+    for (Entry<String, AppearanceHelper> item : mAppearanceComponents.entrySet()) {
+      AppearanceHelper helper = item.getValue();
+
+      if (!helper.isWatch()) {
+        continue;
+      }
+      boolean visible = checkItemVisibleInScroller(helper.getAwareChild());
+
+      int result = helper.setAppearStatus(visible);
+      if (result != AppearanceHelper.RESULT_NO_CHANGE) {
+        helper.getAwareChild().notifyAppearStateChange(result == AppearanceHelper.RESULT_APPEAR ? Constants.Event.APPEAR : Constants.Event.DISAPPEAR, direction);
+      }
+    }
+  }
+
+  /**
+   * Check the view of given component is visible in scrollview.
+   *
+   * @param component ready to be check
+   * @return item is visible
+   */
+  private boolean checkItemVisibleInScroller(WXComponent component) {
+    boolean visible = false;
+    while (component != null && !(component instanceof WXScroller)) {
+      if (component.getParent() instanceof WXScroller) {
+        if (mOrientation == Constants.Orientation.HORIZONTAL) {
+          int offsetLeft = (int) component.getLayoutPosition().getLeft() - getScrollX();
+          visible = (offsetLeft > 0 - component.getLayoutWidth() && offsetLeft < getLayoutWidth());
+        } else {
+          int offsetTop = (int) component.getLayoutPosition().getTop() - getScrollY();
+          visible = (offsetTop > 0 - component.getLayoutHeight() && offsetTop < getLayoutHeight());
+        }
+      }
+      component = component.getParent();
+    }
+    return visible;
+  }
+
+  /**
+   * Dispatch disappear event to the child components in need.
+   */
+  private void dispatchDisappearEvent() {
+    for (Entry<String, AppearanceHelper> item : mAppearanceComponents.entrySet()) {
+      AppearanceHelper helper = item.getValue();
+      if (!helper.isWatch()) {
+        continue;
+      }
+      int result = helper.setAppearStatus(false);
+      if (result != AppearanceHelper.RESULT_NO_CHANGE) {
+        helper.getAwareChild().notifyAppearStateChange(result == AppearanceHelper.RESULT_APPEAR ?
+                Constants.Event.APPEAR : Constants.Event.DISAPPEAR, "");
+      }
+    }
+  }
+
+  @Override
+  public void onScrollToBottom(WXScrollView scrollView, int x, int y) {
+
+  }
+
+  @Override
+  public void onScrollStopped(WXScrollView scrollView, int x, int y) {
+  }
+
+  @Override
+  public void onScroll(WXScrollView scrollView, int x, int y) {
+
+    this.onLoadMore(scrollView, x, y);
+  }
+
+  /**
+   * Handle loadMore Event.when Scroller has bind loadMore Event and set the attr of loadMoreOffset
+   * it will tell the JS to handle the event of onLoadMore;
+   * @param scrollView  the WXScrollView
+   * @param x the X direction
+   * @param y the Y direction
+   */
+  protected void onLoadMore(FrameLayout scrollView, int x, int y) {
+    try {
+      String offset = getAttrs().getLoadMoreOffset();
+      if (TextUtils.isEmpty(offset)) {
+        return;
+      }
+      int offsetInt = (int)WXViewUtils.getRealPxByWidth(Float.parseFloat(offset), getInstance().getInstanceViewPortWidth());
+
+      if (scrollView instanceof WXHorizontalScrollView){
+        int contentWidth = scrollView.getChildAt(0).getWidth();
+        int offScreenX =  contentWidth-x-scrollView.getWidth();
+        if (offScreenX < offsetInt && (mContentWidth != contentWidth || mForceLoadmoreNextTime)){
+          fireEvent(Constants.Event.LOADMORE);
+          mContentWidth=contentWidth;
+          mForceLoadmoreNextTime = false;
+        }
+      }else {
+        int contentH = scrollView.getChildAt(0).getHeight();
+        int scrollerH = scrollView.getHeight();
+        int offScreenY = contentH - y - scrollerH;
+        if (offScreenY < offsetInt) {
+          if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.d("[WXScroller-onScroll] offScreenY :" + offScreenY);
+          }
+          if (mContentHeight != contentH || mForceLoadmoreNextTime) {
+            fireEvent(Constants.Event.LOADMORE);
+            mContentHeight = contentH;
+            mForceLoadmoreNextTime = false;
+          }
+        }
+      }
+    } catch (Exception e) {
+      WXLogUtils.d("[WXScroller-onScroll] ", e);
+    }
+
+  }
+
+  @JSMethod
+  public void resetLoadmore() {
+    mForceLoadmoreNextTime = true;
+  }
+
+  public ScrollStartEndHelper getScrollStartEndHelper() {
+    if(mScrollStartEndHelper == null){
+      mScrollStartEndHelper = new ScrollStartEndHelper(this);
+    }
+    return mScrollStartEndHelper;
+  }
+
+
+  class MyGestureDetector extends GestureDetector.SimpleOnGestureListener {
+    public WXHorizontalScrollView getScrollView() {
+      return scrollView;
+    }
+
+    private final WXHorizontalScrollView scrollView;
+
+    MyGestureDetector(WXHorizontalScrollView horizontalScrollView) {
+      scrollView = horizontalScrollView;
+    }
+
+    @Override
+    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
+      int mItems = mChildren.size();
+      try {
+        //right to left
+        if(e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) {
+          int featureWidth = pageSize;
+          mActiveFeature = (mActiveFeature < (mItems - 1))? mActiveFeature + 1:mItems -1;
+          scrollView.smoothScrollTo(mActiveFeature*featureWidth, 0);
+          return true;
+        }
+        //left to right
+        else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY) {
+          int featureWidth = pageSize;
+          mActiveFeature = (mActiveFeature > 0)? mActiveFeature - 1:0;
+          scrollView.smoothScrollTo(mActiveFeature*featureWidth, 0);
+          return true;
+        }
+      } catch (Exception e) {
+        WXLogUtils.e("There was an error processing the Fling event:" + e.getMessage());
+      }
+      return false;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXSlider.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXSlider.java
new file mode 100644
index 0000000..9459f87
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXSlider.java
@@ -0,0 +1,619 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.support.annotation.NonNull;
+import android.support.v4.view.ViewPager;
+import android.support.v4.view.ViewPager.OnPageChangeListener;
+import android.text.TextUtils;
+import android.view.GestureDetector;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewGroup.LayoutParams;
+import android.widget.FrameLayout;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.BaseFrameLayout;
+import org.apache.weex.ui.view.WXCircleIndicator;
+import org.apache.weex.ui.view.WXCirclePageAdapter;
+import org.apache.weex.ui.view.WXCircleViewPager;
+import org.apache.weex.ui.view.gesture.WXGestureType;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.lang.ref.WeakReference;
+import java.lang.reflect.InvocationTargetException;
+import java.util.HashMap;
+import java.util.Map;
+
+@Component(lazyload = false)
+
+public class WXSlider extends WXVContainer<FrameLayout> {
+
+  public static final String INDEX = "index";
+  public static final String INFINITE = "infinite";
+
+  private boolean isInfinite = true;
+
+  Map<String, Object> params = new HashMap<>();
+  private float offsetXAccuracy = 0.1f;
+  private int initIndex = -1;
+  private boolean keepIndex = false;
+  private Runnable initRunnable;
+
+
+  public static class Creator implements ComponentCreator {
+    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+      return new WXSlider(instance, parent, basicComponentData);
+    }
+  }
+
+  /**
+   * Scrollable sliderview
+   */
+  /**
+   * package
+   **/
+  WXCircleViewPager mViewPager;
+  /**
+   * Circle indicator
+   */
+  protected WXIndicator mIndicator;
+
+  /**
+   * Adapter for sliderview
+   */
+  protected WXCirclePageAdapter mAdapter;
+
+  protected boolean mShowIndicators = true;
+
+  protected OnPageChangeListener mPageChangeListener = new SliderPageChangeListener();
+
+  @Deprecated
+  public WXSlider(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, basicComponentData);
+  }
+
+  public WXSlider(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  @Override
+  protected BaseFrameLayout initComponentHostView(@NonNull Context context) {
+    BaseFrameLayout view = new BaseFrameLayout(context);
+    // init view pager
+    if (getAttrs() != null) {
+      Object obj = getAttrs().get(INFINITE);
+      isInfinite = WXUtils.getBoolean(obj, true);
+    }
+    FrameLayout.LayoutParams pagerParams = new FrameLayout.LayoutParams(
+        LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
+    mViewPager = new WXCircleViewPager(context);
+    mViewPager.setCircle(isInfinite);
+    mViewPager.setLayoutParams(pagerParams);
+
+    // init adapter
+    mAdapter = new WXCirclePageAdapter(isInfinite);
+    mViewPager.setAdapter(mAdapter);
+    // add to parent
+    view.addView(mViewPager);
+    mViewPager.addOnPageChangeListener(mPageChangeListener);
+
+    registerActivityStateListener();
+
+    return view;
+  }
+
+  /**
+   * Slider is not a regular container,top/left/right/bottom not apply to view,expect indicator.
+   */
+  @Override
+  public LayoutParams getChildLayoutParams(WXComponent child,View childView, int width, int height, int left, int right, int top, int bottom) {
+    ViewGroup.LayoutParams lp = childView.getLayoutParams();
+    if (lp == null) {
+      lp = new FrameLayout.LayoutParams(width, height);
+    } else {
+      lp.width = width;
+      lp.height = height;
+    }
+
+    if (lp instanceof ViewGroup.MarginLayoutParams) {
+      //expect indicator .
+      if (child instanceof WXIndicator) {
+        this.setMarginsSupportRTL((ViewGroup.MarginLayoutParams) lp, left, top, right, bottom);
+      } else {
+        this.setMarginsSupportRTL((ViewGroup.MarginLayoutParams) lp, 0, 0, 0, 0);
+      }
+    }
+    return lp;
+  }
+
+
+  @Override
+  public void addEvent(String type) {
+    super.addEvent(type);
+    if (Constants.Event.SCROLL.equals(type)) {
+      if (mViewPager == null) {
+        return;
+      }
+      mViewPager.addOnPageChangeListener(new SliderOnScrollListener(this));
+    }
+  }
+
+  @Override
+  public boolean containsGesture(WXGestureType WXGestureType) {
+    //Enable gesture for slider
+    return super.containsGesture(WXGestureType);
+  }
+
+  @Override
+  public ViewGroup getRealView() {
+    return mViewPager;
+  }
+
+  @Override
+  public void addSubView(View view, int index) {
+    if (view == null || mAdapter == null) {
+      return;
+    }
+
+    if (view instanceof WXCircleIndicator) {
+      return;
+    }
+    mAdapter.addPageView(view);
+    hackTwoItemsInfiniteScroll();
+    if (initIndex != -1 && mAdapter.getRealCount() > initIndex) {
+      if(initRunnable == null){
+        initRunnable = new Runnable() {
+          @Override
+          public void run() {
+            initIndex = getInitIndex();
+            mViewPager.setCurrentItem(getRealIndex(initIndex));
+            initIndex = -1;
+            initRunnable = null;
+          }
+        };
+      }
+      mViewPager.removeCallbacks(initRunnable);
+      mViewPager.postDelayed(initRunnable, 50);
+    } else {
+      if (!keepIndex) {
+        mViewPager.setCurrentItem(getRealIndex(0));
+      }
+    }
+    if (mIndicator != null) {
+      mIndicator.getHostView().forceLayout();
+      mIndicator.getHostView().requestLayout();
+    }
+  }
+
+  @Override
+  public void setLayout(WXComponent component) {
+    if (mAdapter != null) {
+      mAdapter.setLayoutDirectionRTL(this.isLayoutRTL());
+    }
+    super.setLayout(component);
+  }
+
+  @Override
+  public void remove(WXComponent child, boolean destroy) {
+    if (child == null || child.getHostView() == null || mAdapter == null) {
+      return;
+    }
+
+    mAdapter.removePageView(child.getHostView());
+    hackTwoItemsInfiniteScroll();
+    super.remove(child,destroy);
+  }
+
+  @Override
+  public void destroy() {
+    super.destroy();
+    if (mViewPager != null) {
+      mViewPager.stopAutoScroll();
+      mViewPager.removeAllViews();
+      mViewPager.destory();
+    }
+  }
+
+  @Override
+  public void onActivityResume() {
+    super.onActivityResume();
+    if (mViewPager != null && mViewPager.isAutoScroll()) {
+      mViewPager.startAutoScroll();
+    }
+  }
+
+  @Override
+  public void onActivityStop() {
+    super.onActivityStop();
+    if (mViewPager != null) {
+      mViewPager.pauseAutoScroll();
+    }
+  }
+
+  public void addIndicator(WXIndicator indicator) {
+    FrameLayout root = getHostView();
+    if (root == null) {
+      return;
+    }
+    mIndicator = indicator;
+    mIndicator.setShowIndicators(mShowIndicators);
+    WXCircleIndicator indicatorView = indicator.getHostView();
+    if (indicatorView != null) {
+      indicatorView.setCircleViewPager(mViewPager);
+      // indicatorView.setOnPageChangeListener(mPageChangeListener);  // commented for twice onChange() called when do slide.
+      root.addView(indicatorView);
+    }
+
+  }
+
+
+  private int getInitIndex(){
+    Object index = getAttrs().get(Constants.Name.INDEX);
+    int select = WXUtils.getInteger(index, initIndex);
+    if(mAdapter == null || mAdapter.getCount() == 0){
+      return  0;
+    }
+    if(select >= mAdapter.getRealCount()){
+      select = select%mAdapter.getRealCount();
+    }
+
+    return select;
+  }
+
+  private int getRealIndex(int idx) {
+    int retIdx = idx;
+
+    if (mAdapter.getRealCount() > 0) {
+      if(idx >= mAdapter.getRealCount()) retIdx = mAdapter.getRealCount() - 1;
+      if (isLayoutRTL()) {
+        retIdx = mAdapter.getRealCount() - 1 - retIdx;
+      }
+    }
+    retIdx = retIdx + 0;
+    return retIdx;
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.VALUE:
+        String value = WXUtils.getString(param, null);
+        if (value != null) {
+          setValue(value);
+        }
+        return true;
+      case Constants.Name.AUTO_PLAY:
+        String aotu_play = WXUtils.getString(param, null);
+        if (aotu_play != null) {
+          setAutoPlay(aotu_play);
+        }
+        return true;
+      case Constants.Name.SHOW_INDICATORS:
+        String indicators = WXUtils.getString(param, null);
+        if (indicators != null) {
+          setShowIndicators(indicators);
+        }
+        return true;
+      case Constants.Name.INTERVAL:
+        Integer interval = WXUtils.getInteger(param, null);
+        if (interval != null) {
+          setInterval(interval);
+        }
+        return true;
+      case Constants.Name.INDEX:
+        Integer index = WXUtils.getInteger(param, null);
+        if (index != null) {
+          setIndex(index);
+        }
+        return true;
+      case Constants.Name.OFFSET_X_ACCURACY:
+        Float accuracy = WXUtils.getFloat(param, 0.1f);
+        if (accuracy != 0) {
+          setOffsetXAccuracy(accuracy);
+        }
+        return true;
+      case Constants.Name.SCROLLABLE:
+        boolean scrollable = WXUtils.getBoolean(param, true);
+        setScrollable(scrollable);
+        return true;
+      case Constants.Name.KEEP_INDEX:
+        this.keepIndex = WXUtils.getBoolean(param, false);
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @Deprecated
+  @WXComponentProp(name = Constants.Name.VALUE)
+  public void setValue(String value) {
+    if (value == null || getHostView() == null) {
+      return;
+    }
+    int i;
+    try {
+      i = Integer.parseInt(value);
+    } catch (NumberFormatException e) {
+      WXLogUtils.e("", e);
+      return;
+    }
+
+    setIndex(i);
+  }
+
+  @WXComponentProp(name = Constants.Name.AUTO_PLAY)
+  public void setAutoPlay(String autoPlay) {
+    if (TextUtils.isEmpty(autoPlay) || autoPlay.equals("false")) {
+      mViewPager.stopAutoScroll();
+    } else {
+      mViewPager.stopAutoScroll();
+      mViewPager.startAutoScroll();
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.SHOW_INDICATORS)
+  public void setShowIndicators(String show) {
+    if (TextUtils.isEmpty(show) || show.equals("false")) {
+      mShowIndicators = false;
+    } else {
+      mShowIndicators = true;
+    }
+
+    if (mIndicator == null) {
+      return;
+    }
+    mIndicator.setShowIndicators(mShowIndicators);
+  }
+
+  @WXComponentProp(name = Constants.Name.INTERVAL)
+  public void setInterval(int intervalMS) {
+    if (mViewPager != null && intervalMS > 0) {
+      mViewPager.setIntervalTime(intervalMS);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.INDEX)
+  public void setIndex(int index) {
+    if (mViewPager != null && mAdapter != null) {
+      if (index >= mAdapter.getRealCount() || index < 0) {
+        initIndex = index;
+        return;
+      }
+
+      index = getRealIndex(index);
+      mViewPager.setCurrentItem(index);
+      if (mIndicator != null && mIndicator.getHostView() != null
+              && mIndicator.getHostView().getRealCurrentItem() != index) {
+        //OnPageChangeListener not triggered
+        WXLogUtils.d("setIndex >>>> correction indicator to " + index);
+        mIndicator.getHostView().setRealCurrentItem(index);
+        mIndicator.getHostView().invalidate();
+
+        if (mPageChangeListener != null && mAdapter != null) {
+          mPageChangeListener.onPageSelected(mAdapter.getFirst() + index);
+        }
+      }
+    }
+  }
+  @WXComponentProp(name = Constants.Name.SCROLLABLE)
+  public void setScrollable(boolean scrollable) {
+    if (mViewPager != null && mAdapter != null) {
+      mViewPager.setScrollable(scrollable);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.OFFSET_X_ACCURACY)
+  public void setOffsetXAccuracy(float accuracy) {
+    this.offsetXAccuracy = accuracy;
+  }
+
+  protected class SliderPageChangeListener implements OnPageChangeListener {
+
+    private int lastPos = -1;
+
+    @Override
+    public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
+
+    }
+
+    @Override
+    public void onPageSelected(int pos) {
+      if (mAdapter.getRealPosition(pos) == lastPos) {
+        return;
+      }
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.d("onPageSelected >>>>" + mAdapter.getRealPosition(pos) + " lastPos: " + lastPos);
+      }
+      if (mAdapter == null || mAdapter.getRealCount() == 0) {
+        return;
+      }
+
+      int realPosition = mAdapter.getRealPosition(pos);
+      if (mChildren == null || realPosition >= mChildren.size()) {
+        return;
+      }
+
+      if (getEvents().size() == 0) {
+        return;
+      }
+      WXEvent event = getEvents();
+      String ref = getRef();
+      if (event.contains(Constants.Event.CHANGE) && WXViewUtils.onScreenArea(getHostView())) {
+        params.put(INDEX, realPosition);
+
+        Map<String, Object> domChanges = new HashMap<>();
+        Map<String, Object> attrsChanges = new HashMap<>();
+        attrsChanges.put(INDEX, realPosition);
+        domChanges.put("attrs", attrsChanges);
+        WXSDKManager.getInstance().fireEvent(getInstanceId(), ref,
+            Constants.Event.CHANGE, params, domChanges);
+      }
+
+      mViewPager.requestLayout();
+      getHostView().invalidate();
+      lastPos = mAdapter.getRealPosition(pos);
+    }
+
+    @Override
+    public void onPageScrollStateChanged(int arg0) {
+      FrameLayout root = getHostView();
+      if (null != root) {
+        root.invalidate();
+      }
+    }
+  }
+
+  protected static class SliderOnScrollListener implements OnPageChangeListener {
+    private float lastPositionOffset = 99f;
+    private int selectedPosition;
+    private WXSlider target;
+
+    public SliderOnScrollListener(WXSlider target) {
+      this.target = target;
+      this.selectedPosition = target.mViewPager.superGetCurrentItem();
+    }
+
+    @Override
+    public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
+      if (lastPositionOffset == 99f) {
+        lastPositionOffset = positionOffset;
+        return;
+      }
+
+      float offset = positionOffset - lastPositionOffset;
+
+      if (Math.abs(offset) >= target.offsetXAccuracy) {
+        if (position == selectedPosition) {
+          //slide to left. positionOffset[0 -> 1]
+          Map<String,Object> event = new HashMap<>(1);
+          event.put(Constants.Name.OFFSET_X_RATIO, -positionOffset);
+          target.fireEvent(Constants.Event.SCROLL, event);
+        } else if (position < selectedPosition) {
+          //slide to right. positionOffset[1 -> 0]
+          Map<String,Object> event = new HashMap<>(1);
+          event.put(Constants.Name.OFFSET_X_RATIO, (1f - positionOffset));
+          target.fireEvent(Constants.Event.SCROLL, event);
+        }
+        lastPositionOffset = positionOffset;
+      }
+    }
+
+    @Override
+    public void onPageSelected(int position) {
+      selectedPosition = position;
+    }
+
+    @Override
+    public void onPageScrollStateChanged(int state) {
+
+      /**
+       * @homeblog@vip.qq.com
+       *
+       *  add scrollstart & scrollend event
+       *
+       */
+      switch (state) {
+        case ViewPager.SCROLL_STATE_IDLE:
+          lastPositionOffset = 99f;
+          target.fireEvent("scrollend");
+          break;
+        case ViewPager.SCROLL_STATE_DRAGGING:
+          target.fireEvent("scrollstart");
+          break;
+        case ViewPager.SCROLL_STATE_SETTLING:
+          break;
+
+      }
+    }
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  private void hackTwoItemsInfiniteScroll() {
+    if (mViewPager == null || mAdapter == null) {
+      return;
+    }
+    if (isInfinite) {
+      if (mAdapter.getRealCount() == 2) {
+        final GestureDetector gestureDetector = new GestureDetector(getContext(), new FlingGestureListener(mViewPager));
+        mViewPager.setOnTouchListener(new View.OnTouchListener() {
+          @Override
+          public boolean onTouch(View v, MotionEvent event) {
+            return gestureDetector.onTouchEvent(event);
+          }
+        });
+      } else {
+        mViewPager.setOnTouchListener(null);
+      }
+    }
+  }
+
+  private static class FlingGestureListener extends GestureDetector.SimpleOnGestureListener {
+    private static final int SWIPE_MIN_DISTANCE = WXViewUtils.dip2px(50);
+    private static final int SWIPE_MAX_OFF_PATH = WXViewUtils.dip2px(250);
+    private static final int SWIPE_THRESHOLD_VELOCITY = WXViewUtils.dip2px(200);
+    private WeakReference<WXCircleViewPager> pagerRef;
+
+    FlingGestureListener(WXCircleViewPager pager) {
+      this.pagerRef = new WeakReference<>(pager);
+    }
+
+    @Override
+    public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
+      WXCircleViewPager mViewPager = pagerRef.get();
+      if (mViewPager == null) {
+        return false;
+      }
+
+      try {
+        if (Math.abs(e1.getY() - e2.getY()) > SWIPE_MAX_OFF_PATH) {
+          return false;
+        }
+
+        if(e1.getX() - e2.getX() > SWIPE_MIN_DISTANCE
+                && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY
+                && mViewPager.superGetCurrentItem() == 1) {
+          // right to left swipe
+          mViewPager.setCurrentItem(0, false);
+          return true;
+        } else if (e2.getX() - e1.getX() > SWIPE_MIN_DISTANCE
+                && Math.abs(velocityX) > SWIPE_THRESHOLD_VELOCITY
+                && mViewPager.superGetCurrentItem() == 0) {
+          // left to right swipe
+          mViewPager.setCurrentItem(1, false);
+          return true;
+        }
+      } catch (Exception e) {
+        // ignore
+      }
+      return false;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXSliderNeighbor.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXSliderNeighbor.java
new file mode 100644
index 0000000..cfd7d0b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXSliderNeighbor.java
@@ -0,0 +1,413 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+import android.support.v4.view.ViewPager;
+import android.text.TextUtils;
+import android.view.Gravity;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.FrameLayout;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.BaseFrameLayout;
+import org.apache.weex.ui.view.WXCircleIndicator;
+import org.apache.weex.ui.view.WXCirclePageAdapter;
+import org.apache.weex.ui.view.WXCircleViewPager;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.List;
+
+/**
+ * Known Issus: In auto play mode, neighbor view not scaled or aplhaed rarely.
+ *
+ * Created by xingjiu on 16/8/18.
+ */
+public class WXSliderNeighbor extends WXSlider {
+    public static final String NEIGHBOR_SCALE = "neighborScale"; // the init scale of neighbor page
+    public static final String NEIGHBOR_ALPHA = "neighborAlpha"; // the init alpha of neighbor page
+    public static final String NEIGHBOR_SPACE = "neighborSpace"; // the init space of neighbor page
+    public static final String CURRENT_ITEM_SCALE = "currentItemScale"; // the scale of middle item
+
+    private static final int DEFAULT_NEIGHBOR_SPACE = 25;
+    private static final float DEFAULT_NEIGHBOR_SCALE = 0.8F;
+    private static final float DEFAULT_NEIGHBOR_ALPHA = 0.6F;
+    private static final float DEFAULT_CURRENT_ITEM_SCALE = 0.9F;
+
+    private float mNeighborScale = DEFAULT_NEIGHBOR_SCALE;
+    private float mNeighborAlpha = DEFAULT_NEIGHBOR_ALPHA;
+    private float mNeighborSpace = DEFAULT_NEIGHBOR_SPACE;
+    private float mCurrentItemScale = DEFAULT_CURRENT_ITEM_SCALE;
+
+    private ZoomTransformer mCachedTransformer;
+
+    public WXSliderNeighbor(
+        WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+        super(instance, parent, basicComponentData);
+    }
+
+    public static class Creator implements ComponentCreator {
+        public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+            return new WXSliderNeighbor(instance, parent, basicComponentData);
+        }
+    }
+
+    @Override
+    public void bindData(WXComponent component) {
+        super.bindData(component);
+    }
+
+    @Override
+    protected BaseFrameLayout initComponentHostView(@NonNull Context context) {
+        BaseFrameLayout view = new BaseFrameLayout(context);
+
+        // init view pager
+        FrameLayout.LayoutParams pagerParams = new FrameLayout.LayoutParams(
+                FrameLayout.LayoutParams.MATCH_PARENT, FrameLayout.LayoutParams.MATCH_PARENT);
+        pagerParams.gravity = Gravity.CENTER;
+        mViewPager = new WXCircleViewPager(getContext());
+        mViewPager.setLayoutParams(pagerParams);
+
+        // init adapter
+        mAdapter = new WXCirclePageAdapter();
+        mViewPager.setAdapter(mAdapter);
+
+        // add to parent
+        view.addView(mViewPager);
+        mViewPager.addOnPageChangeListener(mPageChangeListener);
+
+        mViewPager.setOverScrollMode(View.OVER_SCROLL_NEVER);
+        registerActivityStateListener();
+
+        mViewPager.setPageTransformer(false, createTransformer());
+
+        return view;
+    }
+
+    ZoomTransformer createTransformer() {
+        if(mCachedTransformer == null) {
+            mCachedTransformer = new ZoomTransformer();
+        }
+        return mCachedTransformer;
+    }
+
+    @Override
+    public void addSubView(View view, final int index) {
+        if (view == null || mAdapter == null) {
+            return;
+        }
+
+        if (view instanceof WXCircleIndicator) {
+            return;
+        }
+
+        FrameLayout wrapper = new FrameLayout(getContext());
+        FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
+        params.gravity = Gravity.CENTER;
+        view.setLayoutParams(params);
+        wrapper.addView(view);
+        super.addSubView(wrapper,index);
+
+        updateAdapterScaleAndAlpha(mNeighborAlpha, mNeighborScale); // we need to set neighbor view status when added.
+
+        mViewPager.postDelayed(WXThread.secure(new Runnable() {
+            @Override
+            public void run() {
+                try {
+                    if(mViewPager.getRealCount() > 0 && index > 2) { // index > 2 mean more than two times, then need a fake drag
+                        // prevent a bug of init status. ZoomTransformer no called as excepted.
+                        mViewPager.beginFakeDrag();
+                        mViewPager.fakeDragBy(1); // must be 1
+                    }
+                }catch (IndexOutOfBoundsException e){
+                    // do nothing
+                } finally {
+                    try {
+                        mViewPager.endFakeDrag();
+                    }catch (Exception e) {
+                        // do nothing
+                    }
+                }
+            }
+        }), 50);
+    }
+
+    private void updateScaleAndAlpha(View view, float alpha, float scale) {
+        if(null == view) {
+            return;
+        }
+        if(alpha >= 0 && view.getAlpha() != alpha) {
+            view.setAlpha(alpha);
+        }
+        if(scale >= 0 && view.getScaleX() != scale) {
+            view.setScaleX(scale);
+            view.setScaleY(scale);
+        }
+    }
+
+    private void updateAdapterScaleAndAlpha(final float alpha, final float scale) {
+        final List<View> pageViews = mAdapter.getViews();
+        final int curPos = mViewPager.getCurrentItem();
+
+        if(pageViews.size() > 0) {
+            final View currentPage = pageViews.get(curPos);
+            updateScaleAndAlpha(((ViewGroup)currentPage).getChildAt(0), 1.0F, mCurrentItemScale);
+
+            if(pageViews.size() < 2) {
+                return;
+            }
+            //make sure View's width & height are measured.
+            currentPage.postDelayed(WXThread.secure(new Runnable() {
+                @Override
+                public void run() {
+                    //change left and right page's translation
+                    updateNeighbor(currentPage, alpha, scale);
+
+                }
+            }), 17);
+
+            // make sure only display view current, left, right.
+            int left = (curPos == 0) ? pageViews.size()-1 : curPos-1;
+            int right = (curPos == pageViews.size()-1) ? 0 : curPos+1;
+            for(int i =0; i<mAdapter.getRealCount(); i++) {
+                if(i != left && i != curPos && i != right) {
+                    ((ViewGroup)pageViews.get(i)).getChildAt(0).setAlpha(0F);
+                }
+            }
+        }
+    }
+
+    private void updateNeighbor(View currentPage, final float alpha, final float scale) {
+        final List<View> pageViews = mAdapter.getViews();
+        final int curPos = mViewPager.getCurrentItem();
+
+        float translation = calculateTranslation(currentPage);
+        int left = (curPos == 0) ? pageViews.size()-1 : curPos-1;
+        View leftPage = pageViews.get(left);
+        int right = (curPos == pageViews.size()-1) ? 0 : curPos+1;
+        View rightPage = pageViews.get(right);
+
+        if(pageViews.size() == 2) {
+            if(curPos == 0) {
+                moveRight(rightPage, translation, alpha, scale);
+            }else if(curPos == 1) {
+                moveLeft(leftPage, translation, alpha, scale);
+            }
+        } else {
+            moveLeft(leftPage, translation, alpha, scale);
+            moveRight(rightPage, translation, alpha, scale);
+        }
+    }
+
+    private void moveLeft(View page, float translation, float alpha, float scale) {
+        updateScaleAndAlpha(((ViewGroup)page).getChildAt(0), alpha, scale);
+        page.setTranslationX(translation);
+        ((ViewGroup)page).getChildAt(0).setTranslationX(translation);
+    }
+    private void moveRight(View page, float translation, float alpha, float scale) {
+        moveLeft(page, -translation, alpha, scale);
+    }
+
+    @WXComponentProp(name = NEIGHBOR_SCALE)
+    public void setNeighborScale(String input) {
+        float neighborScale = DEFAULT_NEIGHBOR_SCALE;
+        if (!TextUtils.isEmpty(input)) {
+            try {
+                neighborScale = Float.parseFloat(input);
+            } catch (NumberFormatException e) {
+            }
+        }
+
+        // addSubView is called before setProperty, so we need to modify the neighbor view in mAdapter.
+        if(this.mNeighborScale != neighborScale) {
+            this.mNeighborScale = neighborScale;
+            updateAdapterScaleAndAlpha(-1, neighborScale);
+        }
+    }
+
+    @WXComponentProp(name = NEIGHBOR_ALPHA)
+    public void setNeighborAlpha(String input) {
+        float neighborAlpha = DEFAULT_NEIGHBOR_ALPHA;
+        if (!TextUtils.isEmpty(input)) {
+            try {
+                neighborAlpha = Float.parseFloat(input);
+            } catch (NumberFormatException e) {
+            }
+        }
+
+        // The same work as setNeighborScale()
+        if(this.mNeighborAlpha != neighborAlpha) {
+            this.mNeighborAlpha = neighborAlpha;
+            updateAdapterScaleAndAlpha(neighborAlpha, -1);
+        }
+    }
+
+    @WXComponentProp(name = NEIGHBOR_SPACE)
+    @SuppressWarnings("unused")
+    public void setNeighborSpace(String input) {
+        float neighborSpace = DEFAULT_NEIGHBOR_SPACE;
+        if (!TextUtils.isEmpty(input)) {
+            try {
+                neighborSpace = Float.parseFloat(input);
+            } catch (NumberFormatException e) {
+            }
+        }
+
+        if(this.mNeighborSpace != neighborSpace) {
+            this.mNeighborSpace = neighborSpace;
+        }
+    }
+
+    @WXComponentProp(name = CURRENT_ITEM_SCALE)
+    @SuppressWarnings("unused")
+    public void setCurrentItemScale(String input) {
+        float currentItemScale = DEFAULT_CURRENT_ITEM_SCALE;
+        if (!TextUtils.isEmpty(input)) {
+            try {
+                currentItemScale = Float.parseFloat(input);
+            } catch (NumberFormatException e) {
+            }
+        }
+
+        if(this.mCurrentItemScale != currentItemScale) {
+            this.mCurrentItemScale = currentItemScale;
+            updateAdapterScaleAndAlpha(-1, -1);
+        }
+    }
+
+    @Override
+    protected boolean setProperty(String key, Object param) {
+        String input;
+        switch (key) {
+            case NEIGHBOR_SCALE:
+                input = WXUtils.getString(param, null);
+                if (input != null) {
+                    setNeighborScale(input);
+                }
+                return true;
+            case NEIGHBOR_ALPHA:
+                input = WXUtils.getString(param, null);
+                if (input != null) {
+                    setNeighborAlpha(input);
+                }
+                return true;
+            case NEIGHBOR_SPACE:
+                input = WXUtils.getString(param, null);
+                if (input != null) {
+                    setNeighborSpace(input);
+                }
+                return true;
+            case CURRENT_ITEM_SCALE:
+                input = WXUtils.getString(param, null);
+                if (input != null) {
+                    setCurrentItemScale(input);
+                }
+                return true;
+        }
+        return super.setProperty(key, param);
+    }
+
+    /**
+     * we need add translation for left and right card view.
+     * */
+    private float calculateTranslation(@NonNull View hostPage) {
+        if(!(hostPage instanceof ViewGroup)) {
+            return 0;
+        }
+        View realView = ((ViewGroup)hostPage).getChildAt(0);
+        float translation = (hostPage.getMeasuredWidth()-realView.getMeasuredWidth()*mNeighborScale)/4;
+        translation += ((hostPage.getMeasuredWidth()-realView.getMeasuredWidth() * mCurrentItemScale)/2 - WXViewUtils.getRealPxByWidth(mNeighborSpace, getInstance().getInstanceViewPortWidth()))/2 ;
+        return translation;
+    }
+
+    // Here is the trick.
+     class ZoomTransformer implements ViewPager.PageTransformer {
+        @Override
+        public void transformPage(View page, float position) {
+            int pagePosition = mAdapter.getPagePosition(page);
+            int curPosition = mViewPager.getCurrentItem();
+
+            int realCount = mAdapter.getRealCount();
+
+            boolean ignore = false;
+            if(curPosition != 0 && curPosition != realCount - 1 && Math.abs(pagePosition - curPosition) > 1)  {
+                ignore = true;
+            }
+            if(curPosition == 0 && pagePosition < realCount - 1 && pagePosition > 1) {
+                ignore = true;
+            }
+            if(curPosition == realCount - 1 && pagePosition < realCount - 2 && pagePosition > 0) {
+                ignore = true;
+            }
+            // just transfer the neighbor(left & right) page.
+            if(ignore) {
+                return;
+            }
+
+            View realView = ((ViewGroup)page).getChildAt(0);
+            if(realView == null){
+                return;
+            }
+            float alpha, scale;
+
+            if(position <= (-realCount + 1)) {
+                position = position + realCount;
+            }
+            if(position >= realCount - 1) {
+                position = position - realCount;
+            }
+
+            if (position >= -1 && position <= 1) {
+                float factor = Math.abs(Math.abs(position) - 1);
+                scale = mNeighborScale + factor * (mCurrentItemScale - mNeighborScale);
+                alpha = (1- mNeighborAlpha) * factor + mNeighborAlpha;
+
+                float translation = calculateTranslation(page);
+                if(position > 0){
+                    translation = (position*translation);
+                    realView.setTranslationX(-translation);
+                    page.setTranslationX(-translation);
+                }else if(position == 0){
+                    page.setTranslationX(0);
+                    realView.setTranslationX(0);
+                    updateAdapterScaleAndAlpha(mNeighborAlpha, mNeighborScale);
+                }else{
+                    if(realCount == 2 && Math.abs(position) == 1) {
+                        return;
+                    }
+                    translation = (-position*translation);
+                    realView.setTranslationX(translation);
+                    page.setTranslationX(translation);
+                }
+                realView.setScaleX(scale);
+                realView.setScaleY(scale);
+                realView.setAlpha(alpha);
+            }
+
+        }
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXSwitch.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXSwitch.java
new file mode 100644
index 0000000..32c06a2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXSwitch.java
@@ -0,0 +1,143 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+import android.view.View;
+import android.widget.CompoundButton;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.layout.ContentBoxMeasurement;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXSwitchView;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.HashMap;
+import java.util.Map;
+
+@Component(lazyload = false)
+
+public class WXSwitch extends WXComponent<WXSwitchView> {
+
+  private CompoundButton.OnCheckedChangeListener mListener;
+
+  @Deprecated
+  public WXSwitch(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+  public WXSwitch(final WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+    super(instance, parent, isLazy, basicComponentData);
+    setContentBoxMeasurement(new ContentBoxMeasurement() {
+      /** uiThread = false **/
+      @Override
+      public void measureInternal(float width, float height, int widthMeasureMode, int heightMeasureMode) {
+        mMeasureWidth = 0;
+        mMeasureHeight = 0;
+        try {
+          WXSwitchView wxSwitchView = new WXSwitchView(instance.getContext());
+          int widthSpec, heightSpec;
+          heightSpec = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
+          if (Float.isNaN(width)) {
+            widthSpec = View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED);
+          } else {
+            widthSpec = View.MeasureSpec.makeMeasureSpec((int) width, View.MeasureSpec.AT_MOST);
+          }
+
+          wxSwitchView.measure(widthSpec, heightSpec);
+          mMeasureWidth = wxSwitchView.getMeasuredWidth();
+          mMeasureHeight = wxSwitchView.getMeasuredHeight();
+        } catch (RuntimeException e) {
+          WXLogUtils.e(WXLogUtils.getStackTrace(e));
+        }
+      }
+
+      /** uiThread = false **/
+      @Override
+      public void layoutBefore() {
+      }
+
+      /** uiThread = false **/
+      @Override
+      public void layoutAfter(float computedWidth, float computedHeight) {
+      }
+    });
+  }
+
+  @Override
+  protected WXSwitchView initComponentHostView(@NonNull Context context) {
+    return new WXSwitchView(context);
+  }
+
+
+  @Override
+  public void addEvent(String type) {
+    super.addEvent(type);
+    if (type != null && type.equals(Constants.Event.CHANGE) && getHostView() != null) {
+      if (mListener == null) {
+        mListener = new CompoundButton.OnCheckedChangeListener() {
+          @Override
+          public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
+            Map<String, Object> params = new HashMap<>(2);
+            params.put("value", isChecked);
+
+            Map<String, Object> domChanges = new HashMap<>();
+            Map<String, Object> attrsChanges = new HashMap<>();
+            attrsChanges.put("checked",Boolean.toString(isChecked));
+            domChanges.put("attrs",attrsChanges);
+            fireEvent(Constants.Event.CHANGE, params,domChanges);
+          }
+        };
+      }
+      getHostView().setOnCheckedChangeListener(mListener);
+    }
+  }
+
+  @Override
+  protected void removeEventFromView(String type) {
+    super.removeEventFromView(type);
+    if (getHostView() != null && Constants.Event.CHANGE.equals(type)) {
+      getHostView().setOnCheckedChangeListener(null);
+    }
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.CHECKED:
+        Boolean result = WXUtils.getBoolean(param, null);
+        if (result != null) {
+          setChecked(result);
+        }
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @WXComponentProp(name = Constants.Name.CHECKED)
+  public void setChecked(boolean checked) {
+    getHostView().setOnCheckedChangeListener(null);
+    getHostView().setChecked(checked);
+    getHostView().setOnCheckedChangeListener(mListener);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXText.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXText.java
new file mode 100644
index 0000000..729414b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXText.java
@@ -0,0 +1,241 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.support.annotation.NonNull;
+import android.support.v4.content.LocalBroadcastManager;
+import android.text.Layout;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.layout.measurefunc.TextContentBoxMeasurement;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.flat.FlatComponent;
+import org.apache.weex.ui.flat.widget.TextWidget;
+import org.apache.weex.ui.view.WXTextView;
+import org.apache.weex.utils.FontDO;
+import org.apache.weex.utils.TypefaceUtil;
+import org.apache.weex.utils.WXLogUtils;
+import java.lang.reflect.InvocationTargetException;
+
+/**
+ * Text component
+ */
+@Component(lazyload = false)
+public class WXText extends WXComponent<WXTextView> implements FlatComponent<TextWidget> {
+
+  private TextWidget mTextWidget;
+
+  /**
+   * The default text size
+   **/
+  public static final int sDEFAULT_SIZE = 32;
+  private BroadcastReceiver mTypefaceObserver;
+  private String mFontFamily;
+
+  @Override
+  public boolean promoteToView(boolean checkAncestor) {
+    if (null != getInstance().getFlatUIContext()) {
+      return getInstance().getFlatUIContext().promoteToView(this, checkAncestor, WXText.class);
+    }
+    return false;
+  }
+
+  @Override
+  @NonNull
+  public TextWidget getOrCreateFlatWidget() {
+    if (mTextWidget == null) {
+      mTextWidget = new TextWidget(getInstance().getFlatUIContext());
+    }
+    return mTextWidget;
+  }
+
+  @Override
+  public boolean isVirtualComponent() {
+    return !promoteToView(true);
+  }
+
+  public static class Creator implements ComponentCreator {
+    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+      return new WXText(instance, parent, basicComponentData);
+    }
+  }
+
+  @Deprecated
+  public WXText(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, basicComponentData);
+  }
+
+  public WXText(WXSDKInstance instance,
+                WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+    setContentBoxMeasurement(new TextContentBoxMeasurement(this));
+  }
+
+  @Override
+  protected WXTextView initComponentHostView(@NonNull Context context) {
+    WXTextView textView = new WXTextView(context);
+    textView.holdComponent(this);
+    return textView;
+  }
+
+  @Override
+  public void updateExtra(Object extra) {
+    super.updateExtra(extra);
+    if(extra instanceof Layout) {
+      final Layout layout = (Layout) extra;
+      if (!promoteToView(true)) {
+        getOrCreateFlatWidget().updateTextDrawable(layout);
+      } else if (getHostView() != null && !extra.equals(getHostView().getTextLayout())) {
+        getHostView().setTextLayout(layout);
+        getHostView().invalidate();
+      }
+    }
+  }
+
+  @Override
+  protected void setAriaLabel(String label) {
+    WXTextView text = getHostView();
+    if (text != null) {
+      text.setAriaLabel(label);
+    }
+  }
+
+  @Override
+  public void refreshData(WXComponent component) {
+    super.refreshData(component);
+    if (component instanceof WXText) {
+      updateExtra(component.getExtra());
+    }
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.LINES:
+      case Constants.Name.FONT_SIZE:
+      case Constants.Name.FONT_WEIGHT:
+      case Constants.Name.FONT_STYLE:
+      case Constants.Name.COLOR:
+      case Constants.Name.TEXT_DECORATION:
+      case Constants.Name.TEXT_ALIGN:
+      case Constants.Name.TEXT_OVERFLOW:
+      case Constants.Name.LINE_HEIGHT:
+      case Constants.Name.VALUE:
+        return true;
+      case Constants.Name.FONT_FAMILY:
+        if (param != null) {
+          registerTypefaceObserver(param.toString());
+        }
+        return true;
+      default:
+        return super.setProperty(key, param);
+    }
+  }
+
+  @Override
+  protected Object convertEmptyProperty(String propName, Object originalValue) {
+    switch (propName) {
+      case Constants.Name.FONT_SIZE:
+        return WXText.sDEFAULT_SIZE;
+      case Constants.Name.COLOR:
+        return "black";
+    }
+    return super.convertEmptyProperty(propName, originalValue);
+  }
+
+  @Override
+  protected void createViewImpl() {
+    if(promoteToView(true)) {
+      super.createViewImpl();
+    }
+  }
+
+  @Override
+  public void destroy() {
+    super.destroy();
+    if (WXEnvironment.getApplication() != null && mTypefaceObserver != null) {
+      WXLogUtils.d("WXText", "Unregister the typeface observer");
+      LocalBroadcastManager.getInstance(WXEnvironment.getApplication()).unregisterReceiver(mTypefaceObserver);
+      mTypefaceObserver = null;
+    }
+  }
+
+  private void registerTypefaceObserver(String desiredFontFamily) {
+    if (WXEnvironment.getApplication() == null) {
+      WXLogUtils.w("WXText", "ApplicationContent is null on register typeface observer");
+      return;
+    }
+    mFontFamily = desiredFontFamily;
+    if (mTypefaceObserver != null) {
+      return;
+    }
+
+    mTypefaceObserver = new BroadcastReceiver() {
+      @Override
+      public void onReceive(Context context, Intent intent) {
+        String fontFamily = intent.getStringExtra("fontFamily");
+        if (!mFontFamily.equals(fontFamily)) {
+          return;
+        }
+
+        FontDO fontDO = TypefaceUtil.getFontDO(fontFamily);
+        if (fontDO != null && fontDO.getTypeface() != null && getHostView() != null) {
+          WXTextView hostView = getHostView();
+          Layout layout = hostView.getTextLayout();
+          if (layout != null) {
+            layout.getPaint().setTypeface(fontDO.getTypeface());
+          } else {
+            WXLogUtils.d("WXText", "Layout not created");
+          }
+          WXBridgeManager
+              .getInstance().markDirty(getInstanceId(), getRef(), true);
+          forceRelayout();
+
+        }
+      }
+    };
+
+    LocalBroadcastManager.getInstance(WXEnvironment.getApplication()).registerReceiver(mTypefaceObserver, new IntentFilter(TypefaceUtil.ACTION_TYPE_FACE_AVAILABLE));
+  }
+
+
+  @Override
+  protected void layoutDirectionDidChanged(boolean isRTL) {
+    forceRelayout();
+  }
+
+  private void forceRelayout(){
+    WXBridgeManager.getInstance().post(new Runnable() {
+      @Override
+      public void run() {
+        if(contentBoxMeasurement instanceof TextContentBoxMeasurement){
+          ((TextContentBoxMeasurement) contentBoxMeasurement).forceRelayout();
+        }
+      }
+    });
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXTextDecoration.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXTextDecoration.java
new file mode 100644
index 0000000..5f6db1b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXTextDecoration.java
@@ -0,0 +1,26 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+public enum WXTextDecoration {
+  INVALID,
+  NONE,
+  UNDERLINE,
+  LINETHROUGH,
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXVContainer.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXVContainer.java
new file mode 100644
index 0000000..6b238e4
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXVContainer.java
@@ -0,0 +1,629 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.content.Intent;
+import android.support.annotation.Nullable;
+import android.support.v4.view.ViewCompat;
+import android.util.Pair;
+import android.view.Menu;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewParent;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXImageView;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.ArrayList;
+
+/**
+ * All container components must implement this class
+ */
+public abstract class WXVContainer<T extends ViewGroup> extends WXComponent<T> {
+
+  private static final String TAG = "WXVContainer";
+  protected ArrayList<WXComponent> mChildren = new ArrayList<>();
+  private BoxShadowHost mBoxShadowHost;
+
+  @Deprecated
+  public WXVContainer(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+  @Deprecated
+  public WXVContainer(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  public WXVContainer(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  /**
+   * Container will get focus before any of its descendants.
+   */
+  public void interceptFocus() {
+    T host = getHostView();
+    if (host != null) {
+      host.setFocusable(true);
+      host.setFocusableInTouchMode(true);
+      host.setDescendantFocusability(ViewGroup.FOCUS_BEFORE_DESCENDANTS);
+      host.requestFocus();
+    }
+  }
+
+  /**
+   * Container will can not receive focus
+   */
+  public void ignoreFocus() {
+    T host = getHostView();
+    if (host != null) {
+      host.setFocusable(false);
+      host.setFocusableInTouchMode(false);
+      host.clearFocus();
+    }
+  }
+
+  /**
+   * Offset top for children layout.
+   */
+  protected int getChildrenLayoutTopOffset() {
+    return 0;
+  }
+
+  /**
+   * use {@link #getHostView()} instead
+   */
+  @Deprecated
+  public ViewGroup getView() {
+    return getHostView();
+  }
+
+  @Override
+  public void applyLayoutAndEvent(WXComponent component) {
+    if (!isLazy()) {
+      if (component == null) {
+        component = this;
+      }
+      super.applyLayoutAndEvent(component);
+      int count = childCount();
+      for (int i = 0; i < count; i++) {
+        WXComponent child = getChild(i);
+        child.applyLayoutAndEvent(((WXVContainer) component).getChild(i));
+      }
+    }
+  }
+
+  /**
+   * Get or generate new layout parameter for child view
+   */
+  public ViewGroup.LayoutParams getChildLayoutParams(WXComponent child, View childView, int width, int height, int left, int right, int top, int bottom) {
+    ViewGroup.LayoutParams lp = null;
+    if (childView != null) {
+      lp = childView.getLayoutParams();
+    }
+
+    if(lp == null) {
+      lp = new ViewGroup.LayoutParams(width,height);
+    }else{
+      lp.width = width;
+      lp.height = height;
+      if(lp instanceof ViewGroup.MarginLayoutParams){
+        this.setMarginsSupportRTL((ViewGroup.MarginLayoutParams) lp, left, top, right, bottom);
+      }
+    }
+    return lp;
+  }
+
+
+  public Scrollable getFirstScroller() {
+    if (this instanceof Scrollable) {
+      return (Scrollable) this;
+    } else {
+      for (int i = 0; i < getChildCount(); i++) {
+        Scrollable scrollable = getChild(i).getFirstScroller();
+        if (scrollable != null) {
+          return scrollable;
+        }
+      }
+    }
+    return null;
+  }
+
+  @Override
+  public void bindData(WXComponent component) {
+    if (!isLazy()) {
+      if (component == null) {
+        component = this;
+      }
+      super.bindData(component);
+      int count = childCount();
+      for (int i = 0; i < count; i++) {
+        getChild(i).bindData(((WXVContainer) component).getChild(i));
+      }
+    }
+  }
+
+  @Override
+  public void refreshData(WXComponent component) {
+    if (component == null) {
+      component = this;
+    }
+    super.refreshData(component);
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).refreshData(((WXVContainer) component).getChild(i));
+    }
+  }
+
+  /**
+   * return real View
+   */
+  @Override
+  public ViewGroup getRealView() {
+    return (ViewGroup) super.getRealView();
+  }
+
+  @Override
+  public void createViewImpl() {
+    super.createViewImpl();
+    int count = childCount();
+    for (int i = 0; i < count; ++i) {
+      createChildViewAt(i);
+    }
+    if (getHostView() != null) {
+      getHostView().setClipToPadding(false);
+    }
+  }
+
+  @Override
+  public void destroy() {
+    if (mChildren != null) {
+      int count = mChildren.size();
+      for (int i = 0; i < count; ++i) {
+        mChildren.get(i).destroy();
+      }
+      mChildren.clear();
+    }
+    super.destroy();
+  }
+
+  /**
+   * recycle component resources
+   */
+  public void recycled() {
+    if (mChildren != null && !isFixed() && getAttrs().canRecycled()) {
+      int count = mChildren.size();
+      for (int i = 0; i < count; ++i) {
+        mChildren.get(i).recycled();
+      }
+    }
+    super.recycled();
+
+  }
+
+  @Override
+  public View detachViewAndClearPreInfo() {
+    View original = super.detachViewAndClearPreInfo();
+    if (mChildren != null) {
+      int count = childCount();
+      for (int i = 0; i < count; ++i) {
+        mChildren.get(i).detachViewAndClearPreInfo();
+      }
+    }
+    return original;
+  }
+
+  public int childCount() {
+    return mChildren == null ? 0 : mChildren.size();
+  }
+
+  public WXComponent getChild(int index) {
+    if (mChildren == null || index < 0 || index >= mChildren.size()) {
+      //To avoid index out of bounds
+      return null;
+    }
+    return mChildren.get(index);
+  }
+
+  public int getChildCount() {
+    return childCount();
+  }
+
+  public void addChild(WXComponent child) {
+    addChild(child, -1);
+  }
+
+  public void addChild(WXComponent child, int index) {
+    if (child == null || index < -1) {
+      return;
+    }
+    child.mDeepInComponentTree = this.mDeepInComponentTree +1;
+    getInstance().setMaxDomDeep(child.mDeepInComponentTree);
+    int count = mChildren.size();
+    index = index >= count ? -1 : index;
+    if (index == -1) {
+      mChildren.add(child);
+    } else {
+      mChildren.add(index, child);
+    }
+  }
+
+  public final int indexOf(WXComponent comp) {
+    return mChildren.indexOf(comp);
+  }
+
+  public void createChildViewAt(int index) {
+    Pair<WXComponent, Integer> ret = rearrangeIndexAndGetChild(index);
+    if (ret.first != null) {
+      WXComponent child = ret.first;
+      child.createView();
+      if (!child.isVirtualComponent()) {
+        addSubView(child.getHostView(), ret.second);
+      }
+    }
+  }
+
+  protected Pair<WXComponent, Integer> rearrangeIndexAndGetChild(int index) {
+    int indexToCreate = index;
+    if (indexToCreate < 0) {
+      indexToCreate = childCount() - 1;
+    }
+
+    if (indexToCreate < 0) {
+      return new Pair<>(null, indexToCreate);
+    } else {
+      return new Pair<>(getChild(indexToCreate), indexToCreate);
+    }
+  }
+
+  public void addSubView(View child, int index) {
+    if (child == null || getRealView() == null) {
+      return;
+    }
+
+    int count = getRealView().getChildCount();
+    index = index >= count ? -1 : index;
+    if (index == -1) {
+      getRealView().addView(child);
+    } else {
+      getRealView().addView(child, index);
+    }
+    WXSDKInstance instance = getInstance();
+    if (null != instance){
+      instance.getApmForInstance().hasAddView = true;
+    }
+  }
+
+  public void remove(WXComponent child, boolean destroy) {
+    if (child == null || mChildren == null || mChildren.size() == 0) {
+      return;
+    }
+
+    mChildren.remove(child);
+    if (getInstance() != null
+            && getInstance().getRootView() != null
+            && child.isFixed()) {
+      getInstance().removeFixedView(child.getHostView());
+    } else if (getRealView() != null) {
+      if (!child.isVirtualComponent()) {
+        ViewParent parent = null;
+        if(child.getParent() instanceof  WXScroller){
+          if(child.getHostView() != null){
+            parent = child.getHostView().getParent();
+          }
+        }
+        if(parent != null && parent instanceof  ViewGroup){
+          ((ViewGroup) parent).removeView(child.getHostView());
+        }else{
+          getRealView().removeView(child.getHostView());
+        }
+      } else {
+        child.removeVirtualComponent();
+      }
+    }
+    if (destroy) {
+      child.destroy();
+    }
+  }
+
+  @Override
+  public void notifyAppearStateChange(String wxEventType, String direction) {
+    super.notifyAppearStateChange(wxEventType, direction);
+    if (getHostView() == null || mChildren == null) {
+      return;
+    }
+    for (WXComponent component : mChildren) {
+      if (component.getHostView() != null && !(component.getHostView().getVisibility() == View.VISIBLE)) {
+        wxEventType = Constants.Event.DISAPPEAR;
+      }
+      component.notifyAppearStateChange(wxEventType, direction);
+    }
+  }
+
+  /********************************************************
+   *  begin hook Activity life cycle callback             *
+   ********************************************************/
+  @Override
+  public void onActivityCreate() {
+    super.onActivityCreate();
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onActivityCreate();
+    }
+  }
+
+  @Override
+  public void onActivityStart() {
+    super.onActivityStart();
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onActivityStart();
+    }
+
+  }
+
+  @Override
+  public void onActivityPause() {
+    super.onActivityPause();
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onActivityPause();
+    }
+  }
+
+  @Override
+  public void onActivityResume() {
+    super.onActivityResume();
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onActivityResume();
+    }
+  }
+
+  @Override
+  public void onActivityStop() {
+    super.onActivityStop();
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onActivityStop();
+    }
+  }
+
+  @Override
+  public void onActivityDestroy() {
+    super.onActivityDestroy();
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onActivityDestroy();
+    }
+
+  }
+
+  @Override
+  public boolean onActivityBack() {
+    super.onActivityBack();
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onActivityBack();
+    }
+    return false;
+  }
+
+  @Override
+  public void onActivityResult(int requestCode, int resultCode, Intent data) {
+    super.onActivityResult(requestCode, resultCode, data);
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onActivityResult(requestCode, resultCode, data);
+    }
+
+  }
+
+  public boolean onCreateOptionsMenu(Menu menu) {
+    super.onCreateOptionsMenu(menu);
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onCreateOptionsMenu(menu);
+    }
+    return false;
+  }
+
+
+  @Override
+  public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
+    super.onRequestPermissionsResult(requestCode, permissions, grantResults);
+
+    int count = childCount();
+    for (int i = 0; i < count; i++) {
+      getChild(i).onRequestPermissionsResult(requestCode, permissions, grantResults);
+    }
+  }
+
+  @Override
+  public void onRenderFinish(@RenderState int state) {
+    for (int i = 0; i < getChildCount(); i++) {
+      WXComponent child = getChild(i);
+      child.mTraceInfo.uiQueueTime = mTraceInfo.uiQueueTime;
+      child.onRenderFinish(state);
+    }
+    super.onRenderFinish(state);
+  }
+
+  @JSMethod
+  public void releaseImageList(String viewTreeRecycle){
+    if(getHostView() == null
+            || !ViewCompat.isAttachedToWindow(getHostView())
+            || !(getHostView() instanceof  ViewGroup)){
+      return;
+    }
+    boolean isViewTree = WXUtils.getBoolean(viewTreeRecycle, false);
+    if(isViewTree){
+      doViewTreeRecycleImageView(getHostView(), true);
+    }else{
+      int count = getChildCount();
+      for(int i=0; i<count; i++){
+        WXComponent component =  getChild(i);
+        if(component instanceof  WXImage && ((WXImage) component).getHostView() instanceof WXImageView){
+          WXImageView imageView = (WXImageView) component.getHostView();
+          if(imageView != null && ViewCompat.isAttachedToWindow(imageView)){
+            imageView.autoReleaseImage();
+          }
+        }else if(component instanceof  WXVContainer){
+          ((WXVContainer) component).releaseImageList(viewTreeRecycle);
+        }
+      }
+    }
+  }
+
+  @JSMethod
+  public void recoverImageList(String viewTreeRecycle){
+    if(getHostView() == null
+            || !ViewCompat.isAttachedToWindow(getHostView())
+            || !(getHostView() instanceof  ViewGroup)){
+      return;
+    }
+    boolean isViewTree = WXUtils.getBoolean(viewTreeRecycle, false);
+    if(isViewTree){
+      doViewTreeRecycleImageView(getHostView(), false);
+    }else{
+      int count = getChildCount();
+      for(int i=0; i<count; i++){
+        WXComponent component =  getChild(i);
+        if(component instanceof  WXImage && ((WXImage) component).getHostView() instanceof WXImageView){
+          WXImageView imageView = (WXImageView) component.getHostView();
+          if(imageView != null && ViewCompat.isAttachedToWindow(imageView)){
+            imageView.autoRecoverImage();
+          }
+        }else if(component instanceof  WXVContainer){
+          ((WXVContainer) component).recoverImageList(viewTreeRecycle);
+        }
+      }
+    }
+  }
+
+  /**
+   * transverse view tree, and recycle wximageview in container
+   * */
+  private void doViewTreeRecycleImageView(ViewGroup viewGroup, boolean isRelease){
+    int count = viewGroup.getChildCount();
+    for(int i=0; i<count; i++){
+      View view = viewGroup.getChildAt(i);
+      if(view instanceof  WXImageView){
+        if(isRelease){
+          ((WXImageView) view).autoReleaseImage();
+        }else{
+          ((WXImageView) view).autoRecoverImage();
+        }
+      }else if(view instanceof  ViewGroup){
+        doViewTreeRecycleImageView((ViewGroup) view, isRelease);
+      }
+    }
+  }
+
+
+  public void requestDisallowInterceptTouchEvent(boolean requestDisallowInterceptTouchEvent) {
+    if(mGesture != null){
+      if(mGesture.isRequestDisallowInterceptTouchEvent()){
+        return;
+      }
+      mGesture.setRequestDisallowInterceptTouchEvent(requestDisallowInterceptTouchEvent);
+    }
+    if(getParent() != null){
+      getParent().requestDisallowInterceptTouchEvent(requestDisallowInterceptTouchEvent);
+    }
+  }
+
+  /********************************
+   *  end hook Activity life cycle callback
+   ********************************************************/
+
+  public @Nullable
+  View getBoxShadowHost(boolean isClear) {
+    if (isClear) {
+      // Return existed host if want clear shadow
+      return mBoxShadowHost;
+    }
+
+    ViewGroup hostView = getHostView();
+    if (hostView == null) {
+      return null;
+    }
+
+    try {
+      String type = getComponentType();
+      if (WXBasicComponentType.DIV.equals(type)) {
+        WXLogUtils.d("BoxShadow", "Draw box-shadow with BoxShadowHost on div: " + toString());
+        if (mBoxShadowHost == null) {
+          mBoxShadowHost = new BoxShadowHost(getContext());
+          WXViewUtils.setBackGround(mBoxShadowHost, null, this);
+
+          hostView.addView(mBoxShadowHost);
+        }
+
+        CSSShorthand padding = this.getPadding();
+        CSSShorthand border = this.getBorder();
+
+        int left = (int) (padding.get(CSSShorthand.EDGE.LEFT) + border.get(CSSShorthand.EDGE.LEFT));
+        int top = (int) (padding.get(CSSShorthand.EDGE.TOP) + border.get(CSSShorthand.EDGE.TOP));
+        int right = (int) (padding.get(CSSShorthand.EDGE.RIGHT) + border.get(CSSShorthand.EDGE.RIGHT));
+        int bottom = (int) (padding.get(CSSShorthand.EDGE.BOTTOM) + border.get(CSSShorthand.EDGE.BOTTOM));
+
+        ViewGroup.MarginLayoutParams layoutParams = new ViewGroup.MarginLayoutParams(hostView.getLayoutParams()) ;
+        this.setMarginsSupportRTL(layoutParams, -left, -top, -right, -bottom);
+
+        mBoxShadowHost.setLayoutParams(layoutParams);
+        
+        hostView.removeView(mBoxShadowHost);
+        hostView.addView(mBoxShadowHost);
+        return mBoxShadowHost;
+      }
+    } catch (Throwable t) {
+      WXLogUtils.w("BoxShadow", t);
+    }
+    return hostView;
+  }
+
+  private class BoxShadowHost extends View {
+    public BoxShadowHost(Context context) {
+      super(context);
+    }
+  }
+
+  public void appendTreeCreateFinish() {
+    
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXVideo.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXVideo.java
new file mode 100644
index 0000000..a4f875f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXVideo.java
@@ -0,0 +1,271 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.media.MediaPlayer;
+import android.net.Uri;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+import android.view.View;
+import android.widget.FrameLayout;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.WXVideoView;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.HashMap;
+import java.util.Map;
+import org.apache.weex.ui.view.WXVideoView.Wrapper;
+
+@Component(lazyload = false)
+
+public class WXVideo extends WXComponent<FrameLayout> {
+
+  private boolean mAutoPlay;
+  private Wrapper mWrapper;
+
+  /**
+   * package
+   **/
+  boolean mPrepared;
+  private boolean mError;
+
+  @Deprecated
+  public WXVideo(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+  public WXVideo(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+    super(instance, parent, isLazy, basicComponentData);
+  }
+
+  @Override
+  protected FrameLayout initComponentHostView(@NonNull Context context) {
+    final Wrapper video = new Wrapper(context);
+    video.setOnErrorListener(new MediaPlayer.OnErrorListener() {
+
+      @Override
+      public boolean onError(MediaPlayer mp, int what, int extra) {
+        if (WXEnvironment.isApkDebugable()) {
+          WXLogUtils.d("Video", "onError:" + what);
+        }
+        video.getProgressBar().setVisibility(View.GONE);
+        mPrepared = false;
+        mError = true;
+
+        if (getEvents().contains(Constants.Event.FAIL)) {
+          WXVideo.this.notify(Constants.Event.FAIL, Constants.Value.STOP);
+        }
+        return true;
+      }
+    });
+
+    video.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
+
+      @Override
+      public void onPrepared(MediaPlayer mediaPlayer) {
+        if (WXEnvironment.isApkDebugable()) {
+          WXLogUtils.d("Video", "onPrepared");
+        }
+        video.getProgressBar().setVisibility(View.GONE);
+        mPrepared = true;
+        if (mAutoPlay) {
+          video.start();
+        }
+
+        //callback from video view, so videoview should not null
+        WXVideoView videoView = video.getVideoView();
+        videoView.seekTo(5);
+
+        if (video.getMediaController() != null) {
+          if (!mStopped) {
+            video.getMediaController().show(3);
+          } else {
+            video.getMediaController().hide();
+          }
+        }
+
+        mStopped = false;
+      }
+    });
+
+    video.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
+
+      @Override
+      public void onCompletion(MediaPlayer mediaPlayer) {
+        if (WXEnvironment.isApkDebugable()) {
+          WXLogUtils.d("Video", "onCompletion");
+        }
+        if (getEvents().contains(Constants.Event.FINISH)) {
+          WXVideo.this.notify(Constants.Event.FINISH, Constants.Value.STOP);
+        }
+      }
+    });
+
+    video.setOnVideoPauseListener(new WXVideoView.VideoPlayListener() {
+
+      @Override
+      public void onPause() {
+        if (WXEnvironment.isApkDebugable()) {
+          WXLogUtils.d("Video", "onPause");
+        }
+        if (getEvents().contains(Constants.Event.PAUSE)) {
+          WXVideo.this.notify(Constants.Event.PAUSE, Constants.Value.PAUSE);
+        }
+      }
+
+      @Override
+      public void onStart() {
+        if (WXEnvironment.isApkDebugable()) {
+          WXLogUtils.d("Video", "onStart");
+        }
+
+        if (getEvents().contains(Constants.Event.START)) {
+          WXVideo.this.notify(Constants.Event.START, Constants.Value.PLAY);
+        }
+      }
+    });
+    mWrapper = video;
+    return video;
+  }
+
+  private void notify(String event, String newStatus) {
+    Map<String, Object> params = new HashMap<>(2);
+    params.put(Constants.Name.PLAY_STATUS, newStatus);
+    params.put("timeStamp", System.currentTimeMillis());
+
+    Map<String, Object> domChanges = new HashMap<>();
+    Map<String, Object> attrsChanges = new HashMap<>();
+    attrsChanges.put(Constants.Name.PLAY_STATUS, newStatus);
+    domChanges.put("attrs", attrsChanges);
+
+    WXSDKManager.getInstance().fireEvent(getInstanceId(), getRef(), event, params, domChanges);
+  }
+
+  @Override
+  public void bindData(WXComponent component) {
+    super.bindData(component);
+    addEvent(Constants.Event.APPEAR);
+  }
+
+  @Override
+  public void notifyAppearStateChange(String wxEventType, String direction) {
+    super.notifyAppearStateChange(wxEventType, direction);
+    mWrapper.createVideoViewIfVisible();
+  }
+
+  @Override
+  public void destroy() {
+    super.destroy();
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case Constants.Name.SRC:
+        String src = WXUtils.getString(param, null);
+        if (src != null) {
+          setSrc(src);
+        }
+        return true;
+      case Constants.Name.AUTO_PLAY:
+      case Constants.Name.AUTOPLAY:
+        Boolean result = WXUtils.getBoolean(param, null);
+        if (result != null) {
+          setAutoPlay(result);
+        }
+        return true;
+      case Constants.Name.ZORDERTOP:
+        Boolean zOrderTop = WXUtils.getBoolean(param, null);
+        if (zOrderTop != null) {
+            mWrapper.getVideoView().setZOrderOnTop(zOrderTop);
+        }
+        return true;
+      case Constants.Name.PLAY_STATUS:
+        String status = WXUtils.getString(param, null);
+        if (status != null) {
+          setPlaystatus(status);
+        }
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @WXComponentProp(name = Constants.Name.SRC)
+  public void setSrc(String src) {
+    if (TextUtils.isEmpty(src) || getHostView() == null) {
+      return;
+    }
+
+    if (!TextUtils.isEmpty(src)) {
+      WXSDKInstance instance = getInstance();
+      mWrapper.setVideoURI(instance.rewriteUri(Uri.parse(src), URIAdapter.VIDEO));
+      mWrapper.getProgressBar().setVisibility(View.VISIBLE);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.AUTO_PLAY)
+  public void setAutoPlay(boolean autoPlay) {
+    mAutoPlay = autoPlay;
+    if(autoPlay){
+      mWrapper.createIfNotExist();
+      mWrapper.start();
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.CONTROLS)
+  public void setControls(String controls) {
+    if (TextUtils.equals("controls", controls)) {
+      mWrapper.setControls(true);
+    } else if (TextUtils.equals("nocontrols", controls)) {
+      mWrapper.setControls(false);
+    }
+  }
+
+  private boolean mStopped;
+
+  @WXComponentProp(name = Constants.Name.PLAY_STATUS)
+  public void setPlaystatus(String playstatus) {
+
+    if (mPrepared && !mError && !mStopped) {
+      if (playstatus.equals(Constants.Value.PLAY)) {
+        mWrapper.start();
+      } else if (playstatus.equals(Constants.Value.PAUSE)) {
+        mWrapper.pause();
+      } else if (playstatus.equals(Constants.Value.STOP)) {
+        mWrapper.stopPlayback();
+        mStopped = true;
+      }
+    } else if ((mError || mStopped) && playstatus.equals(Constants.Value.PLAY)) {
+      mError = false;
+      mWrapper.resume();
+
+      mWrapper.getProgressBar().setVisibility(View.VISIBLE);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/WXWeb.java b/android/sdk/src/main/java/org/apache/weex/ui/component/WXWeb.java
new file mode 100644
index 0000000..321c36a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/WXWeb.java
@@ -0,0 +1,229 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component;
+
+import android.content.Context;
+import android.net.Uri;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+import android.view.View;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.view.IWebView;
+import org.apache.weex.ui.view.WXWebView;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.HashMap;
+import java.util.Map;
+
+@Component(lazyload = false)
+
+public class WXWeb extends WXComponent {
+
+    public static final String GO_BACK = "goBack";
+    public static final String GO_FORWARD = "goForward";
+    public static final String RELOAD = "reload";
+    public static final String POST_MESSAGE = "postMessage";
+    protected IWebView mWebView;
+
+    @Deprecated
+    public WXWeb(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+        this(instance, parent, isLazy, basicComponentData);
+    }
+
+    public WXWeb(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+        super(instance, parent, isLazy, basicComponentData);
+        createWebView();
+    }
+
+    protected void createWebView(){
+        String origin = null;
+        try {
+            String bundleUrl = WXSDKManager.getInstance().getSDKInstance(getInstanceId()).getBundleUrl();
+            Uri uri = Uri.parse(bundleUrl);
+            String scheme = uri.getScheme();
+            String authority = uri.getAuthority();
+            if (!TextUtils.isEmpty(scheme) && !TextUtils.isEmpty(authority)) {
+                origin = scheme + "://" + authority;
+            }
+        } catch (Exception e) {
+            // do noting
+        }
+        mWebView = new WXWebView(getContext(), origin);
+    }
+
+    @Override
+    protected View initComponentHostView(@NonNull Context context) {
+        mWebView.setOnErrorListener(new IWebView.OnErrorListener() {
+            @Override
+            public void onError(String type, Object message) {
+                fireEvent(type, message);
+            }
+        });
+        mWebView.setOnPageListener(new IWebView.OnPageListener() {
+            @Override
+            public void onReceivedTitle(String title) {
+                if (getEvents().contains(Constants.Event.RECEIVEDTITLE)) {
+                    Map<String, Object> params = new HashMap<>();
+                    params.put("title", title);
+                    fireEvent(Constants.Event.RECEIVEDTITLE, params);
+                }
+            }
+
+            @Override
+            public void onPageStart(String url) {
+                if (getEvents().contains(Constants.Event.PAGESTART)) {
+                    Map<String, Object> params = new HashMap<>();
+                    params.put("url", url);
+                    fireEvent(Constants.Event.PAGESTART, params);
+                }
+            }
+
+            @Override
+            public void onPageFinish(String url, boolean canGoBack, boolean canGoForward) {
+                if (getEvents().contains(Constants.Event.PAGEFINISH)) {
+                    Map<String, Object> params = new HashMap<>();
+                    params.put("url", url);
+                    params.put("canGoBack", canGoBack);
+                    params.put("canGoForward", canGoForward);
+                    fireEvent(Constants.Event.PAGEFINISH, params);
+                }
+            }
+        });
+        mWebView.setOnMessageListener(new IWebView.OnMessageListener() {
+            @Override
+            public void onMessage(Map<String, Object> params) {
+                fireEvent(Constants.Event.ONMESSAGE, params);
+            }
+        });
+        return mWebView.getView();
+    }
+
+    @Override
+    public void destroy() {
+        super.destroy();
+        getWebView().destroy();
+    }
+
+    @Override
+    protected boolean setProperty(String key, Object param) {
+        switch (key) {
+            case Constants.Name.SHOW_LOADING:
+                Boolean result = WXUtils.getBoolean(param,null);
+                if (result != null)
+                    setShowLoading(result);
+                return true;
+            case Constants.Name.SRC:
+                String src = WXUtils.getString(param,null);
+                if (src != null)
+                    setUrl(src);
+                return true;
+            case Constants.Name.SOURCE:
+                String source = WXUtils.getString(param,null);
+                if (source != null)
+                    setSource(source);
+                return true;
+        }
+        return super.setProperty(key,param);
+    }
+
+    @WXComponentProp(name = Constants.Name.SHOW_LOADING)
+    public void setShowLoading(boolean showLoading) {
+        getWebView().setShowLoading(showLoading);
+    }
+
+    @WXComponentProp(name = Constants.Name.SRC)
+    public void setUrl(String url) {
+        if (TextUtils.isEmpty(url) || getHostView() == null) {
+            return;
+        }
+        if (!TextUtils.isEmpty(url)) {
+            loadUrl(getInstance().rewriteUri(Uri.parse(url), URIAdapter.WEB).toString());
+        }
+    }
+
+    @WXComponentProp(name = Constants.Name.SOURCE)
+    public void setSource(String source) {
+        if (!TextUtils.isEmpty(source) && getHostView() != null) {
+            loadDataWithBaseURL(source);
+        }
+    }
+
+    public void setAction(String action, Object data) {
+        if (!TextUtils.isEmpty(action)) {
+            if (action.equals(GO_BACK)) {
+                goBack();
+            } else if (action.equals(GO_FORWARD)) {
+                goForward();
+            } else if (action.equals(RELOAD)) {
+                reload();
+            } else if (action.equals(POST_MESSAGE)) {
+                postMessage(data);
+            }
+        }
+    }
+
+    private void fireEvent(String type, Object message) {
+        if (getEvents().contains(Constants.Event.ERROR)) {
+            Map<String, Object> params = new HashMap<>();
+            params.put("type", type);
+            params.put("errorMsg", message);
+            fireEvent(Constants.Event.ERROR, params);
+        }
+    }
+
+    private void loadUrl(String url) {
+        getWebView().loadUrl(url);
+    }
+
+    private void loadDataWithBaseURL(String source) {
+        getWebView().loadDataWithBaseURL(source);
+    }
+
+    @JSMethod
+    public void reload() {
+        getWebView().reload();
+    }
+
+    @JSMethod
+    public void goForward() {
+        getWebView().goForward();
+    }
+
+    @JSMethod
+    public void goBack() {
+        getWebView().goBack();
+    }
+
+    @JSMethod
+    public void postMessage(Object msg) {
+        getWebView().postMessage(msg);
+    }
+
+    private IWebView getWebView() {
+        return mWebView;
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/basic/WXBasicComponent.java b/android/sdk/src/main/java/org/apache/weex/ui/component/basic/WXBasicComponent.java
new file mode 100644
index 0000000..85b063f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/basic/WXBasicComponent.java
@@ -0,0 +1,231 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.basic;
+
+import android.support.annotation.NonNull;
+import android.view.View;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.action.GraphicPosition;
+import org.apache.weex.ui.action.GraphicSize;
+import org.apache.weex.ui.component.WXComponent;
+import java.util.Map;
+import java.util.Set;
+
+public abstract class WXBasicComponent<T extends View> {
+
+  private Object mExtra;
+  private String mComponentType;
+  private String mRef;
+  private GraphicPosition mLayoutPosition;
+  private GraphicSize mLayoutSize;
+  private boolean mIsLayoutRTL;
+  private BasicComponentData mBasicComponentData;
+
+  private int mViewPortWidth = 750;
+
+  public WXBasicComponent(BasicComponentData basicComponentData) {
+    this.mBasicComponentData = basicComponentData;
+    this.mRef = basicComponentData.mRef;
+    this.mComponentType = basicComponentData.mComponentType;
+  }
+
+  public BasicComponentData getBasicComponentData() {
+    return mBasicComponentData;
+  }
+
+  protected void bindComponent(WXComponent component) {
+    mComponentType = component.getComponentType();
+    mRef = component.getRef();
+  }
+
+  public final @NonNull
+  WXStyle getStyles() {
+    return mBasicComponentData.getStyles();
+  }
+
+  public final @NonNull
+  WXAttr getAttrs() {
+    return mBasicComponentData.getAttrs();
+  }
+
+  public final @NonNull
+  WXEvent getEvents() {
+    return mBasicComponentData.getEvents();
+  }
+
+  /**
+   * Get this node's margin, as defined by cssstyle + default margin.
+   */
+  public final @NonNull
+  CSSShorthand getMargin() {
+    return mBasicComponentData.getMargin();
+  }
+
+  /**
+   * Get this node's padding, as defined by cssstyle + default padding.
+   */
+  public final @NonNull
+  CSSShorthand getPadding() {
+    return mBasicComponentData.getPadding();
+  }
+
+  /**
+   * Get this node's border, as defined by cssstyle.
+   */
+  public @NonNull
+  CSSShorthand getBorder() {
+    return mBasicComponentData.getBorder();
+  }
+
+  public final void setMargins(@NonNull CSSShorthand margins) {
+    mBasicComponentData.setMargins(margins);
+  }
+
+  public final void setPaddings(@NonNull CSSShorthand paddings) {
+    mBasicComponentData.setPaddings(paddings);
+  }
+
+  public final void setBorders(@NonNull CSSShorthand borders) {
+    mBasicComponentData.setBorders(borders);
+  }
+
+  public final void addAttr(Map<String, Object> attrs) {
+    if (attrs == null || attrs.isEmpty()) {
+      return;
+    }
+    mBasicComponentData.addAttr(attrs);
+  }
+
+  public final void addStyle(Map<String, Object> styles) {
+    if (styles == null || styles.isEmpty()) {
+      return;
+    }
+    mBasicComponentData.addStyle(styles);
+  }
+
+  public final void addStyle(Map<String, Object> styles, boolean byPesudo) {
+    if (styles == null || styles.isEmpty()) {
+      return;
+    }
+    mBasicComponentData.addStyle(styles, byPesudo);
+  }
+
+  public final void updateStyle(Map<String, Object> styles, boolean byPesudo){
+    if (styles == null || styles.isEmpty()) {
+      return;
+    }
+    mBasicComponentData.getStyles().updateStyle(styles, byPesudo);
+  }
+
+  public final void addEvent(Set<String> events) {
+    if (events == null || events.isEmpty()) {
+      return;
+    }
+
+    mBasicComponentData.addEvent(events);
+  }
+
+  public final void addShorthand(Map<String, String> shorthand) {
+    if (!shorthand.isEmpty() && mBasicComponentData != null) {
+      mBasicComponentData.addShorthand(shorthand);
+    }
+  }
+
+  public int getViewPortWidth() {
+    return mViewPortWidth;
+  }
+
+  public void setViewPortWidth(int mViewPortWidth) {
+    this.mViewPortWidth = mViewPortWidth;
+  }
+
+  public Object getExtra() {
+    return mExtra;
+  }
+
+  public void updateExtra(Object extra) {
+    this.mExtra = extra;
+  }
+
+  public String getComponentType() {
+    return mComponentType;
+  }
+
+  public String getRef() {
+    return mRef;
+  }
+
+  public void setIsLayoutRTL(boolean isRTL) {
+    mIsLayoutRTL = isRTL;
+  }
+
+  public boolean isLayoutRTL() {
+    return mIsLayoutRTL;
+  }
+
+  public GraphicPosition getLayoutPosition() {
+    if (mLayoutPosition == null) {
+      mLayoutPosition = new GraphicPosition(0, 0, 0, 0);
+    }
+    return mLayoutPosition;
+  }
+
+  protected void setLayoutPosition(GraphicPosition mLayoutPosition) {
+    this.mLayoutPosition = mLayoutPosition;
+  }
+
+  public GraphicSize getLayoutSize() {
+    if (mLayoutSize == null) {
+      mLayoutSize = new GraphicSize(0, 0);
+    }
+    return mLayoutSize;
+  }
+
+  protected void setLayoutSize(GraphicSize mLayoutSize) {
+    this.mLayoutSize = mLayoutSize;
+  }
+
+  public float getCSSLayoutTop() {
+    return mLayoutPosition == null ? 0 : mLayoutPosition.getTop();
+  }
+
+  public float getCSSLayoutBottom() {
+    return mLayoutPosition == null ? 0 : mLayoutPosition.getBottom();
+  }
+
+  public float getCSSLayoutLeft() {
+    return mLayoutPosition == null ? 0 : mLayoutPosition.getLeft();
+  }
+
+  public float getCSSLayoutRight() {
+    return mLayoutPosition == null ? 0 : mLayoutPosition.getRight();
+  }
+
+  public float getLayoutWidth() {
+    return mLayoutSize == null ? 0 : mLayoutSize.getWidth();
+  }
+
+  public float getLayoutHeight() {
+    return mLayoutSize == null ? 0 : mLayoutSize.getHeight();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/binding/AsynLayoutTask.java b/android/sdk/src/main/java/org/apache/weex/ui/component/binding/AsynLayoutTask.java
new file mode 100644
index 0000000..8b9e364
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/binding/AsynLayoutTask.java
@@ -0,0 +1,70 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.binding;
+
+import android.os.AsyncTask;
+
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.list.template.TemplateDom;
+import org.apache.weex.ui.component.list.template.TemplateViewHolder;
+
+/**
+ * Created by furture on 2018/5/11.
+ */
+
+class AsynLayoutTask extends AsyncTask<Void, Void, Void> {
+
+    private final TemplateViewHolder templateViewHolder;
+    private final int position;
+    private final WXComponent component;
+
+    AsynLayoutTask(TemplateViewHolder templateViewHolder, int position, WXComponent component) {
+        this.templateViewHolder = templateViewHolder;
+        this.position = position;
+        this.component = component;
+    }
+
+    @Override
+    protected Void doInBackground(Void... params) {
+        if(templateViewHolder.getHolderPosition() == position){
+            if(component.getInstance() != null && !component.getInstance().isDestroy()) {
+                synchronized (templateViewHolder.getTemplateList()){
+                    if(templateViewHolder.getTemplateList().isDestoryed()){
+                        return null;
+                    }
+                    Layouts.doLayoutOnly(component, templateViewHolder);
+                }
+            }
+        }
+        return null;
+    }
+
+    @Override
+    protected void onPostExecute(Void aVoid) {
+        if(position == templateViewHolder.getHolderPosition()) {
+            if(component.getInstance() != null && !component.getInstance().isDestroy()) {
+                Layouts.setLayout(component, false);
+                if(templateViewHolder.getHolderPosition() >= 0){
+                    templateViewHolder.getTemplateList().fireEvent("_attach_slot", TemplateDom
+                        .findAllComponentRefs(templateViewHolder.getTemplateList().getRef(), position, component));
+                }
+            }
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/binding/Layouts.java b/android/sdk/src/main/java/org/apache/weex/ui/component/binding/Layouts.java
new file mode 100644
index 0000000..2095e02
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/binding/Layouts.java
@@ -0,0 +1,134 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.binding;
+
+
+
+import android.os.AsyncTask;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.ui.component.list.template.TemplateDom;
+import org.apache.weex.ui.component.list.template.TemplateViewHolder;
+import org.apache.weex.ui.component.list.template.WXRecyclerTemplateList;
+import org.apache.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+
+/**
+ * Created by furture on 2017/8/21.
+ */
+public class Layouts {
+    /**
+     * do dom layout async or sync , and set layout to component on main.
+     * on first use do sync layout, when compontnet reuse do async layout
+     * */
+    public static void doLayoutAsync(final TemplateViewHolder templateViewHolder, boolean async){
+        final WXComponent component = templateViewHolder.getComponent();
+        final  int position = templateViewHolder.getHolderPosition();
+        if(templateViewHolder.asyncTask != null){
+            templateViewHolder.asyncTask.cancel(false);
+            templateViewHolder.asyncTask = null;
+        }
+        if(async){
+            AsyncTask<Void, Void, Void> asyncTask = new AsynLayoutTask(templateViewHolder, position, component);
+            templateViewHolder.asyncTask = asyncTask;
+            asyncTask.executeOnExecutor(AsyncTask.SERIAL_EXECUTOR); //serial executor is better
+        }else{
+            doLayoutOnly(component, templateViewHolder);
+            setLayout(component, false);
+            if(templateViewHolder.getHolderPosition() >= 0){
+                templateViewHolder.getTemplateList().fireEvent("_attach_slot", TemplateDom
+                    .findAllComponentRefs(templateViewHolder.getTemplateList().getRef(), position, component));
+            }
+        }
+
+    }
+    /**
+     * @param layoutHeight height
+     * @param layoutWidth width
+     * */
+    public static void doLayoutSync(WXCell component, float layoutWidth, float layoutHeight){
+        doSafeLayout(component, layoutWidth, layoutHeight);
+        setLayout(component, false);
+    }
+
+        /**
+         * safe layout
+         * */
+    public static void doLayoutOnly(WXComponent component, TemplateViewHolder holder){
+        doSafeLayout(component, holder.getTemplateList().getLayoutWidth(), holder.getTemplateList().getLayoutHeight());
+    }
+
+    private static void doSafeLayout(WXComponent component, float layoutWidth, float layoutHeight){
+        try{
+            long start = System.currentTimeMillis();
+            int height = NativeRenderObjectUtils.nativeLayoutRenderObject(component.getRenderObjectPtr(),
+                    layoutWidth,
+                    layoutHeight);
+            if(WXEnvironment.isOpenDebugLog() && WXRecyclerTemplateList.ENABLE_TRACE_LOG) {
+                WXLogUtils.d(WXRecyclerTemplateList.TAG, "WXTemplateList doSafeLayout " +
+                        component.getAttrs().get(Constants.Name.Recycler.SLOT_TEMPLATE_CASE) + " " + Thread.currentThread().getName() + " doSafeLayout  used " +
+                        (System.currentTimeMillis() - start));
+            }
+            if(!(height > 0)){
+                WXLogUtils.e(WXRecyclerTemplateList.TAG, " WXTemplateList doSafeLayout wrong template " +
+                        component.getAttrs().get(Constants.Name.Recycler.SLOT_TEMPLATE_CASE)  + " cell height " + height);
+            }
+        }catch (Exception e){
+            if(WXEnvironment.isApkDebugable()){
+                WXLogUtils.e(WXRecyclerTemplateList.TAG, e);
+            }
+        }
+    }
+
+
+    /**
+     * recursive set layout to component,
+     * dom extra will also be updated from dom object to component.
+     * if force is true, always set layout
+     * */
+    public static final void setLayout(WXComponent component, boolean force){
+        if(component.isWaste()){
+            return;
+        }
+        if(component.getAttrs().containsKey(TemplateDom.KEY_RESET_ANIMATION)){
+            if(WXUtils.getBoolean(component.getAttrs().get(TemplateDom.KEY_RESET_ANIMATION), true).booleanValue()){
+                TemplateDom.resetAnimaiton(component.getHostView());
+            }
+        }
+        long ptr = component.getRenderObjectPtr();
+        if(NativeRenderObjectUtils.nativeRenderObjectHasNewLayout(ptr)){
+            NativeRenderObjectUtils.nativeRenderObjectUpdateComponent(ptr, component);
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            int count = container.getChildCount();
+            for (int i = 0; i < count; ++i) {
+                WXComponent child = container.getChild(i);
+                if (child != null) {
+                    setLayout(child, force);
+                }
+            }
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/binding/Statements.java b/android/sdk/src/main/java/org/apache/weex/ui/component/binding/Statements.java
new file mode 100644
index 0000000..5529048
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/binding/Statements.java
@@ -0,0 +1,702 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.binding;
+
+import android.os.Looper;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.bridge.EventResult;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.dom.binding.ELUtils;
+import org.apache.weex.dom.binding.JSONUtils;
+import org.apache.weex.dom.binding.WXStatement;
+import org.apache.weex.el.parse.ArrayStack;
+import org.apache.weex.el.parse.Operators;
+import org.apache.weex.el.parse.Token;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.action.GraphicPosition;
+import org.apache.weex.ui.action.GraphicSize;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXComponentFactory;
+import org.apache.weex.ui.component.WXImage;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.ui.component.list.template.CellDataManager;
+import org.apache.weex.ui.component.list.template.CellRenderContext;
+import org.apache.weex.ui.component.list.template.TemplateDom;
+import org.apache.weex.ui.component.list.template.VirtualComponentLifecycle;
+import org.apache.weex.ui.component.list.template.WXRecyclerTemplateList;
+import org.apache.weex.ui.component.list.template.jni.NativeRenderObjectUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * Created by jianbai.gbj on 2017/8/17.
+ * simple statement execute, render component for template list
+ */
+public class Statements {
+
+
+    /**
+     * parse statements token from attrs and style and event
+     * */
+    public static void  parseStatementsToken(WXComponent component){
+        if(component.getBasicComponentData().isRenderPtrEmpty()){
+           component.getBasicComponentData().setRenderObjectPr(component.getRenderObjectPtr());
+        }
+        if(component.getBasicComponentData() != null){
+            BasicComponentData basicComponentData =  component.getBasicComponentData();
+            basicComponentData.getAttrs().parseStatements();
+            basicComponentData.getStyles().parseStatements();
+            basicComponentData.getEvents().parseStatements();
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            int count = container.getChildCount();
+            for (int i = 0; i < count; ++i) {
+                parseStatementsToken(container.getChild(i));
+            }
+        }
+    }
+
+
+
+    /**
+     * init component  if component is lazy,
+     * if component is not lazy, do nothing
+     * */
+    public static void initLazyComponent(WXComponent component, WXVContainer mParent){
+        if(component.isLazy() || component.getHostView() == null){
+            component.lazy(false);
+            if(mParent != null){
+                int index = mParent.indexOf(component);
+                mParent.createChildViewAt(index);
+            }else {
+                component.createView();
+            }
+            component.applyLayoutAndEvent(component);
+            component.bindData(component);
+        }
+    }
+
+
+
+    /**
+     * recursive copy component, none parent connect
+     * */
+    public static WXComponent copyComponentTree(WXComponent component){
+        WXComponent copy =  copyComponentTree(component, component.getParent());
+        return copy;
+    }
+
+    /**
+     * recursive copy component,
+     * */
+    private static final WXComponent copyComponentTree(WXComponent source, WXVContainer parent){
+        BasicComponentData basicComponentData = null;
+        try {
+            basicComponentData = source.getBasicComponentData().clone();
+        } catch (CloneNotSupportedException e) {
+            e.printStackTrace();
+        }
+        WXComponent component = WXComponentFactory
+            .newInstance(source.getInstance(), parent, basicComponentData);
+        GraphicPosition graphicPosition = source.getLayoutPosition();
+        GraphicSize graphicSize = source.getLayoutSize();
+        component.updateDemission(graphicPosition.getTop(), graphicPosition.getBottom(), graphicPosition.getLeft(), graphicPosition.getRight(),
+                 graphicSize.getHeight(), graphicSize.getWidth());
+        component.updateExtra(source.getExtra());
+        if(source instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) source;
+            WXVContainer childParent = (WXVContainer) component;
+            int count = container.getChildCount();
+            for (int i = 0; i < count; ++i) {
+                WXComponent sourceChild = container.getChild(i);
+                if (sourceChild != null) {
+                    WXComponent targetChild = copyComponentTree(sourceChild,  childParent);childParent.addChild(targetChild);
+                    NativeRenderObjectUtils.nativeAddChildRenderObject(childParent.getRenderObjectPtr(),
+                            targetChild.getRenderObjectPtr());
+                }
+            }
+        }
+        //copy info need be sync
+        if(source.isWaste()){
+            component.setWaste(true);
+        }
+        return  component;
+    }
+
+    /**
+     *  @param component component with v-for statement, v-if statement and bind attrs
+     *  @param stack  execute context
+     *  render component in context, the function do the following  work.
+     *  execute component's v-for statement, v-if statement in context,
+     *  and rebuild component's tree with the statement, v-for reuse component execute by pre render.
+     *  if executed, component will be removed, don't remove, just mark it waste;
+     *  may be next render it can be used.
+     *  after statement has executed, render component's binding attrs in context and bind it to component.
+     * */
+    public static final List<WXComponent> doRender(WXComponent component, CellRenderContext stack){
+        List<WXComponent> updates = new ArrayList<>(4);
+        try{
+            doRenderComponent(component, stack, updates);
+        }catch (Exception e){
+            WXLogUtils.e("WeexStatementRender", e);
+        }
+        return updates;
+    }
+
+    public static final void doInitCompontent(List<WXComponent> updates) {
+        if(updates == null || updates.size() == 0){
+            return;
+        }
+        for(WXComponent renderNode : updates){
+            if(renderNode.getParent() == null){
+                throw new IllegalArgumentException("render node parent cann't find");
+            }
+            WXVContainer parent = renderNode.getParent();
+            int renderIndex = parent.indexOf(renderNode);
+            if(renderIndex < 0){
+                throw new IllegalArgumentException("render node cann't find");
+            }
+            parent.createChildViewAt(renderIndex);
+            renderNode.applyLayoutAndEvent(renderNode);
+            renderNode.bindData(renderNode);
+        }
+    }
+
+        /**
+         *  @param component component with v-for statement, v-if statement and bind attrs
+         *  @param context   execute context
+         *  render component in context, the function do the following  work.
+         *  execute component's v-for statement, v-if statement in context,
+         *  and rebuild component's tree with the statement, v-for reuse component execute by pre render.
+         *  if executed, component will be removed, don't remove, just mark it waste;
+         *  may be next render it can be used.
+         *  after statement has executed, render component's binding attrs in context and bind it to component.
+         * */
+    private static final int doRenderComponent(WXComponent component, CellRenderContext context,
+                                               List<WXComponent> updates){
+        WXVContainer parent = component.getParent();
+        WXAttr attrs = component.getAttrs();
+        WXStatement statement =  attrs.getStatement();
+        if(statement != null){
+            Token vif =  null;
+            JSONObject vfor = null;
+            if(statement.get(WXStatement.WX_IF) instanceof Token){
+                vif = (Token) statement.get(WXStatement.WX_IF);
+            }
+            if(statement.get(WXStatement.WX_FOR) instanceof  JSONObject){
+                vfor = (JSONObject) statement.get(WXStatement.WX_FOR);
+            }
+            // execute v-for content
+            if(vfor != null){
+                int    renderIndex = parent.indexOf(component);
+                if(vfor.get(WXStatement.WX_FOR_LIST) instanceof Token){
+                    Token listBlock = (Token) vfor.get(WXStatement.WX_FOR_LIST);
+                    String indexKey = vfor.getString(WXStatement.WX_FOR_INDEX);
+                    String itemKey = vfor.getString(WXStatement.WX_FOR_ITEM);
+                    Object data = null;
+                    if(listBlock != null) {
+                        data = listBlock.execute(context.stack);
+                    }
+                    if((data instanceof List || data instanceof  Map)){
+
+                        Collection collection = null;
+                        Map  map = null;
+                        if(data instanceof  List){
+                            collection = (List)data;
+                        }else{
+                            map = (Map)data;
+                            collection = map.keySet();
+                        }
+                        Map<String, Object> loop = new HashMap<>();
+                        int index = 0;
+                        for(Object item : collection){
+                            Object key = null;
+                            Object value = item;
+                            if(map == null){
+                                key = index;
+                                value = item;
+                                index ++;
+                            }else{
+                                key = item;
+                                value = map.get(item);
+                            }
+                            if(indexKey != null){
+                                loop.put(indexKey, key);
+                            }
+
+                            if(itemKey != null){
+                                loop.put(itemKey, value);
+                            }else{
+                                context.stack.push(value);
+                            }
+                            if(loop.size() > 0){
+                                context.stack.push(loop);
+                            }
+
+
+                            if(vif != null){
+                                if(!Operators.isTrue(vif.execute(context.stack))){
+                                    continue;
+                                }
+                            }
+                            //find resuable renderNode
+                            WXComponent renderNode = null;
+                            if(renderIndex < parent.getChildCount()){
+                                renderNode = parent.getChild(renderIndex);
+                                //check is same statment, if true, it is usabled.
+                                if(!isCreateFromNodeStatement(renderNode, component)){
+                                    renderNode = null;
+                                }
+                                if(renderNode != null){
+                                    if(renderNode.isWaste()){
+                                        renderNode.setWaste(false);
+                                    }
+                                }
+                            }
+                            //none resuable render node, create node, add to parent, but clear node's statement
+                            if(renderNode == null){
+                                long start = System.currentTimeMillis();
+                                renderNode = copyComponentTree(component, parent);
+                                renderNode.setWaste(false);
+                                if(renderNode.getAttrs().getStatement() != null) {
+                                    renderNode.getAttrs().getStatement().remove(WXStatement.WX_FOR);
+                                    renderNode.getAttrs().getStatement().remove(WXStatement.WX_IF); //clear node's statement
+                                }
+                                parent.addChild(renderNode, renderIndex);
+                                NativeRenderObjectUtils.nativeAddChildRenderObject(parent.getRenderObjectPtr(),
+                                        renderNode.getRenderObjectPtr());
+                                updates.add(renderNode);
+                                if(WXEnvironment.isApkDebugable()){
+                                    WXLogUtils.d(WXRecyclerTemplateList.TAG, Thread.currentThread().getName() +  renderNode.getRef() + renderNode.getComponentType() + "statements copy component tree used " + (System.currentTimeMillis() - start));
+                                }
+                            }
+                            doBindingAttrsEventAndRenderChildNode(renderNode, context, updates);
+                            renderIndex++;
+                            if(loop.size() > 0){
+                                context.stack.push(loop);
+                            }
+                            if(itemKey == null) {
+                                context.stack.pop();
+                            }
+                        }
+                    }
+                }else{
+                    WXLogUtils.e(WXRecyclerTemplateList.TAG,  vfor.toJSONString() + " not call vfor block, for pre compile");
+                }
+                //after v-for execute, remove component created pre v-for.
+                for(;renderIndex<parent.getChildCount(); renderIndex++){
+                    WXComponent wasteNode = parent.getChild(renderIndex);
+                    if(!isCreateFromNodeStatement(wasteNode, component)){
+                        break;
+                    }
+                    wasteNode.setWaste(true);
+                }
+                return renderIndex - parent.indexOf(component);
+            }
+
+            //execute v-if context
+            if(vif != null){
+                if(!Operators.isTrue(vif.execute(context.stack))){
+                    component.setWaste(true);
+                    return 1;
+                }else{
+                    component.setWaste(false);
+                }
+
+            }
+        }
+        doBindingAttrsEventAndRenderChildNode(component, context, updates);
+        return  1;
+    }
+
+
+    /**
+     * bind attrs and doRender component child
+     * */
+    private static void doBindingAttrsEventAndRenderChildNode(WXComponent component, CellRenderContext context,
+                                                              List<WXComponent> updates){
+        WXAttr attr = component.getAttrs();
+
+        /**
+         * sub component supported, sub component new stack
+         * */
+        ArrayStack stack = context.stack;
+
+
+        String virtualComponentId = null;
+        boolean callVirtualComponentAttach = false;
+        if(attr.get(ELUtils.IS_COMPONENT_ROOT) != null
+                && WXUtils.getBoolean(attr.get(ELUtils.IS_COMPONENT_ROOT), false)){
+            if(attr.get(ELUtils.COMPONENT_PROPS) != null
+                    && JSONUtils.isJSON(attr.get(ELUtils.COMPONENT_PROPS))){
+                 String compoentId = (String) attr.get(CellDataManager.SUB_COMPONENT_TEMPLATE_ID);
+                Object compoentData = null;
+                if(!TextUtils.isEmpty(compoentId)){
+                   virtualComponentId =  context.getRenderState().getVirtualComponentIds().get(component.getViewTreeKey());
+                   if(virtualComponentId == null){ //none virtualComponentId, create and do attach
+                        virtualComponentId =  CellDataManager.createVirtualComponentId(context.templateList.getRef(),
+                                component.getViewTreeKey(), context.templateList.getItemId(context.position));
+                        Map<String, Object>  props  = renderProps(JSONUtils.toJSON(attr.get(ELUtils.COMPONENT_PROPS)), context.stack);
+                        EventResult result = WXBridgeManager.getInstance().syncCallJSEventWithResult(WXBridgeManager.METHD_COMPONENT_HOOK_SYNC, component.getInstanceId(), null, compoentId, VirtualComponentLifecycle.LIFECYCLE, VirtualComponentLifecycle.CREATE,  new Object[]{
+                                virtualComponentId,
+                                props
+                        }, null);
+                        if(result != null
+                                && result.getResult() != null
+                                && result.getResult() instanceof Map){
+                            props.putAll((Map<? extends String, ?>) result.getResult());
+                        }
+                        compoentData  =  props;
+                        context.getRenderState().getVirtualComponentIds().put(component.getViewTreeKey(), virtualComponentId);
+                        context.templateList.getCellDataManager().createVirtualComponentData(context.position, virtualComponentId, compoentData);
+                         callVirtualComponentAttach = true; // when first create virtual compoent, call create
+                     }else{ // get virtual component data check has dirty's update
+                       compoentData = context.getRenderState().getVirtualComponentDatas().get(virtualComponentId);
+                       if(context.getRenderState().isHasDataUpdate()){
+                           Map<String, Object>  props  = renderProps((JSONObject) attr.get(ELUtils.COMPONENT_PROPS), context.stack);
+                           EventResult result = WXBridgeManager.getInstance().syncCallJSEventWithResult(WXBridgeManager.METHD_COMPONENT_HOOK_SYNC, component.getInstanceId(), null, virtualComponentId, VirtualComponentLifecycle.LIFECYCLE, VirtualComponentLifecycle.SYNSTATE,  new Object[]{
+                                   virtualComponentId,
+                                   props
+                           }, null);
+
+                           if(result != null
+                                   && result.getResult() != null
+                                   && result.getResult() instanceof Map){
+                               props.putAll((Map<? extends String, ?>) result.getResult());
+                               context.templateList.getCellDataManager().updateVirtualComponentData(virtualComponentId, props);
+                               compoentData = props;
+                           }
+                       }
+                    }
+                    component.getAttrs().put(CellDataManager.VIRTUAL_COMPONENT_ID, virtualComponentId);
+                }else{ //stateless component
+                    Map<String, Object>  props  = renderProps((JSONObject) attr.get(ELUtils.COMPONENT_PROPS), context.stack);
+                    compoentData = props;
+                }
+                //virtual component is new context
+                context.stack = new ArrayStack();
+                if(compoentData != null){
+                    context.stack.push(compoentData);
+                }
+            }
+        }
+
+        /**
+         * check node is render only once, if render once, and has rendered, just return
+         * */
+        Object vonce = null;
+        if(attr.getStatement() != null){
+            vonce = attr.getStatement().get(WXStatement.WX_ONCE);
+        }
+        if(vonce != null){
+            ArrayStack onceStack = context.getRenderState().getOnceComponentStates().get(component.getViewTreeKey());
+            if(onceStack == null){
+                onceStack = context.templateList.copyStack(context, stack);
+                context.getRenderState().getOnceComponentStates().put(component.getViewTreeKey(), onceStack);
+            }
+            context.stack = onceStack;
+        }
+
+        doRenderBindingAttrsAndEvent(component, context);
+        if(component instanceof WXVContainer){
+            if(component.isWaste()){
+                if(!(component instanceof WXCell)){
+                     return;
+                }
+            }
+            WXVContainer container = (WXVContainer) component;
+            for(int k=0; k<container.getChildCount();){
+                WXComponent next = container.getChild(k);
+                k += doRenderComponent(next, context, updates);
+            }
+        }
+        if(stack != context.stack){
+            context.stack = stack;
+        }
+        //create virtual componentId
+        if(callVirtualComponentAttach && virtualComponentId != null){
+            WXBridgeManager.getInstance().asyncCallJSEventVoidResult(WXBridgeManager.METHD_COMPONENT_HOOK_SYNC, component.getInstanceId(), null, virtualComponentId, VirtualComponentLifecycle.LIFECYCLE, VirtualComponentLifecycle.ATTACH, new Object[]{
+                    TemplateDom.findAllComponentRefs(context.templateList.getRef(),context.position, component)
+            });
+        }
+     }
+
+
+    /**
+     * check whether render node is create from component node statement.
+     * */
+    private static boolean isCreateFromNodeStatement(WXComponent renderNode, WXComponent component){
+        return (renderNode.getRef() != null && renderNode.getRef().equals(component.getRef()));
+    }
+
+
+    /**
+     * render dynamic binding attrs and bind them to component node.
+     * */
+    private static void doRenderBindingAttrsAndEvent(WXComponent component, CellRenderContext context){
+        ArrayStack stack  = context.stack;
+        component.setWaste(false);
+        WXAttr attr = component.getAttrs();
+        if(attr != null
+                && attr.getBindingAttrs() != null
+                && attr.getBindingAttrs().size() > 0){
+            ArrayMap<String, Object> bindAttrs = component.getAttrs().getBindingAttrs();
+            Map<String, Object> dynamic =  renderBindingAttrs(bindAttrs, stack);
+            Set<Map.Entry<String, Object>> entries = dynamic.entrySet();
+            /**
+             * diff attrs, see attrs has update, remove none update attrs
+             * */
+            Iterator<Map.Entry<String, Object>> iterator = entries.iterator();
+            while (iterator.hasNext()){
+                Map.Entry<String, Object> entry = iterator.next();
+                String key = entry.getKey();
+                Object value = entry.getValue();
+                Object oldValue = attr.get(key);
+                if(value == null){
+                    if(oldValue == null){
+                        iterator.remove();
+                        continue;
+                    }
+                }else{
+                    if(value.equals(oldValue)){
+                        iterator.remove();
+                    }
+                }
+            }
+
+            if(dynamic.size() > 0) {
+                if(dynamic.size() == 1
+                        && dynamic.get(Constants.Name.SRC) != null
+                        && component instanceof WXImage){
+                    //for image avoid dirty layout, only update src attrs
+                    component.getAttrs().put(Constants.Name.SRC, dynamic.get(Constants.Name.SRC));
+                }else {
+                    component.nativeUpdateAttrs(dynamic);
+                }
+                if(isMainThread()) {
+                    component.updateProperties(dynamic);
+                }
+                dynamic.clear();
+            }
+        }
+
+
+        WXStyle style = component.getStyles();
+        if(style != null && style.getBindingStyle() != null){
+            ArrayMap<String, Object> bindStyle = style.getBindingStyle();
+            Map<String, Object> dynamic =  renderBindingAttrs(bindStyle, stack);
+            Set<Map.Entry<String, Object>> entries = dynamic.entrySet();
+            /**
+             * diff attrs, see attrs has update, remove none update attrs
+             * */
+            Iterator<Map.Entry<String, Object>> iterator = entries.iterator();
+            while (iterator.hasNext()){
+                Map.Entry<String, Object> entry = iterator.next();
+                String key = entry.getKey();
+                Object value = entry.getValue();
+                Object oldValue = style.get(key);
+                if(value == null){
+                    if(oldValue == null){
+                        iterator.remove();
+                        continue;
+                    }
+                }else{
+                    if(value.equals(oldValue)){
+                        iterator.remove();
+                    }
+                }
+            }
+            if(dynamic.size() > 0) {
+                  component.updateNativeStyles(dynamic);
+                 if(isMainThread()) {
+                    component.updateProperties(dynamic);
+                 }
+            }
+        }
+
+        WXEvent event = component.getEvents();
+        if(event == null || event.getEventBindingArgs() == null){
+            return;
+        }
+        Set<Map.Entry<String, Object>> eventBindArgsEntrySet = event.getEventBindingArgs().entrySet();
+        for(Map.Entry<String, Object> eventBindArgsEntry : eventBindArgsEntrySet){
+             List<Object> values = getBindingEventArgs(stack, eventBindArgsEntry.getValue());
+             if(values != null){
+                 event.putEventBindingArgsValue(eventBindArgsEntry.getKey(), values);
+             }
+        }
+
+    }
+
+
+    /**
+     * @param  bindAttrs  none null,
+     * @param  context  context
+     * return binding attrs rended value in context
+     * */
+    private static final  ThreadLocal<Map<String, Object>> dynamicLocal = new ThreadLocal<>();
+    public static Map<String, Object> renderBindingAttrs(ArrayMap bindAttrs, ArrayStack stack){
+        Set<Map.Entry<String, Object>> entrySet = bindAttrs.entrySet();
+        Map<String, Object> dynamic = dynamicLocal.get();
+        if(dynamic == null) {
+            dynamic = new HashMap<>();
+            dynamicLocal.set(dynamic);
+        }
+        if(dynamic.size() > 0){
+            dynamic.clear();
+        }
+        for(Map.Entry<String, Object> entry : entrySet){
+            Object value = entry.getValue();
+            String key = entry.getKey();
+            if(value instanceof  JSONObject
+                    && (((JSONObject) value).get(ELUtils.BINDING)  instanceof Token)){
+                JSONObject binding = (JSONObject) value;
+                Token block = (Token) (binding.get(ELUtils.BINDING));
+                Object blockValue = block.execute(stack);
+                dynamic.put(key, blockValue);
+            }else if(value instanceof JSONArray){
+                JSONArray array = (JSONArray) value;
+                StringBuilder builder = new StringBuilder();
+                for(int i=0; i<array.size(); i++){
+                    Object element = array.get(i);
+                    if(element instanceof  CharSequence){
+                        builder.append(element);
+                        continue;
+                    }
+                    if(element instanceof JSONObject
+                            && (((JSONObject) element).get(ELUtils.BINDING) instanceof Token)){
+                        JSONObject binding = (JSONObject) element;
+                        Token block = (Token) (binding.get(ELUtils.BINDING));
+                        Object blockValue = block.execute(stack);
+                        if(blockValue == null){
+                            blockValue = "";
+                        }
+                        builder.append(blockValue);
+                    }
+                }
+                String builderString = builder.toString();
+                if(builderString.length() > 256){
+                    if(WXEnvironment.isApkDebugable()){
+                        WXLogUtils.w(WXRecyclerTemplateList.TAG, " warn too big string " + builderString);
+                    }
+                }
+                dynamic.put(key, builderString);
+            }
+        }
+        return  dynamic;
+    }
+
+
+    public static Map<String, Object> renderProps(JSONObject props, ArrayStack stack){
+        Set<Map.Entry<String, Object>> entrySet = props.entrySet();
+        Map<String, Object> renderProps = new ArrayMap<>(4);
+        for(Map.Entry<String, Object> entry : entrySet){
+            Object value = entry.getValue();
+            String key = entry.getKey();
+            if(value instanceof  JSONObject
+                    && (((JSONObject) value).get(ELUtils.BINDING)  instanceof Token)){
+                JSONObject binding = (JSONObject) value;
+                Token block = (Token) (binding.get(ELUtils.BINDING));
+                Object blockValue = block.execute(stack);
+                renderProps.put(key, blockValue);
+            }else{
+                renderProps.put(key, value);
+            }
+        }
+        return  renderProps;
+    }
+
+    public static List<Object> getBindingEventArgs(ArrayStack stack, Object bindings){
+          List<Object>  params = new ArrayList<>(4);
+          if(bindings instanceof  JSONArray){
+              JSONArray array = (JSONArray) bindings;
+              for(int i=0; i<array.size(); i++){
+                  Object value = array.get(i);
+                  if(value instanceof  JSONObject
+                          && (((JSONObject) value).get(ELUtils.BINDING) instanceof Token)){
+                      Token block = (Token)(((JSONObject) value).get(ELUtils.BINDING));
+                      Object blockValue = block.execute(stack);
+                      params.add(blockValue);
+                  }else{
+                      params.add(value);
+                  }
+              }
+          }else if(bindings instanceof  JSONObject){
+              JSONObject binding = (JSONObject) bindings;
+               if(binding.get(ELUtils.BINDING) instanceof Token){
+                   Token block = (Token) binding.get(ELUtils.BINDING);
+                   Object blockValue = block.execute(stack);
+                   params.add(blockValue);
+               }else{
+                   params.add(bindings.toString());
+               }
+          }else{
+              params.add(bindings.toString());
+          }
+          return  params;
+    }
+
+
+    private static boolean isMainThread(){
+        return  Thread.currentThread() == Looper.getMainLooper().getThread();
+    }
+
+
+
+    public static String getComponentId(WXComponent component){
+        if(component instanceof WXCell || component == null){
+            return  null;
+        }
+        WXAttr attr = component.getAttrs();
+        if(attr.get(ELUtils.IS_COMPONENT_ROOT) != null
+                && WXUtils.getBoolean(attr.get(ELUtils.IS_COMPONENT_ROOT), false)){
+            if(attr.get(ELUtils.COMPONENT_PROPS) != null
+                    && attr.get(ELUtils.COMPONENT_PROPS) instanceof  JSONObject){
+                Object componentId = attr.get(CellDataManager.VIRTUAL_COMPONENT_ID);
+                if(componentId == null){
+                    return null;
+                }
+                return componentId.toString();
+            }
+        }
+        return getComponentId(component.getParent());
+    }
+
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/helper/ScrollStartEndHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/helper/ScrollStartEndHelper.java
new file mode 100644
index 0000000..339c267
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/helper/ScrollStartEndHelper.java
@@ -0,0 +1,153 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.helper;
+
+import android.os.Handler;
+import android.os.Looper;
+
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.OnWXScrollListener;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXScroller;
+import org.apache.weex.ui.component.list.BasicListComponent;
+import org.apache.weex.ui.component.list.ListComponentView;
+import org.apache.weex.ui.component.list.template.WXRecyclerTemplateList;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.Map;
+
+
+/**
+ * Created by furture on 2017/11/13.
+ */
+
+public class ScrollStartEndHelper implements Runnable{
+
+    private Handler handler;
+    private WXComponent component;
+    private boolean  hasStart;
+    private boolean  canStart = false;
+
+    private long  minInterval;
+    private int oldState = OnWXScrollListener.IDLE;
+
+    private int x;
+    private int y;
+    private boolean hasScrollEnd;
+
+
+    public ScrollStartEndHelper(WXComponent component) {
+        this.component = component;
+        this.handler = new Handler(Looper.getMainLooper());
+        this.minInterval = WXUtils.getNumberInt(component.getAttrs().get("minscrolldelayinterval"), 32);
+    }
+
+    /**
+     * @param  x scroll offset or dx, which is not accurate
+     * @param  y scroll offset or dy, which is not accurate
+     * */
+    public void  onScrolled(int x, int y){
+        if((component.getEvents().contains(Constants.Event.SCROLL_START)
+                || component.getEvents().contains(Constants.Event.SCROLL_END))){
+            this.x = x;
+            this.y = y;
+            if(!hasStart && canStart){
+                if(component.getEvents().contains(Constants.Event.SCROLL_START)){
+                    Map<String, Object> event = getScrollEvent(x,y);
+                    if (null !=event && !event.isEmpty()){
+                        component.fireEvent(Constants.Event.SCROLL_START,event);
+
+                    }
+                }
+                hasStart = true;
+                canStart = false;
+            }
+            handler.removeCallbacks(this);
+            handler.postDelayed(this, minInterval);
+        }
+    }
+
+
+    @Override
+    public void run() {
+        if(component.isDestoryed()){
+            return;
+        }
+        if(!hasScrollEnd){
+            return;
+        }
+        if(canStart){
+            component.fireEvent(Constants.Event.SCROLL_START, getScrollEvent(this.x, this.y));
+            canStart = false;
+        }
+        if(component.getEvents().contains(Constants.Event.SCROLL_END)){
+            component.fireEvent(Constants.Event.SCROLL_END, getScrollEvent(this.x, this.y));
+
+        }
+        hasStart = false;
+        hasScrollEnd = false;
+
+    }
+
+    private Map<String, Object> getScrollEvent(int offsetX, int offsetY){
+        if(component instanceof BasicListComponent){
+            BasicListComponent basicListComponent = (BasicListComponent) component;
+            if(basicListComponent.getHostView() instanceof ListComponentView){
+                ListComponentView componentView = (ListComponentView) basicListComponent.getHostView();
+                if(componentView != null){
+                    return basicListComponent.getScrollEvent(componentView.getInnerView(), offsetX, offsetY);
+                }
+            }
+        }else if(component instanceof WXRecyclerTemplateList){
+            WXRecyclerTemplateList templateList = (WXRecyclerTemplateList) component;
+            return templateList.getScrollEvent(templateList.getHostView().getInnerView(), offsetX, offsetY);
+        }else if(component instanceof WXScroller){
+            WXScroller scroller = (WXScroller) component;
+            return scroller.getScrollEvent(offsetX, offsetY);
+        }
+        return null;
+    }
+
+    public void onScrollStateChanged(int newState){
+
+        if(oldState == OnWXScrollListener.IDLE){
+            canStart = true;
+        }
+
+        if(newState == OnWXScrollListener.IDLE){
+            hasScrollEnd = true;
+            handler.removeCallbacks(this);
+            handler.postDelayed(this, minInterval);
+        }
+
+        oldState = newState;
+    }
+
+
+    public static boolean isScrollEvent(String type){
+        if(Constants.Event.SCROLL.equals(type)){
+            return  true;
+        }else if(Constants.Event.SCROLL_START.equals(type)){
+            return  true;
+        }else if(Constants.Event.SCROLL_END.equals(type)){
+            return  true;
+        }
+        return  false;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/helper/SoftKeyboardDetector.java b/android/sdk/src/main/java/org/apache/weex/ui/component/helper/SoftKeyboardDetector.java
new file mode 100644
index 0000000..b524e16
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/helper/SoftKeyboardDetector.java
@@ -0,0 +1,148 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.helper;
+
+import android.app.Activity;
+import android.graphics.Rect;
+import android.os.Build;
+import android.support.annotation.Nullable;
+import android.view.View;
+import android.view.ViewTreeObserver;
+import android.view.WindowManager;
+
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.lang.ref.WeakReference;
+
+/**
+ * Created by moxun on 17/3/24.
+ */
+
+public class SoftKeyboardDetector {
+
+    private static final int KEYBOARD_VISIBLE_THRESHOLD_DIP = 100;
+
+    public static Unregister registerKeyboardEventListener(Activity activity, final OnKeyboardEventListener listener) {
+        if (activity == null || listener == null) {
+            WXLogUtils.e("Activity or listener is null!");
+            return null;
+        }
+
+        if (activity.getWindow() != null) {
+            WindowManager.LayoutParams attributes = activity.getWindow().getAttributes();
+            if (attributes != null) {
+                int softInputMode = attributes.softInputMode;
+                if (softInputMode == WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING
+                        || softInputMode == WindowManager.LayoutParams.SOFT_INPUT_ADJUST_PAN) {
+                    WXLogUtils.e("SoftKeyboard detector can't work with softInputMode is SOFT_INPUT_ADJUST_NOTHING or SOFT_INPUT_ADJUST_PAN");
+                    return null;
+                }
+            }
+        }
+
+        final View activityRoot = getActivityRoot(activity);
+
+        if (activityRoot == null) {
+            WXLogUtils.e("Activity root is null!");
+            return null;
+        }
+
+        final ViewTreeObserver.OnGlobalLayoutListener layoutListener = new ViewTreeObserver.OnGlobalLayoutListener() {
+
+            private final Rect visibleFrame = new Rect();
+            private final int threshold = WXViewUtils.dip2px(KEYBOARD_VISIBLE_THRESHOLD_DIP);
+            private boolean wasKeyboardOpened = false;
+
+            @Override
+            public void onGlobalLayout() {
+                activityRoot.getWindowVisibleDisplayFrame(visibleFrame);
+                int heightDiff = activityRoot.getRootView().getHeight() - visibleFrame.height();
+                boolean isOpen = heightDiff > threshold;
+                if (isOpen == wasKeyboardOpened) {
+                    return;
+                }
+
+                wasKeyboardOpened = isOpen;
+                listener.onKeyboardEvent(isOpen);
+            }
+        };
+
+        activityRoot.getViewTreeObserver().addOnGlobalLayoutListener(layoutListener);
+        return new DefaultUnRegister(activity, layoutListener);
+    }
+
+    public static boolean isKeyboardVisible(Activity activity) {
+        Rect windowFrame = new Rect();
+        View root = getActivityRoot(activity);
+
+        if (root != null) {
+            root.getWindowVisibleDisplayFrame(windowFrame);
+            int heightDiff = root.getRootView().getHeight() - windowFrame.height();
+            return heightDiff > WXViewUtils.dip2px(KEYBOARD_VISIBLE_THRESHOLD_DIP);
+        }
+        return false;
+    }
+
+    public static @Nullable View getActivityRoot(Activity activity) {
+        if (activity != null) {
+            return activity.findViewById(android.R.id.content);
+        }
+        return null;
+    }
+
+    public static final class DefaultUnRegister implements Unregister {
+
+        private WeakReference<Activity> activityRef;
+        private WeakReference<ViewTreeObserver.OnGlobalLayoutListener> listenerRef;
+
+        public DefaultUnRegister(Activity activity, ViewTreeObserver.OnGlobalLayoutListener listener) {
+            this.activityRef = new WeakReference<>(activity);
+            this.listenerRef = new WeakReference<>(listener);
+        }
+
+        @Override
+        public void execute() {
+            Activity activity = activityRef.get();
+            ViewTreeObserver.OnGlobalLayoutListener listener = listenerRef.get();
+
+            if (activity != null && listener != null) {
+                View root = SoftKeyboardDetector.getActivityRoot(activity);
+                if (root != null) {
+                    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+                        root.getViewTreeObserver().removeOnGlobalLayoutListener(listener);
+                    } else {
+                        root.getViewTreeObserver().removeGlobalOnLayoutListener(listener);
+                    }
+                }
+            }
+
+            activityRef.clear();
+            listenerRef.clear();
+        }
+    }
+
+    public interface Unregister {
+        void execute();
+    }
+
+    public interface OnKeyboardEventListener {
+        void onKeyboardEvent(boolean isShown);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/helper/WXStickyHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/helper/WXStickyHelper.java
new file mode 100644
index 0000000..58b1d94
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/helper/WXStickyHelper.java
@@ -0,0 +1,67 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.helper;
+
+import org.apache.weex.ui.component.Scrollable;
+import org.apache.weex.ui.component.WXComponent;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+/**
+ * Created by miomin on 16/7/7.
+ */
+public class WXStickyHelper {
+
+    private Scrollable scrollable;
+
+    public WXStickyHelper(Scrollable scrollable) {
+        this.scrollable = scrollable;
+    }
+
+    public void bindStickStyle(WXComponent component, Map<String, Map<String, WXComponent>> mStickyMap) {
+        Scrollable scroller = component.getParentScroller();
+        if (scroller == null) {
+            return;
+        }
+        Map<String, WXComponent> stickyMap = mStickyMap.get(scroller
+                .getRef());
+        if (stickyMap == null) {
+            stickyMap = new ConcurrentHashMap<>();
+        }
+        if (stickyMap.containsKey(component.getRef())) {
+            return;
+        }
+        stickyMap.put(component.getRef(), component);
+        mStickyMap.put(scroller.getRef(), stickyMap);
+    }
+
+    public void unbindStickStyle(WXComponent component, Map<String, Map<String, WXComponent>> mStickyMap) {
+        Scrollable scroller = component.getParentScroller();
+        if (scroller == null) {
+            return;
+        }
+        Map<String, WXComponent> stickyMap = mStickyMap.get(scroller
+                .getRef());
+        if (stickyMap == null) {
+            return;
+        }
+        stickyMap.remove(component.getRef());
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/helper/WXTimeInputHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/helper/WXTimeInputHelper.java
new file mode 100644
index 0000000..600fde7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/helper/WXTimeInputHelper.java
@@ -0,0 +1,70 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.helper;
+
+import android.support.annotation.Nullable;
+import android.widget.TextView;
+
+import org.apache.weex.appfram.pickers.DatePickerImpl;
+import org.apache.weex.ui.component.AbstractEditComponent;
+
+/**
+ * Created by moxun on 16/10/12.
+ */
+
+public class WXTimeInputHelper {
+  public static void pickDate(String max, String min, final AbstractEditComponent component) {
+    final TextView target = component.getHostView();
+
+    DatePickerImpl.pickDate(
+            target.getContext(),
+            target.getText().toString(),
+            max,
+            min,
+            new DatePickerImpl.OnPickListener() {
+              @Override
+              public void onPick(boolean set, @Nullable String result) {
+                if (set) {
+                  target.setText(result);
+                  component.performOnChange(result);
+                }
+              }
+            },
+            null);
+  }
+
+  public static void pickTime(final AbstractEditComponent component) {
+    final TextView target = component.getHostView();
+
+    DatePickerImpl.pickTime(
+            target.getContext(),
+            target.getText().toString(),
+            new DatePickerImpl.OnPickListener() {
+              @Override
+              public void onPick(boolean set, @Nullable String result) {
+                if (set) {
+                  target.setText(result);
+                  component.performOnChange(result);
+                }
+              }
+            },
+            null
+    );
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/BasicListComponent.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/BasicListComponent.java
new file mode 100644
index 0000000..d4b8f52
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/BasicListComponent.java
@@ -0,0 +1,1477 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.annotation.SuppressLint;
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.graphics.Color;
+import android.graphics.Point;
+import android.graphics.PointF;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v4.util.ArrayMap;
+import android.support.v4.view.MotionEventCompat;
+import android.support.v4.view.ViewCompat;
+import android.support.v7.widget.GridLayoutManager;
+import android.support.v7.widget.LinearLayoutManager;
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+import android.text.TextUtils;
+import android.util.SparseArray;
+import android.view.Gravity;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewTreeObserver;
+import android.widget.FrameLayout;
+import android.widget.LinearLayout;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.ICheckBindingScroller;
+import org.apache.weex.common.OnWXScrollListener;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.AppearanceHelper;
+import org.apache.weex.ui.component.Scrollable;
+import org.apache.weex.ui.component.WXBaseRefresh;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXComponentProp;
+import org.apache.weex.ui.component.WXHeader;
+import org.apache.weex.ui.component.WXLoading;
+import org.apache.weex.ui.component.WXRefresh;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.component.helper.ScrollStartEndHelper;
+import org.apache.weex.ui.component.helper.WXStickyHelper;
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+import org.apache.weex.ui.view.listview.adapter.IOnLoadMoreListener;
+import org.apache.weex.ui.view.listview.adapter.IRecyclerAdapterListener;
+import org.apache.weex.ui.view.listview.adapter.ListBaseViewHolder;
+import org.apache.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
+import org.apache.weex.ui.view.listview.adapter.WXRecyclerViewOnScrollListener;
+import org.apache.weex.ui.view.refresh.wrapper.BounceRecyclerView;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.ArrayDeque;
+import java.util.ArrayList;
+import java.util.Deque;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.regex.Pattern;
+
+/**
+ * Created by sospartan on 13/12/2016.
+ */
+
+public abstract class BasicListComponent<T extends ViewGroup & ListComponentView> extends
+    WXVContainer<T> implements
+    IRecyclerAdapterListener<ListBaseViewHolder>, IOnLoadMoreListener, Scrollable {
+  public static final String TRANSFORM = "transform";
+  public static final String LOADMOREOFFSET = "loadmoreoffset";
+  private String TAG = "BasicListComponent";
+  private int mListCellCount = 0;
+  private boolean mForceLoadmoreNextTime = false;
+  private static final Pattern transformPattern = Pattern.compile("([a-z]+)\\(([0-9\\.]+),?([0-9\\.]+)?\\)");
+
+  private Map<String, AppearanceHelper> mAppearComponents = new HashMap<>();
+  private Runnable mAppearChangeRunnable = null;
+  private long mAppearChangeRunnableDelay = 50;
+
+  private boolean isScrollable = true;
+  private ArrayMap<String, Long> mRefToViewType;
+  private SparseArray<ArrayList<WXComponent>> mViewTypes;
+  private WXRecyclerViewOnScrollListener mViewOnScrollListener = new WXRecyclerViewOnScrollListener(this);
+
+  private static final int MAX_VIEWTYPE_ALLOW_CACHE = 9;
+  private static boolean mAllowCacheViewHolder = true;
+  private static boolean mDownForBidCacheViewHolder = false;
+
+
+  protected int mLayoutType = WXRecyclerView.TYPE_LINEAR_LAYOUT;
+  protected int mColumnCount = 1;
+  protected float mColumnGap = 0;
+  protected float mColumnWidth = 0;
+  protected float mLeftGap = 0;
+  protected float mRightGap = 0;
+
+  private int mOffsetAccuracy = 10;
+  private Point mLastReport = new Point(-1, -1);
+  private boolean mHasAddScrollEvent = false;
+
+  private RecyclerView.ItemAnimator mItemAnimator;
+
+  private DragHelper mDragHelper;
+
+  /**
+   * exclude cell when dragging(attributes for cell)
+   */
+  private static final String EXCLUDED = "dragExcluded";
+
+  /**
+   * the type to trigger drag-drop
+   */
+  private static final String DRAG_TRIGGER_TYPE = "dragTriggerType";
+
+  private static final String DEFAULT_TRIGGER_TYPE = DragTriggerType.LONG_PRESS;
+  private static final boolean DEFAULT_EXCLUDED = false;
+
+  private static final String DRAG_ANCHOR = "dragAnchor";
+
+  /**
+   * gesture type which can trigger drag&drop
+   */
+  interface DragTriggerType {
+    String PAN = "pan";
+    String LONG_PRESS = "longpress";
+  }
+
+  private String mTriggerType;
+
+  /**
+   * Map for storing component that is sticky.
+   **/
+  private Map<String, Map<String, WXComponent>> mStickyMap = new HashMap<>();
+  private WXStickyHelper stickyHelper;
+
+  /**
+   * scroll start and scroll end event
+   * */
+  private ScrollStartEndHelper mScrollStartEndHelper;
+
+  /**
+   * keep positon
+   * */
+  private  WXComponent keepPositionCell = null;
+  private  Runnable keepPositionCellRunnable = null;
+  private  long keepPositionLayoutDelay = 150;
+
+
+  public BasicListComponent(
+      WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+    stickyHelper = new WXStickyHelper(this);
+  }
+
+  @SuppressLint("RtlHardcoded")
+  @Override
+  public void setMarginsSupportRTL(ViewGroup.MarginLayoutParams lp, int left, int top, int right, int bottom) {
+    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR1) {
+      lp.setMargins(left, top, right, bottom);
+      lp.setMarginStart(left);
+      lp.setMarginEnd(right);
+    } else {
+      if (lp instanceof FrameLayout.LayoutParams) {
+        FrameLayout.LayoutParams lp_frameLayout = (FrameLayout.LayoutParams) lp;
+        if (this.isLayoutRTL()) {
+          lp_frameLayout.gravity = Gravity.RIGHT | Gravity.TOP;
+          lp.setMargins(right, top, left, bottom);
+        } else {
+          lp_frameLayout.gravity = Gravity.LEFT | Gravity.TOP;
+          lp.setMargins(left, top, right, bottom);
+        }
+      } else {
+        lp.setMargins(left, top, right, bottom);
+      }
+    }
+  }
+
+  @Override
+  public void setLayout(WXComponent component) {
+    if (component.getHostView() != null) {
+      int layoutDirection = component.isLayoutRTL() ? ViewCompat.LAYOUT_DIRECTION_RTL : ViewCompat.LAYOUT_DIRECTION_LTR;
+      ViewCompat.setLayoutDirection(component.getHostView(), layoutDirection);
+    }
+    super.setLayout(component);
+  }
+
+  @Override
+  protected void onHostViewInitialized(T host) {
+    super.onHostViewInitialized(host);
+
+    WXRecyclerView recyclerView = host.getInnerView();
+    if (recyclerView == null || recyclerView.getAdapter() == null) {
+      WXLogUtils.e(TAG, "RecyclerView is not found or Adapter is not bound");
+      return;
+    }
+    if(WXUtils.getBoolean(getAttrs().get("prefetchGapDisable"), false)){
+      if(recyclerView.getLayoutManager() != null){
+        recyclerView.getLayoutManager().setItemPrefetchEnabled(false);
+      }
+    }
+
+    if (mChildren == null) {
+      WXLogUtils.e(TAG, "children is null");
+      return;
+    }
+
+    mDragHelper = new DefaultDragHelper(mChildren, recyclerView, new EventTrigger() {
+      @Override
+      public void triggerEvent(String type, Map<String, Object> args) {
+        fireEvent(type, args);
+      }
+    });
+
+    mTriggerType = getTriggerType(this);
+  }
+
+  /**
+   * Measure the size of the recyclerView.
+   *
+   * @param width  the expected width
+   * @param height the expected height
+   * @return the result of measurement
+   */
+  @Override
+  protected MeasureOutput measure(int width, int height) {
+    int screenH = WXViewUtils.getScreenHeight(getInstanceId());
+    int weexH = WXViewUtils.getWeexHeight(getInstanceId());
+    int outHeight = height > (weexH >= screenH ? screenH : weexH) ? weexH - getAbsoluteY() : height;
+    return super.measure(width, outHeight);
+  }
+
+  public int getOrientation() {
+    return Constants.Orientation.VERTICAL;
+  }
+
+  @Override
+  public void destroy() {
+    if(mAppearChangeRunnable != null &&  getHostView() != null) {
+      getHostView().removeCallbacks(mAppearChangeRunnable);
+      mAppearChangeRunnable = null;
+    }
+    super.destroy();
+    if (mStickyMap != null)
+      mStickyMap.clear();
+    if (mViewTypes != null)
+      mViewTypes.clear();
+    if (mRefToViewType != null)
+      mRefToViewType.clear();
+
+  }
+
+  @Override
+  public ViewGroup.LayoutParams getChildLayoutParams(WXComponent child, View hostView, int width, int height, int left, int right, int top, int bottom) {
+    ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) hostView.getLayoutParams();
+    if (child instanceof WXBaseRefresh && params == null) {
+      params = new LinearLayout.LayoutParams(width, height);
+    } else if (params == null) {
+      params = new RecyclerView.LayoutParams(width, height);
+    } else {
+      params.width = width;
+      params.height = height;
+
+      this.setMarginsSupportRTL(params, left, 0, right, 0);
+    }
+    return params;
+  }
+
+  abstract T generateListView(Context context, int orientation);
+
+  @Override
+  protected T initComponentHostView(@NonNull Context context) {
+    T bounceRecyclerView = generateListView(context, getOrientation());
+
+    String transforms = getAttrByKey(TRANSFORM);
+    if (transforms != null) {
+      bounceRecyclerView.getInnerView().addItemDecoration(RecyclerTransform.parseTransforms(getOrientation(), transforms));
+    }
+    if(getAttrs().get(Constants.Name.KEEP_POSITION_LAYOUT_DELAY) != null){
+      keepPositionLayoutDelay = WXUtils.getNumberInt(getAttrs().get(Constants.Name.KEEP_POSITION_LAYOUT_DELAY), (int)keepPositionLayoutDelay);
+    }
+    if(getAttrs().get("appearActionDelay") != null){
+      mAppearChangeRunnableDelay =  WXUtils.getNumberInt(getAttrs().get("appearActionDelay"), (int) mAppearChangeRunnableDelay);
+    }
+
+    mItemAnimator=bounceRecyclerView.getInnerView().getItemAnimator();
+
+    RecyclerViewBaseAdapter recyclerViewBaseAdapter = new RecyclerViewBaseAdapter<>(this);
+    recyclerViewBaseAdapter.setHasStableIds(true);
+    bounceRecyclerView.setRecyclerViewBaseAdapter(recyclerViewBaseAdapter);
+    bounceRecyclerView.setOverScrollMode(View.OVER_SCROLL_NEVER);
+    bounceRecyclerView.getInnerView().addOnScrollListener(mViewOnScrollListener);
+    if(getAttrs().get(Constants.Name.HAS_FIXED_SIZE) != null){
+      boolean hasFixedSize = WXUtils.getBoolean(getAttrs().get(Constants.Name.HAS_FIXED_SIZE), false);
+      bounceRecyclerView.getInnerView().setHasFixedSize(hasFixedSize);
+    }
+
+    bounceRecyclerView.getInnerView().addOnScrollListener(new RecyclerView.OnScrollListener() {
+      @Override
+      public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
+        super.onScrollStateChanged(recyclerView, newState);
+        getScrollStartEndHelper().onScrollStateChanged(newState);
+        List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
+        int size;
+        OnWXScrollListener listener;
+        if (listeners != null && (size = listeners.size()) > 0) {
+          for (int i=0; i<size; ++i) {
+            if(i >= listeners.size()){
+              break;
+            }
+            listener = listeners.get(i);
+            if (listener != null) {
+              View topView = recyclerView.getChildAt(0);
+              if (topView != null) {
+                int y = topView.getTop();
+                listener.onScrollStateChanged(recyclerView, 0, y, newState);
+              }
+            }
+          }
+        }
+      }
+
+      @Override
+      public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
+        super.onScrolled(recyclerView, dx, dy);
+        List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
+        if (listeners != null && listeners.size() > 0) {
+          try {
+            for (OnWXScrollListener listener : listeners) {
+              if (listener != null) {
+                if (listener instanceof ICheckBindingScroller) {
+                  if (((ICheckBindingScroller) listener).isNeedScroller(getRef(), null)) {
+                    listener.onScrolled(recyclerView, dx, dy);
+                  }
+                } else {
+                  listener.onScrolled(recyclerView, dx, dy);
+                }
+              }
+            }
+          } catch (Exception e) {
+            e.printStackTrace();
+          }
+        }
+      }
+    });
+
+    bounceRecyclerView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
+      @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
+      @Override
+      public void onGlobalLayout() {
+        T view;
+        if ((view = getHostView()) == null)
+          return;
+        mViewOnScrollListener.onScrolled(view.getInnerView(), 0, 0);
+        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+          view.getViewTreeObserver().removeOnGlobalLayoutListener(this);
+        } else {
+          view.getViewTreeObserver().removeGlobalOnLayoutListener(this);
+        }
+      }
+    });
+    return bounceRecyclerView;
+  }
+
+  @Override
+  public void bindStickStyle(WXComponent component) {
+    stickyHelper.bindStickStyle(component, mStickyMap);
+  }
+
+  @Override
+  public void unbindStickStyle(WXComponent component) {
+    stickyHelper.unbindStickStyle(component, mStickyMap);
+    WXHeader cell = (WXHeader) findTypeParent(component, WXHeader.class);
+    if(cell != null && getHostView() != null) {
+      getHostView().notifyStickyRemove(cell);
+    }
+  }
+
+  private
+  @Nullable
+  WXComponent findDirectListChild(WXComponent comp) {
+    WXComponent parent;
+    if (comp == null || (parent = comp.getParent()) == null) {
+      return null;
+    }
+
+    if (parent instanceof BasicListComponent) {
+      return comp;
+    }
+
+    return findDirectListChild(parent);
+  }
+
+  @Override
+  protected boolean setProperty(String key, Object param) {
+    switch (key) {
+      case LOADMOREOFFSET:
+        return true;
+      case Constants.Name.SCROLLABLE:
+        boolean scrollable = WXUtils.getBoolean(param, true);
+        setScrollable(scrollable);
+        return true;
+      case Constants.Name.OFFSET_ACCURACY:
+        int accuracy = WXUtils.getInteger(param, 10);
+        setOffsetAccuracy(accuracy);
+        return true;
+      case Constants.Name.DRAGGABLE:
+        boolean draggable = WXUtils.getBoolean(param,false);
+        setDraggable(draggable);
+        return true;
+      case Constants.Name.SHOW_SCROLLBAR:
+        Boolean result = WXUtils.getBoolean(param,null);
+        if (result != null)
+          setShowScrollbar(result);
+        return true;
+    }
+    return super.setProperty(key, param);
+  }
+
+  @WXComponentProp(name = Constants.Name.SCROLLABLE)
+  public void setScrollable(boolean scrollable) {
+    this.isScrollable = scrollable;
+    WXRecyclerView inner = getHostView().getInnerView();
+    if(inner != null) {
+      inner.setScrollable(scrollable);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.OFFSET_ACCURACY)
+  public void setOffsetAccuracy(int accuracy) {
+    float real = WXViewUtils.getRealPxByWidth(accuracy, getInstance().getInstanceViewPortWidth());
+    this.mOffsetAccuracy = (int) real;
+  }
+
+  @WXComponentProp(name = Constants.Name.DRAGGABLE)
+  public void setDraggable(boolean isDraggable) {
+    if (mDragHelper != null) {
+      mDragHelper.setDraggable(isDraggable);
+    }
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("set draggable : " + isDraggable);
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.SHOW_SCROLLBAR)
+  public void setShowScrollbar(boolean show) {
+    if(getHostView() == null || getHostView().getInnerView() == null){
+      return;
+    }
+    if (getOrientation() == Constants.Orientation.VERTICAL) {
+      getHostView().getInnerView().setVerticalScrollBarEnabled(show);
+    } else {
+      getHostView().getInnerView().setHorizontalScrollBarEnabled(show);
+    }
+  }
+
+  @Override
+  public boolean isScrollable() {
+    return isScrollable;
+  }
+
+
+  private void setAppearanceWatch(WXComponent component, int event, boolean enable) {
+    AppearanceHelper item = mAppearComponents.get(component.getRef());
+    if (item != null) {
+      item.setWatchEvent(event, enable);
+    } else if (!enable) {
+      //Do nothing if disable target not exist.
+    } else {
+      WXComponent dChild = findDirectListChild(component);
+      int index = mChildren.indexOf(dChild);
+      if (index != -1) {
+        item = new AppearanceHelper(component, index);
+        item.setWatchEvent(event, true);
+        mAppearComponents.put(component.getRef(), item);
+      }
+    }
+  }
+
+  @Override
+  public void bindAppearEvent(WXComponent component) {
+    setAppearanceWatch(component, AppearanceHelper.APPEAR, true);
+    if(mAppearChangeRunnable == null){
+      mAppearChangeRunnable =  new Runnable() {
+        @Override
+        public void run() {
+          if(mAppearChangeRunnable != null) {
+            notifyAppearStateChange(0, 0, 0, 0);
+          }
+        }
+      };
+    }
+    if (getHostView() != null) {
+      getHostView().removeCallbacks(mAppearChangeRunnable);
+      getHostView().postDelayed(mAppearChangeRunnable, mAppearChangeRunnableDelay);
+    }
+  }
+
+  @Override
+  public void bindDisappearEvent(WXComponent component) {
+    setAppearanceWatch(component, AppearanceHelper.DISAPPEAR, true);
+  }
+
+  @Override
+  public void unbindAppearEvent(WXComponent component) {
+    setAppearanceWatch(component, AppearanceHelper.APPEAR, false);
+  }
+
+  @Override
+  public void unbindDisappearEvent(WXComponent component) {
+    setAppearanceWatch(component, AppearanceHelper.DISAPPEAR, false);
+  }
+
+  @Override
+  public void scrollTo(WXComponent component, Map<String, Object> options) {
+    float offsetFloat = 0;
+    boolean smooth = true;
+
+    if (options != null) {
+      String offsetStr = options.get(Constants.Name.OFFSET) == null ? "0" : options.get(Constants.Name.OFFSET).toString();
+      smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
+      if (offsetStr != null) {
+        try {
+          offsetFloat = WXViewUtils.getRealPxByWidth(Float.parseFloat(offsetStr), getInstance().getInstanceViewPortWidth());
+        }catch (Exception e ){
+          WXLogUtils.e("Float parseFloat error :"+e.getMessage());
+        }
+      }
+    }
+
+    final int offset = (int) offsetFloat;
+
+    T bounceRecyclerView = getHostView();
+    if (bounceRecyclerView == null) {
+      return;
+    }
+
+    WXComponent parent = component;
+    WXCell cell = null;
+    while (parent != null) {
+      if (parent instanceof WXCell) {
+        cell = (WXCell) parent;
+        break;
+      }
+      parent = parent.getParent();
+    }
+
+    if (cell != null) {
+      final int pos = mChildren.indexOf(cell);
+      if (pos == -1) {
+        //Invalid position
+        return;
+      }
+      final WXRecyclerView view = bounceRecyclerView.getInnerView();
+      view.scrollTo(smooth, pos, offset, getOrientation());
+    }
+  }
+
+  @Override
+  public void onBeforeScroll(int dx, int dy) {
+    T bounceRecyclerView = getHostView();
+    if (mStickyMap == null || bounceRecyclerView == null) {
+      return;
+    }
+    Map<String, WXComponent> stickyMap = mStickyMap.get(getRef());
+    if (stickyMap == null) {
+      return;
+    }
+    Iterator<Map.Entry<String, WXComponent>> iterator = stickyMap.entrySet().iterator();
+    Map.Entry<String, WXComponent> entry;
+    WXComponent stickyComponent;
+    int currentStickyPos = -1;
+    while (iterator.hasNext()) {
+      entry = iterator.next();
+      stickyComponent = entry.getValue();
+
+      if (stickyComponent != null && stickyComponent instanceof WXCell) {
+
+        WXCell cell = (WXCell) stickyComponent;
+        if (cell.getHostView() == null) {
+          return;
+        }
+
+        int[] location = new int[2];
+        stickyComponent.getHostView().getLocationOnScreen(location);
+        int[] parentLocation = new int[2];
+        stickyComponent.getParentScroller().getView().getLocationOnScreen(parentLocation);
+        int top = location[1] - parentLocation[1];
+
+
+        RecyclerView.LayoutManager layoutManager;
+        boolean beforeFirstVisibleItem = false;
+        boolean removeOldSticky = false;
+        layoutManager = getHostView().getInnerView().getLayoutManager();
+        if (layoutManager instanceof LinearLayoutManager || layoutManager instanceof GridLayoutManager) {
+          int firstVisiblePosition = ((LinearLayoutManager) layoutManager).findFirstVisibleItemPosition();
+          int lastVisiblePosition = ((LinearLayoutManager) layoutManager).findLastVisibleItemPosition();
+          int pos = mChildren.indexOf(cell);
+          cell.setScrollPositon(pos);
+          if (pos <= firstVisiblePosition
+                  || (cell.getStickyOffset() > 0 && firstVisiblePosition < pos && pos <= lastVisiblePosition  &&
+                  top <= cell.getStickyOffset())) {
+            beforeFirstVisibleItem = true;
+            if(pos > currentStickyPos) {
+              currentStickyPos = pos;
+            }
+          }else{
+            removeOldSticky = true;
+          }
+        } else if(layoutManager instanceof StaggeredGridLayoutManager){
+          int [] firstItems= new int[3];
+          int firstVisiblePosition = ((StaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(firstItems)[0];
+          int lastVisiblePosition = ((StaggeredGridLayoutManager)  layoutManager).findLastVisibleItemPositions(firstItems)[0];
+          int pos = mChildren.indexOf(cell);
+
+          if (pos <= firstVisiblePosition || (cell.getStickyOffset() > 0 && firstVisiblePosition < pos && pos <= lastVisiblePosition  &&
+                  top <= cell.getStickyOffset())) {
+            beforeFirstVisibleItem = true;
+            if(pos > currentStickyPos) {
+              currentStickyPos = pos;
+            }
+          }else{
+            removeOldSticky = true;
+          }
+        }
+
+
+        boolean showSticky = beforeFirstVisibleItem && cell.getLocationFromStart() >= 0 && top <= cell.getStickyOffset() && dy >= 0;
+        boolean removeSticky = cell.getLocationFromStart() <= cell.getStickyOffset() && top > cell.getStickyOffset() && dy <= 0;
+        if (showSticky) {
+          bounceRecyclerView.notifyStickyShow(cell);
+        } else if (removeSticky || removeOldSticky) {
+          bounceRecyclerView.notifyStickyRemove(cell);
+        }
+        cell.setLocationFromStart(top);
+      }
+    }
+
+    if(currentStickyPos >= 0){
+      bounceRecyclerView.updateStickyView(currentStickyPos);
+    }else{
+      if(bounceRecyclerView instanceof BounceRecyclerView){
+        ((BounceRecyclerView) bounceRecyclerView).getStickyHeaderHelper().clearStickyHeaders();
+      }
+    }
+  }
+
+  @Override
+  public int getScrollY() {
+    T bounceRecyclerView = getHostView();
+    return bounceRecyclerView == null ? 0 : bounceRecyclerView.getInnerView().getScrollY();
+  }
+
+  @Override
+  public int getScrollX() {
+    T bounceRecyclerView = getHostView();
+    return bounceRecyclerView == null ? 0 : bounceRecyclerView.getInnerView().getScrollX();
+  }
+
+  /**
+   * Append a child component to the end of list. This will not refresh the underlying
+   * view immediately. The message of index of the inserted child is given to the adapter, and the
+   * adapter will determine when to refresh. The default implementation of adapter will push the
+   * message into a message and refresh the view in a period of time.
+   *
+   * @param child the inserted child
+   */
+  @Override
+  public void addChild(WXComponent child) {
+    addChild(child, -1);
+  }
+
+  @Override
+  protected int getChildrenLayoutTopOffset() {
+    return 0;
+  }
+
+  /**
+   * @param child the inserted child
+   * @param index the index of the child to be inserted.
+   * @see #addChild(WXComponent)
+   */
+  @Override
+  public void addChild(WXComponent child, int index) {
+    super.addChild(child, index);
+    if (child == null || index < -1) {
+      return;
+    }
+    int count = mChildren.size();
+    index = index >= count ? -1 : index;
+    bindViewType(child);
+
+    int adapterPosition = index == -1 ? mChildren.size() - 1 : index;
+    final T view = getHostView();
+    if (view != null) {
+      boolean isAddAnimation = false;
+      if (getBasicComponentData() != null) {
+        Object attr = getAttrs().get(Constants.Name.INSERT_CELL_ANIMATION);
+        if (Constants.Value.DEFAULT.equals(attr)) {
+          isAddAnimation = true;
+        }
+      }
+      if (isAddAnimation) {
+        view.getInnerView().setItemAnimator(mItemAnimator);
+      } else {
+        view.getInnerView().setItemAnimator(null);
+      }
+      boolean isKeepScrollPosition =  false;
+      if (child.getBasicComponentData() != null) {
+        Object attr = child.getAttrs().get(Constants.Name.KEEP_SCROLL_POSITION);
+        if (WXUtils.getBoolean(attr, false) && index <= getChildCount() && index>-1) {
+          isKeepScrollPosition = true;
+        }
+      }
+      if (isKeepScrollPosition) {
+        if(view.getInnerView().getLayoutManager() instanceof  LinearLayoutManager){
+          if(keepPositionCell == null){
+            int last=((LinearLayoutManager)view.getInnerView().getLayoutManager()).findLastCompletelyVisibleItemPosition();
+            ListBaseViewHolder holder = (ListBaseViewHolder) view.getInnerView().findViewHolderForAdapterPosition(last);
+            if(holder != null){
+              keepPositionCell = holder.getComponent();
+            }
+            if(keepPositionCell != null) {
+              if(!view.getInnerView().isLayoutFrozen()){ //frozen, prevent layout when scroll
+                view.getInnerView().setLayoutFrozen(true);
+              }
+              if(keepPositionCellRunnable != null){
+                view.removeCallbacks(keepPositionCellRunnable);
+              }
+              keepPositionCellRunnable = new Runnable() {
+                @Override
+                public void run() {
+                  if(keepPositionCell != null){
+                    int keepPosition = indexOf(keepPositionCell);
+                    int offset = 0;
+                    if(keepPositionCell.getHostView() != null){
+                      offset = keepPositionCell.getHostView().getTop();
+                    }
+                    if(offset > 0) {
+                      ((LinearLayoutManager) view.getInnerView().getLayoutManager()).scrollToPositionWithOffset(keepPosition, offset);
+                    }else{
+                      view.getInnerView().getLayoutManager().scrollToPosition(keepPosition);
+
+                    }
+                    view.getInnerView().setLayoutFrozen(false);
+                    keepPositionCell = null;
+                    keepPositionCellRunnable = null;
+                  }
+                }
+              };
+            }
+          }
+          if(keepPositionCellRunnable == null){
+            view.getInnerView().scrollToPosition(((LinearLayoutManager)view.getInnerView().getLayoutManager()).findLastVisibleItemPosition());
+          }
+        }
+        view.getRecyclerViewBaseAdapter().notifyItemInserted(adapterPosition);
+        if(keepPositionCellRunnable != null){
+          view.removeCallbacks(keepPositionCellRunnable);
+          view.postDelayed(keepPositionCellRunnable, keepPositionLayoutDelay);
+        }
+      } else {
+        view.getRecyclerViewBaseAdapter().notifyItemChanged(adapterPosition);
+      }
+    }
+    relocateAppearanceHelper();
+  }
+
+  private void relocateAppearanceHelper() {
+    Iterator<Map.Entry<String, AppearanceHelper>> iterator = mAppearComponents.entrySet().iterator();
+    while (iterator.hasNext()) {
+      Map.Entry<String, AppearanceHelper> item = iterator.next();
+      AppearanceHelper value = item.getValue();
+      WXComponent dChild = findDirectListChild(value.getAwareChild());
+      int index = mChildren.indexOf(dChild);
+      value.setCellPosition(index);
+    }
+  }
+
+
+  /**
+   * RecyclerView manage its children in a way that different from {@link WXVContainer}. Therefore,
+   * {@link WXVContainer#addSubView(View, int)} is an empty implementation in {@link
+   * WXRecyclerView}
+   */
+  @Override
+  public void addSubView(View child, int index) {
+
+  }
+
+  /**
+   * Remove the child from list. This method will use {@link
+   * java.util.List#indexOf(Object)} to retrieve the component to be deleted. Like {@link
+   * #addChild(WXComponent)}, this method will not refresh the view immediately, the adapter will
+   * decide when to refresh.
+   *
+   * @param child the child to be removed
+   */
+  @Override
+  public void remove(WXComponent child, boolean destroy) {
+    int index = mChildren.indexOf(child);
+    if (destroy) {
+      child.detachViewAndClearPreInfo();
+    }
+    unBindViewType(child);
+
+    T view = getHostView();
+    if (view == null) {
+      return;
+    }
+
+    boolean isRemoveAnimation = false;
+    Object attr = child.getAttrs().get(Constants.Name.DELETE_CELL_ANIMATION);
+    if (Constants.Value.DEFAULT.equals(attr)) {
+      isRemoveAnimation = true;
+    }
+    if (isRemoveAnimation) {
+      view.getInnerView().setItemAnimator(mItemAnimator);
+    } else {
+      view.getInnerView().setItemAnimator(null);
+    }
+
+    view.getRecyclerViewBaseAdapter().notifyItemRemoved(index);
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d(TAG, "removeChild child at " + index);
+    }
+    super.remove(child, destroy);
+  }
+
+
+
+  @Override
+  public void computeVisiblePointInViewCoordinate(PointF pointF) {
+    RecyclerView view = getHostView().getInnerView();
+    pointF.set(view.computeHorizontalScrollOffset(), view.computeVerticalScrollOffset());
+  }
+
+  /**
+   * Recycle viewHolder and its underlying view. This may because the view is removed or reused.
+   * Either case, this method will be called.
+   *
+   * @param holder The view holder to be recycled.
+   */
+  @Override
+  public void onViewRecycled(ListBaseViewHolder holder) {
+    long begin = System.currentTimeMillis();
+
+    holder.setComponentUsing(false);
+    if (holder != null
+            && holder.canRecycled()
+            && holder.getComponent() != null
+            && !holder.getComponent().isUsing()) {
+      holder.recycled();
+
+    } else {
+      WXLogUtils.w(TAG, "this holder can not be allowed to  recycled");
+    }
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d(TAG, "Recycle holder " + (System.currentTimeMillis() - begin) + "  Thread:" + Thread.currentThread().getName());
+    }
+  }
+
+  /**
+   * Bind the component of the position to the holder. Then flush the view.
+   *
+   * @param holder   viewHolder, which holds reference to the view
+   * @param position position of component in list
+   */
+  @Override
+  public void onBindViewHolder(final ListBaseViewHolder holder, int position) {
+    if (holder == null) return;
+    holder.setComponentUsing(true);
+    WXComponent component = getChild(position);
+    if (component == null
+            || (component instanceof WXRefresh)
+            || (component instanceof WXLoading)
+            || (component.isFixed())
+            ) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.d(TAG, "Bind WXRefresh & WXLoading " + holder);
+      }
+      if(component instanceof  WXBaseRefresh
+              && holder.getView() != null
+              && (component.getAttrs().get("holderBackground") != null)){
+        Object holderBackground = component.getAttrs().get("holderBackground");
+        int color = WXResourceUtils.getColor(holderBackground.toString(), Color.WHITE);
+        holder.getView().setBackgroundColor(color);
+        holder.getView().setVisibility(View.VISIBLE);
+        holder.getView().postInvalidate();
+      }
+      return;
+    }
+
+    if (holder.getComponent() != null && holder.getComponent() instanceof WXCell) {
+      if(holder.isRecycled()) {
+        holder.bindData(component);
+        component.onRenderFinish(STATE_UI_FINISH);
+      }
+      if (mDragHelper == null || !mDragHelper.isDraggable()) {
+        return;
+      }
+      mTriggerType = (mTriggerType == null) ? DEFAULT_TRIGGER_TYPE : mTriggerType;
+
+      WXCell cell = (WXCell) holder.getComponent();
+      boolean isExcluded = DEFAULT_EXCLUDED;
+      WXAttr cellAttrs = cell.getAttrs();
+      isExcluded = WXUtils.getBoolean(cellAttrs.get(EXCLUDED), DEFAULT_EXCLUDED);
+
+      mDragHelper.setDragExcluded(holder, isExcluded);
+
+      //NOTICE: event maybe consumed by other views
+      if (DragTriggerType.PAN.equals(mTriggerType)) {
+        mDragHelper.setLongPressDragEnabled(false);
+
+        WXComponent anchorComponent = findComponentByAnchorName(cell, DRAG_ANCHOR);
+
+        if (anchorComponent != null && anchorComponent.getHostView() != null && !isExcluded) {
+          View anchor = anchorComponent.getHostView();
+          anchor.setOnTouchListener(new View.OnTouchListener() {
+            @SuppressLint("ClickableViewAccessibility")
+            @Override
+            public boolean onTouch(View v, MotionEvent event) {
+              if (MotionEventCompat.getActionMasked(event) == MotionEvent.ACTION_DOWN) {
+                mDragHelper.startDrag(holder);
+              }
+              return true;
+            }
+          });
+        } else {
+          if (WXEnvironment.isApkDebugable()) {
+            if(!isExcluded) {
+              WXLogUtils.e(TAG, "[error] onBindViewHolder: the anchor component or view is not found");
+            } else {
+              WXLogUtils.d(TAG, "onBindViewHolder: position "+ position + " is drag excluded");
+            }
+          }
+        }
+
+      } else if (DragTriggerType.LONG_PRESS.equals(mTriggerType)) {
+        mDragHelper.setLongPressDragEnabled(true);
+      }
+    }
+
+  }
+
+  protected void markComponentUsable(){
+    for (WXComponent component : mChildren){
+      component.setUsing(false);
+    }
+  }
+  /**
+   * Create an instance of {@link ListBaseViewHolder} for the given viewType (not for the given
+   * index). This  markComponentUsable();method will look up for the first component that fits the viewType requirement and
+   * doesn't be used. Then create the certain type of view, detach the view f[rom the component.
+   *
+   * @param parent   the ViewGroup into which the new view will be inserted
+   * @param viewType the type of the new view
+   * @return the created view holder.
+   */
+  @Override
+  public ListBaseViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
+    if (mChildren != null) {
+      if (mViewTypes == null)
+        return createVHForFakeComponent(viewType);
+      ArrayList<WXComponent> mTypes = mViewTypes.get(viewType);
+      checkRecycledViewPool(viewType);
+      if (mTypes == null)
+        return createVHForFakeComponent(viewType);
+
+      for (int i = 0; i < mTypes.size(); i++) {
+        WXComponent component = mTypes.get(i);
+        if (component == null
+            || component.isUsing()) {
+          continue;
+        }
+        if (component.isFixed()) {
+          return createVHForFakeComponent(viewType);
+        } else {
+          if (component instanceof WXCell) {
+            if (component.getRealView() != null) {
+              return new ListBaseViewHolder(component, viewType);
+            } else {
+              component.lazy(false);
+              component.createView();
+              component.applyLayoutAndEvent(component);
+              return new ListBaseViewHolder(component, viewType, true);
+            }
+          } else if (component instanceof WXBaseRefresh) {
+            return createVHForRefreshComponent(viewType);
+          } else {
+            WXLogUtils.e(TAG, "List cannot include element except cell、header、fixed、refresh and loading");
+            return createVHForFakeComponent(viewType);
+          }
+        }
+      }
+    }
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.e(TAG, "Cannot find request viewType: " + viewType);
+    }
+    return createVHForFakeComponent(viewType);
+  }
+
+  /**
+   * Forbid ViewHolder cache if viewType > MAX_VIEWTYPE_ALLOW_CACHE
+   *
+   * @param viewType
+   */
+  private void checkRecycledViewPool(int viewType) {
+    try {
+      if (mViewTypes.size() > MAX_VIEWTYPE_ALLOW_CACHE)
+        mAllowCacheViewHolder = false;
+
+      if (mDownForBidCacheViewHolder)
+        if (getHostView() != null && getHostView().getInnerView() != null)
+          getHostView().getInnerView().getRecycledViewPool().setMaxRecycledViews(viewType, 0);
+
+      if (!mDownForBidCacheViewHolder) {
+        if (!mAllowCacheViewHolder) {
+          if (getHostView() != null && getHostView().getInnerView() != null) {
+            for (int i = 0; i < mViewTypes.size(); i++) {
+              getHostView().getInnerView().getRecycledViewPool().setMaxRecycledViews(mViewTypes.keyAt(i), 0);
+            }
+            mDownForBidCacheViewHolder = true;
+          }
+        }
+      }
+    } catch (Exception e) {
+      WXLogUtils.e(TAG, "Clear recycledViewPool error!");
+    }
+  }
+
+  /**
+   * Return the child component type. The type is defined by scopeValue in .we file.
+   *
+   * @param position the position of the child component.
+   * @return the type of certain component.
+   */
+  @Override
+  public int getItemViewType(int position) {
+    return generateViewType(getChild(position));
+  }
+
+  @Nullable
+  private WXComponent findComponentByAnchorName(@NonNull WXComponent root, @NonNull String anchorName) {
+    long start = 0;
+    if (WXEnvironment.isApkDebugable()) {
+      start = System.currentTimeMillis();
+    }
+
+    Deque<WXComponent> deque = new ArrayDeque<>();
+    deque.add(root);
+    while (!deque.isEmpty()) {
+      WXComponent curComponent = deque.removeFirst();
+      if (curComponent != null) {
+        String isAnchorSet = WXUtils.getString(curComponent.getAttrs().get(anchorName), null);
+
+        //hit
+        if (isAnchorSet != null && isAnchorSet.equals("true")) {
+          if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.d("dragPerf", "findComponentByAnchorName time: " + (System.currentTimeMillis() - start) + "ms");
+          }
+          return curComponent;
+        }
+      }
+      if (curComponent instanceof WXVContainer) {
+        WXVContainer container = (WXVContainer) curComponent;
+        for (int i = 0, len = container.childCount(); i < len; i++) {
+          WXComponent child = container.getChild(i);
+          deque.add(child);
+        }
+      }
+    }
+
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("dragPerf", "findComponentByAnchorName elapsed time: " + (System.currentTimeMillis() - start) + "ms");
+    }
+    return null;
+
+  }
+
+  private String getTriggerType(@Nullable WXComponent component) {
+    String triggerType = DEFAULT_TRIGGER_TYPE;
+    if (component == null) {
+      return triggerType;
+    }
+    triggerType = WXUtils.getString(component.getAttrs().get(DRAG_TRIGGER_TYPE), DEFAULT_TRIGGER_TYPE);
+    if (!DragTriggerType.LONG_PRESS.equals(triggerType) && !DragTriggerType.PAN.equals(triggerType)) {
+      triggerType = DEFAULT_TRIGGER_TYPE;
+    }
+
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d(TAG, "trigger type is " + triggerType);
+    }
+
+    return triggerType;
+  }
+
+
+  /**
+   * ViewType will be classified into {HashMap<Integer,ArrayList<Integer>> mViewTypes}
+   *
+   * @param component
+   */
+  private void bindViewType(WXComponent component) {
+    int id = generateViewType(component);
+
+    if (mViewTypes == null) {
+      mViewTypes = new SparseArray<>();
+    }
+
+    ArrayList<WXComponent> mTypes = mViewTypes.get(id);
+
+    if (mTypes == null) {
+      mTypes = new ArrayList<>();
+      mViewTypes.put(id, mTypes);
+    }
+    mTypes.add(component);
+  }
+
+  private void unBindViewType(WXComponent component) {
+    int id = generateViewType(component);
+
+    if (mViewTypes == null)
+      return;
+    ArrayList<WXComponent> mTypes = mViewTypes.get(id);
+    if (mTypes == null)
+      return;
+
+    mTypes.remove(component);
+  }
+
+  /**
+   * generate viewtype by component
+   *
+   * @param component
+   * @return
+   */
+  private int generateViewType(WXComponent component) {
+    long id;
+    try {
+      id = Integer.parseInt(component.getRef());
+      String type = component.getAttrs().getScope();
+
+      if (!TextUtils.isEmpty(type)) {
+        if (mRefToViewType == null) {
+          mRefToViewType = new ArrayMap<>();
+        }
+        if (!mRefToViewType.containsKey(type)) {
+          mRefToViewType.put(type, id);
+        }
+        id = mRefToViewType.get(type);
+
+      }
+    } catch (RuntimeException e) {
+      WXLogUtils.eTag(TAG, e);
+      id = RecyclerView.NO_ID;
+      WXLogUtils.e(TAG, "getItemViewType: NO ID, this will crash the whole render system of WXListRecyclerView");
+    }
+    return (int) id;
+  }
+
+  /**
+   * Get child component num.
+   *
+   * @return return the size of {@link #mChildren} if mChildren is not empty, otherwise, return 0;
+   */
+  @Override
+  public int getItemCount() {
+    return getChildCount();
+  }
+
+  @Override
+  public boolean onFailedToRecycleView(ListBaseViewHolder holder) {
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d(TAG, "Failed to recycle " + holder);
+    }
+    return false;
+  }
+
+  @Override
+  public long getItemId(int position) {
+    long id;
+    try {
+      id = Long.parseLong(getChild(position).getRef());
+    } catch (RuntimeException e) {
+      WXLogUtils.e(TAG, WXLogUtils.getStackTrace(e));
+      id = RecyclerView.NO_ID;
+    }
+    return id;
+  }
+
+  @Override
+  public void onLoadMore(int offScreenY) {
+    try {
+      String offset = getAttrs().getLoadMoreOffset();
+
+      if (TextUtils.isEmpty(offset)) {
+        offset = "0";
+      }
+
+
+      float offsetParsed = WXViewUtils.getRealPxByWidth(WXUtils.getInt(offset),getInstance().getInstanceViewPortWidth());
+
+      if (offScreenY <= offsetParsed && getEvents().contains(Constants.Event.LOADMORE)) {
+        if (mListCellCount != mChildren.size()
+            || mForceLoadmoreNextTime) {
+          fireEvent(Constants.Event.LOADMORE);
+          mListCellCount = mChildren.size();
+          mForceLoadmoreNextTime = false;
+        }
+      }
+    } catch (Exception e) {
+      WXLogUtils.d(TAG + "onLoadMore :", e);
+    }
+  }
+
+  @Override
+  public void notifyAppearStateChange(int firstVisible, int lastVisible, int directionX, int directionY) {
+    if(mAppearChangeRunnable != null) {
+      getHostView().removeCallbacks(mAppearChangeRunnable);
+      mAppearChangeRunnable = null;
+    }
+    //notify appear state
+    Iterator<AppearanceHelper> it = mAppearComponents.values().iterator();
+    String direction = directionY > 0 ? Constants.Value.DIRECTION_UP :
+            directionY < 0 ? Constants.Value.DIRECTION_DOWN : null;
+    if (getOrientation() == Constants.Orientation.HORIZONTAL && directionX != 0) {
+      direction = directionX > 0 ? Constants.Value.DIRECTION_LEFT : Constants.Value.DIRECTION_RIGHT;
+    }
+
+    while (it.hasNext()) {
+      AppearanceHelper item = it.next();
+      WXComponent component = item.getAwareChild();
+
+      if (!item.isWatch()) {
+        continue;
+      }
+
+
+      View view = component.getHostView();
+      if (view == null) {
+        continue;
+      }
+
+      boolean outOfVisibleRange = !ViewCompat.isAttachedToWindow(view);
+      boolean visible = (!outOfVisibleRange) && item.isViewVisible(true);
+
+      int result = item.setAppearStatus(visible);
+      if (result == AppearanceHelper.RESULT_NO_CHANGE) {
+        continue;
+      }
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.d("appear", "item " + item.getCellPositionINScollable() + " result " + result);
+      }
+      component.notifyAppearStateChange(result == AppearanceHelper.RESULT_APPEAR ? Constants.Event.APPEAR : Constants.Event.DISAPPEAR, direction);
+    }
+  }
+
+  @NonNull
+  private ListBaseViewHolder createVHForFakeComponent(int viewType) {
+    FrameLayout view = new FrameLayout(getContext());
+    view.setBackgroundColor(Color.WHITE);
+    view.setLayoutParams(new FrameLayout.LayoutParams(0, 0));
+    return new ListBaseViewHolder(view, viewType);
+  }
+
+
+  private ListBaseViewHolder createVHForRefreshComponent(int viewType) {
+    FrameLayout view = new FrameLayout(getContext());
+    view.setLayoutParams(new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, 1));
+    return new ListBaseViewHolder(view, viewType);
+  }
+
+  @JSMethod
+  public void resetLoadmore() {
+    mForceLoadmoreNextTime = true;
+    mListCellCount = 0;
+  }
+
+  @Override
+  public void addEvent(String type) {
+    super.addEvent(type);
+    if (ScrollStartEndHelper.isScrollEvent(type)
+            && getHostView() != null
+            && getHostView().getInnerView() != null
+            && !mHasAddScrollEvent) {
+      mHasAddScrollEvent = true;
+      WXRecyclerView innerView = getHostView().getInnerView();
+      innerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
+        private int offsetXCorrection, offsetYCorrection;
+        private boolean mFirstEvent = true;
+
+        @Override
+        public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
+          super.onScrolled(recyclerView, dx, dy);
+//          WXLogUtils.e("SCROLL", dx + ", " + dy + ", " + recyclerView.computeHorizontalScrollRange()
+//          + ", " + recyclerView.computeVerticalScrollRange()
+//          + ", " + recyclerView.computeHorizontalScrollOffset()
+//          + ", " + recyclerView.computeVerticalScrollOffset());
+
+          int offsetX = recyclerView.computeHorizontalScrollOffset();
+          int offsetY = recyclerView.computeVerticalScrollOffset();
+
+          if (dx == 0 && dy == 0) {
+            offsetXCorrection = offsetX;
+            offsetYCorrection = offsetY;
+            offsetX = 0;
+            offsetY = 0;
+          } else {
+            offsetX = offsetX - offsetXCorrection;
+            offsetY = offsetY - offsetYCorrection;
+          }
+          getScrollStartEndHelper().onScrolled(offsetX, offsetY);
+          if(!getEvents().contains(Constants.Event.SCROLL)){
+            return;
+          }
+          if (mFirstEvent) {
+            //skip first event
+            mFirstEvent = false;
+            return;
+          }
+
+          RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
+          if (!layoutManager.canScrollVertically()) {
+            return;
+          }
+
+          if (shouldReport(offsetX, offsetY)) {
+            fireScrollEvent(recyclerView, offsetX, offsetY);
+          }
+        }
+      });
+    }
+  }
+
+  private void fireScrollEvent(RecyclerView recyclerView, int offsetX, int offsetY) {
+    fireEvent(Constants.Event.SCROLL, getScrollEvent(recyclerView, offsetX, offsetY));
+  }
+
+  public Map<String, Object> getScrollEvent(RecyclerView recyclerView, int offsetX, int offsetY){
+    if(getOrientation() == Constants.Orientation.VERTICAL){
+      offsetY = - calcContentOffset(recyclerView);
+    }
+    int contentWidth = recyclerView.getMeasuredWidth() + recyclerView.computeHorizontalScrollRange();
+    int contentHeight = 0;
+    for (int i = 0; i < getChildCount(); i++) {
+      WXComponent child = getChild(i);
+      if (child != null) {
+        contentHeight += child.getLayoutHeight();
+      }
+    }
+
+    Map<String, Object> event = new HashMap<>(3);
+    Map<String, Object> contentSize = new HashMap<>(3);
+    Map<String, Object> contentOffset = new HashMap<>(3);
+
+    contentSize.put(Constants.Name.WIDTH, WXViewUtils.getWebPxByWidth(contentWidth, getInstance().getInstanceViewPortWidth()));
+    contentSize.put(Constants.Name.HEIGHT, WXViewUtils.getWebPxByWidth(contentHeight, getInstance().getInstanceViewPortWidth()));
+
+    contentOffset.put(Constants.Name.X, - WXViewUtils.getWebPxByWidth(offsetX, getInstance().getInstanceViewPortWidth()));
+    contentOffset.put(Constants.Name.Y, - WXViewUtils.getWebPxByWidth(offsetY, getInstance().getInstanceViewPortWidth()));
+    event.put(Constants.Name.CONTENT_SIZE, contentSize);
+    event.put(Constants.Name.CONTENT_OFFSET, contentOffset);
+    event.put(Constants.Name.ISDRAGGING, recyclerView.getScrollState() == RecyclerView.SCROLL_STATE_DRAGGING);
+    return event;
+  }
+
+  private boolean shouldReport(int offsetX, int offsetY) {
+    if (mLastReport.x == -1 && mLastReport.y == -1) {
+      mLastReport.x = offsetX;
+      mLastReport.y = offsetY;
+      return true;
+    }
+
+    int gapX = Math.abs(mLastReport.x - offsetX);
+    int gapY = Math.abs(mLastReport.y - offsetY);
+
+    if (gapX >= mOffsetAccuracy || gapY >= mOffsetAccuracy) {
+      mLastReport.x = offsetX;
+      mLastReport.y = offsetY;
+      return true;
+    }
+
+    return false;
+  }
+
+
+
+  public int calcContentOffset(RecyclerView recyclerView) {
+    RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
+    if (layoutManager instanceof LinearLayoutManager) {
+      int firstVisibleItemPosition = ((LinearLayoutManager) layoutManager).findFirstVisibleItemPosition();
+      if (firstVisibleItemPosition == -1) {
+        return 0;
+      }
+
+      View firstVisibleView = layoutManager.findViewByPosition(firstVisibleItemPosition);
+      int firstVisibleViewOffset = 0;
+      if (firstVisibleView != null) {
+        firstVisibleViewOffset = firstVisibleView.getTop();
+      }
+
+      int offset = 0;
+      for (int i=0;i<firstVisibleItemPosition;i++) {
+        WXComponent child = getChild(i);
+        if (child != null) {
+          offset -= child.getLayoutHeight();
+        }
+      }
+
+      if (layoutManager instanceof GridLayoutManager) {
+        int spanCount = ((GridLayoutManager) layoutManager).getSpanCount();
+        offset = offset / spanCount;
+      }
+
+      offset += firstVisibleViewOffset;
+      return offset;
+    } else if (layoutManager instanceof StaggeredGridLayoutManager) {
+      int spanCount = ((StaggeredGridLayoutManager) layoutManager).getSpanCount();
+      int firstVisibleItemPosition = ((StaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(null)[0];
+      if (firstVisibleItemPosition == -1) {
+        return 0;
+      }
+
+      View firstVisibleView = layoutManager.findViewByPosition(firstVisibleItemPosition);
+      int firstVisibleViewOffset = 0;
+      if (firstVisibleView != null) {
+        firstVisibleViewOffset = firstVisibleView.getTop();
+      }
+
+      int offset = 0;
+      for (int i=0;i<firstVisibleItemPosition;i++) {
+        WXComponent child = getChild(i);
+        if (child != null) {
+          offset -= child.getLayoutHeight();
+        }
+      }
+
+      offset = offset / spanCount;
+      offset += firstVisibleViewOffset;
+      return offset;
+    }
+    //Unhandled LayoutManager type
+    return -1;
+  }
+
+  public ScrollStartEndHelper getScrollStartEndHelper() {
+    if(mScrollStartEndHelper == null){
+      mScrollStartEndHelper = new ScrollStartEndHelper(this);
+    }
+    return mScrollStartEndHelper;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/DefaultDragHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/DefaultDragHelper.java
new file mode 100644
index 0000000..944e91c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/DefaultDragHelper.java
@@ -0,0 +1,173 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.helper.ItemTouchHelper;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Description:
+ * Drag-drop support for list
+ * <p>
+ * Created by rowandjj(chuyi)<br/>
+ */
+
+class DefaultDragHelper implements DragHelper {
+
+    private boolean mLongPressEnabled;
+
+    @NonNull
+    private final EventTrigger mEventTrigger;
+    @NonNull
+    private final RecyclerView mRecyclerView;
+    @NonNull
+    private final List<WXComponent> mDataSource;
+    @NonNull
+    private ItemTouchHelper mItemTouchHelper;
+
+    private static final String EVENT_START_DRAG = "dragstart";
+    private static final String EVENT_END_DRAG = "dragend";
+
+    private static final String TAG_EXCLUDED = "drag_excluded";
+
+    private static final String TAG = "WXListExComponent";
+
+    private boolean isDraggable = false;
+
+    DefaultDragHelper(@NonNull List<WXComponent> dataSource, @NonNull RecyclerView recyclerView, @NonNull EventTrigger trigger) {
+        this.mDataSource = dataSource;
+        this.mEventTrigger = trigger;
+        this.mRecyclerView = recyclerView;
+
+        //attach
+        this.mItemTouchHelper = new ItemTouchHelper(new DragSupportCallback(this, true));
+        try {
+            mItemTouchHelper.attachToRecyclerView(mRecyclerView);
+        }catch (Throwable e) {
+            //ignore
+        }
+    }
+
+    @Override
+    public void onDragStart(@NonNull WXComponent component, int from) {
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.d(TAG, "list on drag start : from index " + from);
+        }
+        mEventTrigger.triggerEvent(EVENT_START_DRAG, buildEvent(component.getRef(), from, -1));
+    }
+
+    @Override
+    public void onDragEnd(@NonNull WXComponent component, int from, int to) {
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.d(TAG, "list on drag end : " + "from index " + from + " to index " + to);
+        }
+        mEventTrigger.triggerEvent(EVENT_END_DRAG, buildEvent(component.getRef(), from, to));
+    }
+
+    @Override
+    public void onDragging(int fromPos, int toPos) {
+        if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.d(TAG, "list on dragging : from index " + fromPos + " to index " + toPos);
+        }
+
+        RecyclerView.Adapter adapter = mRecyclerView.getAdapter();
+        if (adapter == null) {
+            WXLogUtils.e(TAG, "drag failed because of RecyclerView#Adapter is not bound");
+            return;
+        }
+
+        if (fromPos >= 0 && fromPos <= mDataSource.size() - 1 && toPos >= 0 && toPos <= mDataSource.size() - 1) {
+            Collections.swap(mDataSource, fromPos, toPos);
+            adapter.notifyItemMoved(fromPos, toPos);
+        }
+    }
+
+    @Override
+    public boolean isLongPressDragEnabled() {
+        return mLongPressEnabled;
+    }
+
+    @Override
+    public void setLongPressDragEnabled(boolean enabled) {
+        this.mLongPressEnabled = enabled;
+    }
+
+    @Override
+    public void startDrag(@NonNull RecyclerView.ViewHolder viewHolder) {
+        if (isDraggable) {
+            mItemTouchHelper.startDrag(viewHolder);
+        }
+    }
+
+    @Override
+    public boolean isDraggable() {
+        return this.isDraggable;
+    }
+
+    @Override
+    public void setDraggable(boolean draggable) {
+        this.isDraggable = draggable;
+    }
+
+    @Override
+    public void setDragExcluded(@NonNull RecyclerView.ViewHolder viewHolder, boolean isExcluded) {
+        if (viewHolder.itemView == null) {
+            if (WXEnvironment.isApkDebugable()) {
+                WXLogUtils.e(TAG, "[error] viewHolder.itemView is null");
+            }
+            return;
+        }
+        if (isExcluded) {
+            viewHolder.itemView.setTag(TAG_EXCLUDED);
+        } else {
+            viewHolder.itemView.setTag(null);
+        }
+    }
+
+    @Override
+    public boolean isDragExcluded(@NonNull RecyclerView.ViewHolder viewHolder) {
+        if (viewHolder.itemView == null) {
+            if (WXEnvironment.isApkDebugable()) {
+                WXLogUtils.e(TAG, "[error] viewHolder.itemView is null");
+            }
+            return false;
+        }
+        return viewHolder.itemView.getTag() != null && TAG_EXCLUDED.equals(viewHolder.itemView.getTag());
+    }
+
+    private Map<String, Object> buildEvent(@Nullable String target, int fromIndex, int toIndex) {
+        Map<String, Object> args = new HashMap<>(4);
+        args.put("target", target == null ? "unknown" : target);
+        args.put("fromIndex", fromIndex);
+        args.put("toIndex", toIndex);
+        args.put("timestamp", System.currentTimeMillis());
+        return args;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/DragHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/DragHelper.java
new file mode 100644
index 0000000..8d3337f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/DragHelper.java
@@ -0,0 +1,53 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.support.annotation.NonNull;
+import android.support.v7.widget.RecyclerView;
+
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Description:
+ *
+ * interface for drag&drop support
+ *
+ */
+interface DragHelper {
+
+    void onDragStart(@NonNull WXComponent component, int from);
+
+    void onDragEnd(@NonNull WXComponent component, int from, int to);
+
+    void onDragging(int fromPos, int toPos);
+
+    boolean isLongPressDragEnabled();
+
+    void setLongPressDragEnabled(boolean enabled);
+
+    void startDrag(@NonNull RecyclerView.ViewHolder viewHolder);
+
+    boolean isDraggable();
+
+    void setDraggable(boolean draggable);
+
+    void setDragExcluded(@NonNull RecyclerView.ViewHolder viewHolder, boolean isExcluded);
+
+    boolean isDragExcluded(@NonNull RecyclerView.ViewHolder viewHolder);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/DragSupportCallback.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/DragSupportCallback.java
new file mode 100644
index 0000000..0a71b3b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/DragSupportCallback.java
@@ -0,0 +1,142 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.support.annotation.NonNull;
+import android.support.v7.widget.GridLayoutManager;
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+import android.support.v7.widget.helper.ItemTouchHelper;
+
+import org.apache.weex.ui.view.listview.adapter.ListBaseViewHolder;
+import org.apache.weex.utils.WXLogUtils;
+
+/**
+ * Description:
+ * An implementation of {@link ItemTouchHelper.Callback}. with drag&drop support:)
+ *
+ */
+class DragSupportCallback extends ItemTouchHelper.Callback {
+    private final DragHelper mDragHelper;
+    private boolean mEnableDifferentViewTypeDrag = false;
+
+    private int dragFrom = -1;
+    private int dragTo = -1;
+
+    private static final String TAG = "WXListExComponent";
+
+    DragSupportCallback(@NonNull DragHelper DragHelper) {
+        this.mDragHelper = DragHelper;
+        this.mEnableDifferentViewTypeDrag = false;
+    }
+
+    DragSupportCallback(@NonNull DragHelper DragHelper, boolean enableDifferentViewTypeDrag) {
+        this.mDragHelper = DragHelper;
+        this.mEnableDifferentViewTypeDrag = enableDifferentViewTypeDrag;
+    }
+
+    @Override
+    public int getMovementFlags(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) {
+        if (recyclerView.getLayoutManager() instanceof GridLayoutManager || recyclerView.getLayoutManager() instanceof StaggeredGridLayoutManager) {
+            int dragFlags = ItemTouchHelper.UP | ItemTouchHelper.DOWN | ItemTouchHelper.LEFT | ItemTouchHelper.RIGHT;
+            int swipeFlags = 0;
+            return makeMovementFlags(dragFlags, swipeFlags);
+        } else {
+            int dragFlags = ItemTouchHelper.UP | ItemTouchHelper.DOWN;
+            int swipeFlags = ItemTouchHelper.START | ItemTouchHelper.END;
+            return makeMovementFlags(dragFlags, swipeFlags);
+        }
+    }
+
+    @Override
+    public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target) {
+        if (viewHolder == null || target == null) {
+            return false;
+        }
+
+        if (!mEnableDifferentViewTypeDrag && viewHolder.getItemViewType() != target.getItemViewType()) {
+            return false;
+        }
+
+        if (mDragHelper.isDragExcluded(viewHolder)) {
+            return false;
+        }
+
+        try {
+            int fromPos = viewHolder.getAdapterPosition();
+            int toPos = target.getAdapterPosition();
+
+            if (dragFrom == -1) {
+                dragFrom = fromPos;
+            }
+            dragTo = toPos;
+
+            mDragHelper.onDragging(fromPos, toPos);
+            return true;
+        } catch (Exception e) {
+            WXLogUtils.e(TAG, e.getMessage());
+            return false;
+        }
+    }
+
+
+    @Override
+    public boolean isLongPressDragEnabled() {
+        return mDragHelper.isDraggable() && mDragHelper.isLongPressDragEnabled();
+    }
+
+    @Override
+    public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction) {
+    }
+
+    @Override
+    public boolean isItemViewSwipeEnabled() {
+        return false;
+    }
+
+    @Override
+    public void onSelectedChanged(RecyclerView.ViewHolder viewHolder, int actionState) {
+        if (actionState != ItemTouchHelper.ACTION_STATE_IDLE && viewHolder instanceof ListBaseViewHolder) {
+            ListBaseViewHolder vh = (ListBaseViewHolder) viewHolder;
+            if (vh.getComponent() != null) {
+                mDragHelper.onDragStart(vh.getComponent(), vh.getAdapterPosition());
+            }
+        }
+
+        super.onSelectedChanged(viewHolder, actionState);
+    }
+
+
+    @Override
+    public void clearView(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder) {
+        super.clearView(recyclerView, viewHolder);
+
+        if (viewHolder instanceof ListBaseViewHolder) {
+            ListBaseViewHolder vh = (ListBaseViewHolder) viewHolder;
+            if (vh.getComponent() != null) {
+                if (dragFrom != -1 && dragTo != -1) {
+                    mDragHelper.onDragEnd(vh.getComponent(), dragFrom, dragTo);
+                }
+            }
+
+        }
+
+        dragFrom = dragTo = -1;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/EventTrigger.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/EventTrigger.java
new file mode 100644
index 0000000..9cf2c37
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/EventTrigger.java
@@ -0,0 +1,25 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import java.util.Map;
+
+interface EventTrigger {
+    void triggerEvent(String type, Map<String, Object> args);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/GapItemDecoration.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/GapItemDecoration.java
new file mode 100644
index 0000000..0f58a25
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/GapItemDecoration.java
@@ -0,0 +1,81 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.graphics.Rect;
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+import android.view.View;
+
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.utils.WXViewUtils;
+
+/**
+ * Created by furture on 2018/2/12.
+ * recyclerview's height is layout width + column gap,
+ * so the the offset should include, leftGap and rightGap is via this
+ */
+public class GapItemDecoration extends RecyclerView.ItemDecoration {
+
+    private WXListComponent listComponent;
+
+    public GapItemDecoration(WXListComponent listComponent) {
+        this.listComponent = listComponent;
+    }
+
+    @Override
+    public void getItemOffsets(Rect outRect, View view, RecyclerView parent, RecyclerView.State state) {
+        final Float[] spanOffsets = listComponent.getSpanOffsets();
+        if (spanOffsets == null) {
+            return;
+        }
+        int position = parent.getChildAdapterPosition(view);
+        if(position < 0) {
+            return;
+        }
+        if(view.getLayoutParams() instanceof StaggeredGridLayoutManager.LayoutParams){
+            StaggeredGridLayoutManager.LayoutParams params = (StaggeredGridLayoutManager.LayoutParams) view.getLayoutParams();
+            if(params.isFullSpan()){
+                return;
+            }
+            WXComponent component = listComponent.getChild(position);
+            if(component instanceof WXCell){
+                WXCell cell = (WXCell) component;
+                if(cell.isFixed() || cell.isSticky()) {
+                    return;
+                }
+
+                if (params.getSpanIndex() >= spanOffsets.length) {
+                    return;
+                }
+
+                int index = listComponent.isLayoutRTL() ? spanOffsets.length - params.getSpanIndex() - 1 : params.getSpanIndex();
+                float spanOffset = listComponent.getSpanOffsets()[index];
+                int   spanOffsetPx =  Math.round(WXViewUtils.getRealPxByWidth(spanOffset, listComponent.getViewPortWidth()));
+                if (listComponent.isLayoutRTL()) {
+                    outRect.left = -spanOffsetPx;
+                    outRect.right = spanOffsetPx;
+                } else {
+                    outRect.left = spanOffsetPx;
+                    outRect.right = -spanOffsetPx;
+                }
+            }
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/HorizontalListComponent.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/HorizontalListComponent.java
new file mode 100644
index 0000000..1473b8d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/HorizontalListComponent.java
@@ -0,0 +1,41 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXVContainer;
+
+/**
+ * Created by sospartan on 6/2/16.
+ */
+@Component(lazyload = false)
+
+public class HorizontalListComponent extends WXListComponent {
+  public HorizontalListComponent(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
+    super(instance, parent, lazy, basicComponentData);
+  }
+
+  @Override
+  public int getOrientation() {
+    return Constants.Orientation.HORIZONTAL;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/ListComponentView.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/ListComponentView.java
new file mode 100644
index 0000000..0b6fdd7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/ListComponentView.java
@@ -0,0 +1,35 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+import org.apache.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
+
+/**
+ * Created by sospartan on 13/12/2016.
+ */
+
+public interface ListComponentView {
+  WXRecyclerView getInnerView();
+  void setRecyclerViewBaseAdapter(RecyclerViewBaseAdapter adapter);
+  void notifyStickyShow(WXCell component);
+  void notifyStickyRemove(WXCell component);
+  void updateStickyView(int currentStickyPos);
+  RecyclerViewBaseAdapter getRecyclerViewBaseAdapter();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/RecyclerTransform.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/RecyclerTransform.java
new file mode 100644
index 0000000..6117741
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/RecyclerTransform.java
@@ -0,0 +1,90 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.support.v7.widget.RecyclerView;
+
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.view.listview.adapter.TransformItemDecoration;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * recycler item decoration transform
+ * Created by jianbai.gbj on 2017/9/14.
+ */
+public class RecyclerTransform {
+
+    public static final String TRANSFORM = Constants.Name.TRANSFORM;
+    private static final Pattern transformPattern = Pattern.compile("([a-z]+)\\(([0-9\\.]+),?([0-9\\.]+)?\\)");
+    private static final String TAG = "RecyclerTransform";
+
+    /**
+     * These transform functions are supported:
+     * - `scale(x,y)`: scale item, x and y should be a positive float number.
+     * - `translate(x,y)`: translate item, `x` and `y` shoule be integer numbers.
+     * - `opacity(n)`: change the transparency of item, `n` must in `[0,1.0]`.
+     * - `rotate(n)`: rotate item, n is integer number.
+     *
+     * @param raw
+     * @return
+     */
+    public static RecyclerView.ItemDecoration parseTransforms(int orientation, String raw) {
+        if (raw == null) {
+            return null;
+        }
+        float scaleX = 0f, scaleY = 0f;
+        int translateX = 0, translateY = 0;
+        float opacity = 0f;
+        int rotate = 0;
+        //public TransformItemDecoration(boolean isVertical,float alpha,int translateX,int translateY,int rotation,float scale)
+        Matcher matcher = transformPattern.matcher(raw);
+        while (matcher.find()) {
+            String match = matcher.group();
+            String name = matcher.group(1);
+            try {
+                switch (name) {
+                    case "scale":
+                        scaleX = Float.parseFloat(matcher.group(2));
+                        scaleY = Float.parseFloat(matcher.group(3));
+                        break;
+                    case "translate":
+                        translateX = Integer.parseInt(matcher.group(2));
+                        translateY = Integer.parseInt(matcher.group(3));
+                        break;
+                    case "opacity":
+                        opacity = Float.parseFloat(matcher.group(2));
+                        break;
+                    case "rotate":
+                        rotate = Integer.parseInt(matcher.group(2));
+                        break;
+                    default:
+                        WXLogUtils.e(TAG, "Invaild transform expression:" + match);
+                        break;
+                }
+            } catch (NumberFormatException e) {
+                WXLogUtils.e("", e);
+                WXLogUtils.e(TAG, "Invaild transform expression:" + match);
+            }
+        }
+        return new TransformItemDecoration(orientation == Constants.Orientation.VERTICAL, opacity, translateX, translateY, rotate, scaleX, scaleY);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/SimpleListComponent.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/SimpleListComponent.java
new file mode 100644
index 0000000..4f3b3d8
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/SimpleListComponent.java
@@ -0,0 +1,46 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.content.Context;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+
+/**
+ * A simple list component based on regular recyclerview, do not support refreshing and loading.
+ * Created by sospartan on 13/12/2016.
+ *
+ */
+public class SimpleListComponent extends BasicListComponent<SimpleRecyclerView>{
+
+  public SimpleListComponent(
+      WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  @Override
+  protected SimpleRecyclerView generateListView(Context context, int orientation) {
+    SimpleRecyclerView view = new SimpleRecyclerView(context);
+    view.initView(context, WXRecyclerView.TYPE_LINEAR_LAYOUT, orientation);
+    return view;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/SimpleRecyclerView.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/SimpleRecyclerView.java
new file mode 100644
index 0000000..f6ea5cc
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/SimpleRecyclerView.java
@@ -0,0 +1,72 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.content.Context;
+
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+import org.apache.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
+
+/**
+ * Simple list is used for specific occasion, NOT Support sticky,load more,bounce etc.
+ * Created by sospartan on 13/12/2016.
+ */
+
+class SimpleRecyclerView extends WXRecyclerView implements ListComponentView{
+  private RecyclerViewBaseAdapter mAdapter = null;
+
+  public SimpleRecyclerView(Context context) {
+    super(context);
+  }
+
+  @Override
+  public WXRecyclerView getInnerView() {
+    return this;
+  }
+
+  @Override
+  public void setRecyclerViewBaseAdapter(RecyclerViewBaseAdapter adapter) {
+    setAdapter(adapter);
+    this.mAdapter = adapter;
+  }
+
+  /**
+   * @param component
+   */
+  public void notifyStickyShow(WXCell component) {
+    //Simple list is used for specific occasion, NOT Support sticky,load more,bounce etc.
+  }
+
+  /**
+   * @param component
+   */
+  public void notifyStickyRemove(WXCell component) {
+    //Simple list is used for specific occasion, NOT Support sticky,load more,bounce etc.
+  }
+
+  @Override
+  public void updateStickyView(int currentStickyPos) {
+    //Simple list is used for specific occasion, NOT Support sticky,load more,bounce etc.
+  }
+
+  @Override
+  public RecyclerViewBaseAdapter getRecyclerViewBaseAdapter() {
+    return mAdapter;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/StickyHeaderHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/StickyHeaderHelper.java
new file mode 100644
index 0000000..8b0efd9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/StickyHeaderHelper.java
@@ -0,0 +1,206 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.view.View;
+import android.view.ViewGroup;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Created by sospartan on 17/03/2017.
+ */
+
+public class StickyHeaderHelper {
+  private final ViewGroup mParent;
+  private Map<String,View> mHeaderViews = new HashMap<>(); // map for <ref,view>
+  private Map<String,WXCell> mHeaderComps = new HashMap<>(); // map for <ref,comp>
+  private String mCurrentStickyRef = null;
+
+  public StickyHeaderHelper(ViewGroup parent){
+    this.mParent = parent;
+  }
+
+  /**
+   * @param component
+   */
+  public void notifyStickyShow(WXCell component) {
+    if (component == null)
+      return;
+    mHeaderComps.put(component.getRef(),component);
+    if(mCurrentStickyRef != null){
+      WXCell cell = mHeaderComps.get(mCurrentStickyRef);
+      if(cell ==null || component.getScrollPositon() > cell.getScrollPositon()){
+        mCurrentStickyRef = component.getRef();
+      }
+    }else{
+      mCurrentStickyRef = component.getRef();
+    }
+
+    {
+      if(mCurrentStickyRef==null){
+        WXLogUtils.e("Current Sticky ref is null.");
+        return;
+      }
+
+      WXCell headComponent = mHeaderComps.get(mCurrentStickyRef);
+      final View headerView = headComponent.getRealView();
+      if (headerView == null) {
+        WXLogUtils.e("Sticky header's real view is null.");
+        return;
+      }
+      View header = mHeaderViews.get(headComponent.getRef());
+      if( header != null){
+        //already there
+        header.bringToFront();
+      }else {
+        mHeaderViews.put(headComponent.getRef(), headerView);
+        //record translation, it should not change after transformation
+        final float translationX = headerView.getTranslationX();
+        final float translationY = headerView.getTranslationY();
+        headComponent.removeSticky();
+
+        ViewGroup existedParent;
+        if ((existedParent = (ViewGroup) headerView.getParent()) != null) {
+          existedParent.removeView(headerView);
+        }
+        headerView.setTag(headComponent.getRef());
+        ViewGroup.MarginLayoutParams mlp =
+                new ViewGroup.MarginLayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT,
+                        ViewGroup.LayoutParams.WRAP_CONTENT);
+        mParent.addView(headerView, mlp);
+        headerView.setTag(this);
+        if(headComponent.getStickyOffset() > 0) {
+          ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) headerView.getLayoutParams();
+          if(headComponent.getStickyOffset() != params.topMargin) {
+            params.topMargin = headComponent.getStickyOffset();
+          }
+        }
+        //recover translation, sometimes it will be changed on fling
+        headerView.setTranslationX(translationX);
+        headerView.setTranslationY(translationY);
+      }
+      changeFrontStickyVisible();
+      if (headComponent.getEvents().contains("sticky")) {
+        headComponent.fireEvent("sticky");
+      }
+    }
+  }
+
+
+  public void notifyStickyRemove(WXCell compToRemove) {
+    if (compToRemove == null)
+      return;
+    final WXCell component = mHeaderComps.containsValue(compToRemove) ? mHeaderComps.remove(compToRemove.getRef()) : compToRemove;
+    final View headerView = mHeaderViews.remove(compToRemove.getRef());
+
+    if(component == null || headerView == null){
+      if(WXEnvironment.isApkDebugable()) {
+      }
+      return;
+    }
+    if(mCurrentStickyRef != null && mCurrentStickyRef.equals(compToRemove.getRef())){
+      mCurrentStickyRef = null;
+    }
+    mParent.post(WXThread.secure(new Runnable() {
+      @Override
+      public void run() {
+        mParent.removeView(headerView);
+        if(headerView.getVisibility() != View.VISIBLE){
+          headerView.setVisibility(View.VISIBLE);
+        }
+        component.recoverySticky();
+        changeFrontStickyVisible();
+
+      }
+    }));
+    if (component.getEvents().contains("unsticky")) {
+      component.fireEvent("unsticky");
+    }
+  }
+
+
+  public void updateStickyView(int currentStickyPos) {
+    Iterator<Map.Entry<String, WXCell>> iterator = mHeaderComps.entrySet().iterator();
+    List<WXCell> toRemove = new ArrayList<>();
+    while(iterator.hasNext()){
+      Map.Entry<String, WXCell> next = iterator.next();
+      WXCell cell = next.getValue();
+      int pos = cell.getScrollPositon();
+      if(pos > currentStickyPos){
+        toRemove.add(cell);
+      }else if(pos == currentStickyPos){
+        mCurrentStickyRef = cell.getRef();
+        View view = mHeaderViews.get(cell.getRef());
+        if(view != null){
+          view.bringToFront();
+          changeFrontStickyVisible();
+        }
+      }
+    }
+    for(WXCell cell:toRemove){
+      notifyStickyRemove(cell);
+    }
+  }
+
+  public void  clearStickyHeaders(){
+    if(mHeaderViews.size() <= 0){
+      return;
+    }
+    Iterator<Map.Entry<String, WXCell>> iterator = mHeaderComps.entrySet().iterator();
+
+    while (iterator.hasNext()) {
+      Map.Entry<String, WXCell> next = iterator.next();
+      WXCell value = next.getValue();
+      iterator.remove();
+      notifyStickyRemove(value);
+    }
+  }
+
+
+  private void changeFrontStickyVisible(){
+    if(mHeaderViews.size() <= 0){
+      return;
+    }
+    boolean  fontVisible = false;
+    for(int i=mParent.getChildCount()-1; i>=0; i--){
+      View view = mParent.getChildAt(i);
+      if(fontVisible && view.getTag() instanceof  StickyHeaderHelper){
+        if(view.getVisibility() != View.GONE){
+          view.setVisibility(View.GONE);
+        }
+      }else{
+        if(view.getTag() instanceof  StickyHeaderHelper){
+          fontVisible = true;
+          if(view != null && view.getVisibility() != View.VISIBLE){
+            view.setVisibility(View.VISIBLE);
+          }
+        }
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXCell.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXCell.java
new file mode 100644
index 0000000..4efee98
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXCell.java
@@ -0,0 +1,278 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.content.Context;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.RestrictTo;
+import android.text.TextUtils;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.FrameLayout;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXHeader;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.flat.WidgetContainer;
+import org.apache.weex.ui.view.WXFrameLayout;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import org.apache.weex.common.Constants.Name;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.LinkedList;
+
+/**
+ * Root component for components in {@link WXListComponent}
+ */
+@Component(lazyload = false)
+
+public class WXCell extends WidgetContainer<WXFrameLayout> {
+
+    private int mLastLocationY = 0;
+    private ViewGroup mRealView;
+    private View mTempStickyView;
+    private View mHeadView;
+
+    /** used in list sticky detect **/
+    private int mScrollPosition = -1;
+    private boolean mFlatUIEnabled = false;
+
+
+    private Object  renderData;
+
+    private boolean isSourceUsed = false;
+
+    private boolean isAppendTreeDone;
+
+    private CellAppendTreeListener cellAppendTreeListener;
+
+    public static class Creator implements ComponentCreator {
+        public WXComponent createInstance(WXSDKInstance instance,
+                                          WXVContainer parent,
+                                          BasicComponentData basicComponentData)
+                throws IllegalAccessException, InvocationTargetException, InstantiationException {
+            return new WXCell(instance, parent, true, basicComponentData);
+        }
+    }
+
+    @Deprecated
+    public WXCell(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+        super(instance, parent, basicComponentData);
+    }
+
+    public WXCell(WXSDKInstance instance, WXVContainer parent, boolean isLazy, BasicComponentData basicComponentData) {
+        super(instance, parent, basicComponentData);
+        lazy(true);
+        if(Build.VERSION.SDK_INT< Build.VERSION_CODES.LOLLIPOP) {
+            try {
+                //TODO a WTF is necessary if anyone try to change the flat flag during update attrs.
+                WXAttr attr = getAttrs();
+                if (attr.containsKey(Constants.Name.FLAT)) {
+                    mFlatUIEnabled = WXUtils.getBoolean(attr.get(Constants.Name.FLAT), false);
+                }
+            } catch (NullPointerException e) {
+                WXLogUtils.e("Cell", WXLogUtils.getStackTrace(e));
+            }
+        }
+        if (!canRecycled()){
+            instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_CELL_DATA_UN_RECYCLE_NUM,1);
+        }
+        if (TextUtils.isEmpty(getAttrs().getScope())){
+            instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_STATS_CELL_UN_RE_USE_NUM,1);
+        }
+    }
+
+    @Override
+    public boolean isLazy() {
+        return super.isLazy() && !isFixed();
+    }
+
+    @Override
+    @RestrictTo(RestrictTo.Scope.LIBRARY)
+    public boolean isFlatUIEnabled() {
+        return mFlatUIEnabled;
+    }
+
+    /**
+     * If Cell is Sticky, need wraped FrameLayout
+     */
+    @Override
+    protected WXFrameLayout initComponentHostView(@NonNull Context context) {
+        if (isSticky() || this instanceof WXHeader) {
+            WXFrameLayout view = new WXFrameLayout(context);
+            mRealView = new WXFrameLayout(context);
+            view.addView(mRealView);
+            //TODO Maybe there is a better solution for hardware-acceleration view's display list.
+            if (isFlatUIEnabled()) {
+                view.setLayerType(View.LAYER_TYPE_HARDWARE, null);
+            }
+            return view;
+        } else {
+            WXFrameLayout view = new WXFrameLayout(context);
+            mRealView = view;
+            if (isFlatUIEnabled()) {
+                view.setLayerType(View.LAYER_TYPE_HARDWARE, null);
+            }
+            return view;
+        }
+    }
+
+    public int getLocationFromStart(){
+        return mLastLocationY;
+    }
+
+    public void setLocationFromStart(int l){
+        mLastLocationY = l;
+    }
+
+    void setScrollPositon(int pos){
+        mScrollPosition = pos;
+    }
+
+    public int getScrollPositon() {
+        return mScrollPosition;
+    }
+
+    @Override
+    public ViewGroup getRealView() {
+        return mRealView;
+    }
+
+    public void removeSticky() {
+        if(getHostView().getChildCount() > 0) {
+            mHeadView = getHostView().getChildAt(0);
+            int[] location = new int[2];
+            int[] parentLocation = new int[2];
+            getHostView().getLocationOnScreen(location);
+            getParentScroller().getView().getLocationOnScreen(parentLocation);
+            int headerViewOffsetX = location[0] - parentLocation[0];
+            int headerViewOffsetY = getParent().getHostView().getTop();
+            getHostView().removeView(mHeadView);
+            mRealView = (ViewGroup) mHeadView;
+            mTempStickyView = new FrameLayout(getContext());
+            FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams((int) getLayoutWidth(),
+                    (int) getLayoutHeight());
+            getHostView().addView(mTempStickyView, lp);
+            mHeadView.setTranslationX(headerViewOffsetX);
+            mHeadView.setTranslationY(headerViewOffsetY);
+        }
+    }
+
+    public void recoverySticky() {
+        if(mHeadView != null){
+            if(mHeadView.getLayoutParams() != null){
+                ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) mHeadView.getLayoutParams();
+                if(params.topMargin > 0){
+                    params.topMargin = 0;
+                }
+            }
+            if(mHeadView.getVisibility() != View.VISIBLE){
+                mHeadView.setVisibility(View.VISIBLE);
+            }
+            if(mHeadView.getParent() != null){
+                ((ViewGroup)mHeadView.getParent()).removeView(mHeadView);
+            }
+            getHostView().removeView(mTempStickyView);
+            getHostView().addView(mHeadView);
+            mHeadView.setTranslationX(0);
+            mHeadView.setTranslationY(0);
+        }
+    }
+
+    @Override
+    protected void mountFlatGUI() {
+        if(getHostView()!=null) {
+            if(widgets == null){
+                widgets = new LinkedList<>();
+            }
+            getHostView().mountFlatGUI(widgets);
+        }
+    }
+
+    @Override
+    public void unmountFlatGUI() {
+        if (getHostView() != null) {
+            getHostView().unmountFlatGUI();
+        }
+    }
+
+    @Override
+    public boolean intendToBeFlatContainer() {
+        return getInstance().getFlatUIContext().isFlatUIEnabled(this) && WXCell.class.equals(getClass()) && !isSticky();
+    }
+
+    public int getStickyOffset(){
+        if(getAttrs().get(Name.STICKY_OFFSET) == null){
+            return 0;
+        }
+        float  offset = WXUtils.getFloat(getAttrs().get(Name.STICKY_OFFSET));
+        return (int)(WXViewUtils.getRealPxByWidth(offset, getViewPortWidth()));
+    }
+
+    public Object getRenderData() {
+        return renderData;
+    }
+
+    public void setRenderData(Object renderData) {
+        this.renderData = renderData;
+    }
+
+    public boolean isSourceUsed() {
+        return isSourceUsed;
+    }
+
+    public void setSourceUsed(boolean sourceUsed) {
+        isSourceUsed = sourceUsed;
+    }
+
+
+    public boolean isAppendTreeDone(){
+        return isAppendTreeDone;
+    }
+
+    @Override
+    public void appendTreeCreateFinish() {
+        super.appendTreeCreateFinish();
+        isAppendTreeDone = true;
+        if(cellAppendTreeListener != null){
+            cellAppendTreeListener.onAppendTreeDone();
+        }
+    }
+
+    public void setCellAppendTreeListener(CellAppendTreeListener cellAppendTreeListener) {
+        this.cellAppendTreeListener = cellAppendTreeListener;
+        if(isAppendTreeDone){
+            cellAppendTreeListener.onAppendTreeDone();
+        }
+    }
+
+    public interface CellAppendTreeListener{
+        public void onAppendTreeDone();
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXListComponent.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXListComponent.java
new file mode 100644
index 0000000..542d7ad
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXListComponent.java
@@ -0,0 +1,339 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.content.Context;
+import android.support.v4.util.ArrayMap;
+import android.support.v7.widget.PagerSnapHelper;
+import android.text.TextUtils;
+import com.alibaba.fastjson.JSON;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXBaseRefresh;
+import org.apache.weex.ui.component.WXBasicComponentType;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXComponentProp;
+import org.apache.weex.ui.component.WXLoading;
+import org.apache.weex.ui.component.WXRefresh;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+import org.apache.weex.ui.view.listview.adapter.ListBaseViewHolder;
+import org.apache.weex.ui.view.refresh.wrapper.BounceRecyclerView;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import java.lang.reflect.InvocationTargetException;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+
+/**
+ * Unlike other components, there is immutable bi-directional association between View and
+ * ViewHolder, while only mutable and temporal uni-directional association between view and
+ * components. The association only exist from {@link #onBindViewHolder(ListBaseViewHolder, int)} to
+ * {@link #onViewRecycled(ListBaseViewHolder)}. In other situations, the association may not valid
+ * or not even exist.
+ */
+@Component(lazyload = false)
+
+public class WXListComponent extends BasicListComponent<BounceRecyclerView> {
+  private String TAG = "WXListComponent";
+  //  private WXRecyclerDomObject mDomObject;
+  private float mPaddingLeft;
+  private float mPaddingRight;
+  private String mSpanOffsetsStr;
+  private Float[] mSpanOffsets;
+  private boolean hasSetGapItemDecoration = false;
+
+  public static class Creator implements ComponentCreator {
+    public WXComponent createInstance(WXSDKInstance instance,
+                                      WXVContainer parent,
+                                      BasicComponentData basicComponentData)
+            throws IllegalAccessException, InvocationTargetException, InstantiationException {
+      return new WXListComponent(instance, parent, true, basicComponentData);
+    }
+  }
+
+  @Deprecated
+  public WXListComponent(WXSDKInstance instance, WXVContainer parent, String instanceId, boolean isLazy, BasicComponentData basicComponentData) {
+    this(instance, parent, isLazy, basicComponentData);
+  }
+
+
+  public WXListComponent(WXSDKInstance instance, WXVContainer parent, boolean lazy, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  @Override
+  protected BounceRecyclerView generateListView(Context context, int orientation) {
+    BounceRecyclerView bounceRecyclerView = new BounceRecyclerView(context, mLayoutType, mColumnCount, mColumnGap, orientation);
+    if (bounceRecyclerView.getSwipeLayout() != null) {
+      if (WXUtils.getBoolean(getAttrs().get(Constants.Name.NEST_SCROLLING_ENABLED), false)) {
+        bounceRecyclerView.getSwipeLayout().setNestedScrollingEnabled(true);
+      }
+    }
+
+    /**
+     *  enable pagingEnabled attr
+     */
+    if(WXUtils.getBoolean(getAttrs().get(Constants.Name.PAGE_ENABLED),false)){
+      PagerSnapHelper snapHelper = null;
+      String pageSize = WXUtils.getString(getAttrs().get(Constants.Name.PAGE_SIZE), null);
+      if(TextUtils.isEmpty(pageSize)) {
+        snapHelper = new PagerSnapHelper();
+      } else  {
+        snapHelper = new WXPagerSnapHelper();
+      }
+
+      snapHelper.attachToRecyclerView(bounceRecyclerView.getInnerView());
+    }
+
+    return bounceRecyclerView;
+  }
+
+  @Override
+  public void addChild(WXComponent child, int index) {
+    super.addChild(child, index);
+    if (child == null || index < -1) {
+      return;
+    }
+    setRefreshOrLoading(child);
+    // Synchronize DomObject's attr to Component and Native View
+    if(getHostView() != null && hasColumnPros()) {
+      updateRecyclerAttr();
+      getHostView().getInnerView().initView(getContext(), mLayoutType,mColumnCount,mColumnGap,getOrientation());
+    }
+  }
+
+  private boolean hasColumnPros() {
+    return (getAttrs().containsKey(Constants.Name.COLUMN_WIDTH) && mColumnWidth != WXUtils.parseFloat(getAttrs().get(Constants.Name.COLUMN_WIDTH))) ||
+            (getAttrs().containsKey(Constants.Name.COLUMN_COUNT) &&  mColumnCount != WXUtils.parseInt(getAttrs().get(Constants.Name.COLUMN_COUNT))) ||
+            (getAttrs().containsKey(Constants.Name.COLUMN_GAP) && mColumnGap != WXUtils.parseFloat(getAttrs().get(Constants.Name.COLUMN_GAP)));
+  }
+
+  /**
+   * Setting refresh view and loading view
+   *
+   * @param child the refresh_view or loading_view
+   */
+  private boolean setRefreshOrLoading(final WXComponent child) {
+
+    if (getHostView() == null) {
+      WXLogUtils.e(TAG, "setRefreshOrLoading: HostView == null !!!!!! check list attr has append =tree");
+      return true;
+    }
+    if (child instanceof WXRefresh) {
+      getHostView().setOnRefreshListener((WXRefresh) child);
+      getHostView().postDelayed(WXThread.secure(new Runnable() {
+        @Override
+        public void run() {
+          getHostView().setHeaderView(child);
+        }
+      }), 100);
+      return true;
+    }
+
+    if (child instanceof WXLoading) {
+      getHostView().setOnLoadingListener((WXLoading) child);
+      getHostView().postDelayed(WXThread.secure(new Runnable() {
+        @Override
+        public void run() {
+          getHostView().setFooterView(child);
+        }
+      }), 100);
+      return true;
+    }
+    return false;
+  }
+
+  private void updateRecyclerAttr() {
+    mColumnCount = WXUtils.parseInt(getAttrs().get(Constants.Name.COLUMN_COUNT));
+    if (mColumnCount <= 0 && mLayoutType != WXRecyclerView.TYPE_LINEAR_LAYOUT) {
+      Map<String, String> ext = new ArrayMap<>();
+      ext.put("componentType", getComponentType());
+      ext.put("attribute", getAttrs().toString());
+      ext.put("stackTrace", Arrays.toString(Thread.currentThread().getStackTrace()));
+      WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),
+          WXErrorCode.WX_RENDER_ERR_LIST_INVALID_COLUMN_COUNT, "columnCount",
+          String.format(Locale.ENGLISH,
+              "You are trying to set the list/recycler/vlist/waterfall's column to %d, which is illegal. The column count should be a positive integer",
+              mColumnCount),
+          ext);
+      mColumnCount = Constants.Value.COLUMN_COUNT_NORMAL;
+    }
+    mColumnGap = WXUtils.parseFloat(getAttrs().get(Constants.Name.COLUMN_GAP));
+    mColumnWidth = WXUtils.parseFloat(getAttrs().get(Constants.Name.COLUMN_WIDTH));
+    mPaddingLeft = WXUtils.parseFloat(getAttrs().get(Constants.Name.PADDING_LEFT));
+    mPaddingRight = WXUtils.parseFloat(getAttrs().get(Constants.Name.PADDING_RIGHT));
+    mSpanOffsetsStr = (String)getAttrs().get(Constants.Name.SPAN_OFFSETS);
+
+    try {
+      if (!TextUtils.isEmpty(mSpanOffsetsStr)) {
+        List<Float> list = JSON.parseArray(mSpanOffsetsStr, Float.class);
+        final int size = list.size();
+        if (null == mSpanOffsets || mSpanOffsets.length != size) {
+          mSpanOffsets = new Float[size];
+        }
+        list.toArray(mSpanOffsets);
+      } else {
+        mSpanOffsets = null;
+      }
+    } catch (Throwable e) {
+      WXLogUtils.w("Parser SpanOffsets error ", e);
+    }
+
+    if (!hasSetGapItemDecoration && null != getSpanOffsets() && null != getHostView()
+        && null != getHostView().getInnerView()) {
+      hasSetGapItemDecoration = true;
+      getHostView().getInnerView().addItemDecoration(new GapItemDecoration(this));
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.SPAN_OFFSETS)
+  public void setSpanOffsets(String spanOffsets)  {
+    if (!TextUtils.equals(spanOffsets, mSpanOffsetsStr)) {
+      markComponentUsable();
+      updateRecyclerAttr();
+      WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+      wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.COLUMN_WIDTH)
+  public void setColumnWidth(float columnWidth)  {
+    if(columnWidth != mColumnWidth){
+      markComponentUsable();
+      updateRecyclerAttr();
+      WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+      wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap,getOrientation());
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.COLUMN_COUNT)
+  public void setColumnCount(int columnCount){
+    if(columnCount != mColumnCount) {
+      markComponentUsable();
+      updateRecyclerAttr();
+      WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+      wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap,getOrientation());
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.COLUMN_GAP)
+  public void setColumnGap(float columnGap) throws InterruptedException {
+    if(columnGap != mColumnGap) {
+      markComponentUsable();
+      updateRecyclerAttr();
+      WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+      wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
+    }
+  }
+
+  @WXComponentProp(name = Constants.Name.SCROLLABLE)
+  public void setScrollable(boolean scrollable) {
+    WXRecyclerView inner = getHostView().getInnerView();
+    inner.setScrollable(scrollable);
+  }
+
+  @Override
+  public void updateProperties(Map<String, Object> props) {
+    super.updateProperties(props);
+    if (isRecycler(this)) {
+      if(WXBasicComponentType.WATERFALL.equals(getComponentType())){
+        mLayoutType = WXRecyclerView.TYPE_STAGGERED_GRID_LAYOUT;
+      }else{
+        mLayoutType = getAttrs().getLayoutType();
+      }
+    }
+
+    if(props.containsKey(Constants.Name.PADDING)
+            ||props.containsKey(Constants.Name.PADDING_LEFT)
+            || props.containsKey(Constants.Name.PADDING_RIGHT)){
+      if(mPaddingLeft != WXUtils.parseFloat(props.get(Constants.Name.PADDING_LEFT)) || mPaddingRight != WXUtils.parseFloat(props.get(Constants.Name.PADDING_RIGHT))) {
+        markComponentUsable();
+        updateRecyclerAttr();
+        WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+        wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
+      }
+    }
+  }
+
+  @Override
+  public void createChildViewAt(int index) {
+    int indexToCreate = index;
+    if (indexToCreate < 0) {
+      indexToCreate = childCount() - 1;
+      if (indexToCreate < 0) {
+        return;
+      }
+    }
+    final WXComponent child = getChild(indexToCreate);
+    if (child instanceof WXBaseRefresh) {
+      child.createView();
+      if (child instanceof WXRefresh) {
+        getHostView().setOnRefreshListener((WXRefresh) child);
+        getHostView().postDelayed(new Runnable() {
+          @Override
+          public void run() {
+            getHostView().setHeaderView(child);
+          }
+        }, 100);
+      } else if (child instanceof WXLoading) {
+        getHostView().setOnLoadingListener((WXLoading) child);
+        getHostView().postDelayed(new Runnable() {
+          @Override
+          public void run() {
+            getHostView().setFooterView(child);
+          }
+        }, 100);
+      }
+    } else {
+      super.createChildViewAt(indexToCreate);
+    }
+  }
+
+  public void remove(WXComponent child, boolean destroy) {
+    super.remove(child, destroy);
+    removeFooterOrHeader(child);
+  }
+
+  private void removeFooterOrHeader(WXComponent child) {
+    if (child instanceof WXLoading) {
+      getHostView().removeFooterView(child);
+    } else if (child instanceof WXRefresh) {
+      getHostView().removeHeaderView(child);
+    }
+  }
+
+  private boolean isRecycler(WXComponent component) {
+    return WXBasicComponentType.WATERFALL.equals(component.getComponentType())
+            || WXBasicComponentType.RECYCLE_LIST.equals(component.getComponentType())
+            || WXBasicComponentType.RECYCLER.equals(component.getComponentType());
+  }
+
+  public Float[] getSpanOffsets() {
+    return mSpanOffsets;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXPagerSnapHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXPagerSnapHelper.java
new file mode 100644
index 0000000..7419aaf
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/WXPagerSnapHelper.java
@@ -0,0 +1,75 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v7.widget.OrientationHelper;
+import android.support.v7.widget.PagerSnapHelper;
+import android.support.v7.widget.RecyclerView;
+import android.view.View;
+
+public class WXPagerSnapHelper extends PagerSnapHelper {
+    @Nullable
+    private OrientationHelper mVerticalHelper;
+    @Nullable
+    private OrientationHelper mHorizontalHelper;
+
+    @Nullable
+    @Override
+    public int[] calculateDistanceToFinalSnap(@NonNull RecyclerView.LayoutManager layoutManager, @NonNull View targetView) {
+
+        int[] out = new int[2];
+        if (layoutManager.canScrollHorizontally()) {
+            out[0] = this.distanceToStart(layoutManager, targetView, this.getHorizontalHelper(layoutManager));
+        } else {
+            out[0] = 0;
+        }
+
+        if (layoutManager.canScrollVertically()) {
+            out[1] = this.distanceToStart(layoutManager, targetView, this.getVerticalHelper(layoutManager));
+        } else {
+            out[1] = 0;
+        }
+
+        return out;
+    }
+
+    @NonNull
+    private OrientationHelper getVerticalHelper(@NonNull RecyclerView.LayoutManager layoutManager) {
+        if (this.mVerticalHelper == null) {
+            this.mVerticalHelper = OrientationHelper.createVerticalHelper(layoutManager);
+        }
+
+        return this.mVerticalHelper;
+    }
+
+    @NonNull
+    private OrientationHelper getHorizontalHelper(@NonNull RecyclerView.LayoutManager layoutManager) {
+        if (this.mHorizontalHelper == null) {
+            this.mHorizontalHelper = OrientationHelper.createHorizontalHelper(layoutManager);
+        }
+
+        return this.mHorizontalHelper;
+    }
+
+    private int distanceToStart(@NonNull RecyclerView.LayoutManager layoutManager, @NonNull View targetView, OrientationHelper helper) {
+        return helper.getDecoratedStart(targetView) - helper.getStartAfterPadding();
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/AsyncCellLoadTask.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/AsyncCellLoadTask.java
new file mode 100644
index 0000000..098405d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/AsyncCellLoadTask.java
@@ -0,0 +1,129 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import android.os.AsyncTask;
+import android.os.Looper;
+import android.os.MessageQueue;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.Iterator;
+import java.util.concurrent.ConcurrentLinkedQueue;
+
+/**
+ * Created by furture on 2018/1/25.
+ * async template cell component copy in background and init component when idle
+ */
+class AsyncCellLoadTask extends AsyncTask<Void,Void, Void> {
+
+    private String template;
+    private WXCell source;
+    private WXRecyclerTemplateList templateList;
+
+    public AsyncCellLoadTask(String template, WXCell source, WXRecyclerTemplateList templateList) {
+        this.template = template;
+        this.source = source;
+        this.templateList = templateList;
+    }
+
+    /**
+     * async template cell component copy in background
+     * */
+    @Override
+    protected Void doInBackground(Void... params) {
+        TemplateCache cellCache = templateList.getTemplatesCache().get(template);
+        if(cellCache == null || cellCache.cells == null){
+            return null;
+        }
+        while (cellCache.cells.size() < templateList.getTemplateCacheSize()){
+            long start = System.currentTimeMillis();
+            WXCell component = (WXCell) templateList.copyComponentFromSourceCell(source);
+            if(WXEnvironment.isOpenDebugLog() && WXRecyclerTemplateList.ENABLE_TRACE_LOG){
+                WXLogUtils.d(WXRecyclerTemplateList.TAG, " AsyncCellLoadTask load " + template
+                        + "  " +  component.hashCode()
+                + " used " + (System.currentTimeMillis() - start));
+            }
+            if(component == null){
+                return null;
+            }
+            if(isDestory()){
+                return null;
+            }
+            cellCache.cells.add(component);
+        }
+        return null;
+    }
+
+    /**
+     * init component view when main thread idle
+     * */
+    @Override
+    protected void onPostExecute(Void aVoid) {
+        if(isDestory()){
+            return;
+        }
+        final TemplateCache cellCache = templateList.getTemplatesCache().get(template);
+        if(cellCache == null){
+            return;
+        }
+        if(cellCache.cells == null
+                || cellCache.cells.size() == 0){
+            cellCache.isLoadIng = false;
+            return;
+        }
+        Looper.myQueue().addIdleHandler(new MessageQueue.IdleHandler() {
+            @Override
+            public boolean queueIdle() {
+                if(isDestory()){
+                    return false;
+                }
+                ConcurrentLinkedQueue<WXCell> queue =  cellCache.cells;
+                Iterator<WXCell> iterator =  queue.iterator();
+                while (iterator.hasNext()){
+                    WXCell component =  iterator.next();
+                    if(component.isLazy()){
+                        templateList.doCreateCellViewBindData(component, template, true);
+                        return iterator.hasNext();
+                    }
+                }
+                return false;
+            }
+        });
+        cellCache.isLoadIng = false;
+    }
+
+    private boolean isDestory(){
+        if(source.getInstance() == null
+                || source.getInstance().isDestroy()){
+            return true;
+        }
+        return templateList.isDestoryed();
+    }
+
+    /**
+     * start cell load task on THREAD_POOL_EXECUTOR
+     * */
+    public void startTask(){
+        executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR);
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellDataManager.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellDataManager.java
new file mode 100644
index 0000000..1abfd21
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellDataManager.java
@@ -0,0 +1,271 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+
+import com.alibaba.fastjson.JSONArray;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Created by furture on 2018/1/23.
+ * template data manager, manage data and render state
+ */
+public class CellDataManager {
+
+    private static final String VIRTUAL_COMPONENT_SEPRATOR = "@";
+
+    public static final String SUB_COMPONENT_TEMPLATE_ID = "@templateId";
+
+    public static final String VIRTUAL_COMPONENT_ID = "@virtualComponentId";
+
+    /**
+     * template list data, update should vis data manager interface, this field is read only
+     * */
+    JSONArray listData;
+
+    /**
+     * current template list
+     * */
+    public final WXRecyclerTemplateList templateList;
+
+    /**
+     * data render state for position, itemId、dirty、and other info
+     * */
+    private Map<Integer, CellRenderState> renderStates = new ArrayMap<>();
+
+
+    /**
+     * list virtual component data, rendet state
+     * key virtual component id, value is cell render state.
+     * */
+    private Map<String, CellRenderState> virtualComponentRenderStates;
+
+
+
+    /**
+     * template list data manager
+     * */
+    public CellDataManager(WXRecyclerTemplateList templateList) {
+        this.templateList = templateList;
+    }
+
+    /**
+     * get current render state for current position, never return null.
+     * */
+    public CellRenderState getRenderState(int position){
+        CellRenderState renderState = renderStates.get(position);
+        if(renderState == null){
+            renderState = new CellRenderState();
+            renderState.position = position;
+            renderStates.put(position, renderState);
+        }
+        if(position != renderState.position) {
+            renderState.position = position;
+            renderState.hasPositionChange = true;
+        }
+        return renderState;
+    }
+
+    /**
+     * @param  virutalComponentId virutalComponentId
+     * @param  data   update    virutalComponent's data
+     * update virtual component data
+     * */
+    public void updateVirtualComponentData(String virutalComponentId, Object data){
+        if(virtualComponentRenderStates != null){
+            CellRenderState cellRenderState = virtualComponentRenderStates.get(virutalComponentId);
+            if(cellRenderState != null){
+                cellRenderState.getVirtualComponentDatas().put(virutalComponentId, data);
+                cellRenderState.hasVirtualCompoentUpdate = true;
+            }else{
+                if(WXEnvironment.isApkDebugable()) {
+                    throw new IllegalArgumentException("virtualComponentDatas illegal state empty render state" + virutalComponentId);
+                }
+            }
+        }else{
+            if(WXEnvironment.isApkDebugable()){
+                throw  new IllegalArgumentException("virtualComponentDatas illegal state " + virutalComponentId);
+            }
+        }
+    }
+
+    /**
+     * @param  position  current position virtual component
+     * @param  virutalComponentId virutalComponentId
+     * @param  data   update    virutalComponent's data
+     * create virtual component data
+     * */
+    public void createVirtualComponentData(int position, String virutalComponentId, Object data){
+        if(virtualComponentRenderStates == null){
+            virtualComponentRenderStates = new HashMap<>(8);
+        }
+        CellRenderState renderState = renderStates.get(position);
+        renderState.getVirtualComponentDatas().put(virutalComponentId, data);
+        virtualComponentRenderStates.put(virutalComponentId, renderState);
+
+    }
+
+
+
+
+    /**
+     * @param  listData setList data
+     * clear render state for current cell, and virtual component data
+     * */
+    public void setListData(JSONArray listData) {
+        if(this.listData != listData) {
+            if(this.listData != null){
+                if(WXUtils.getBoolean(templateList.getAttrs().get("exitDetach"), true)){
+                    for(int i=0; i<this.listData.size(); i++){
+                        cleanRenderState(renderStates.remove(i));
+                    }
+                }
+            }
+            this.listData = listData;
+            renderStates.clear();
+            if (virtualComponentRenderStates != null) {
+                virtualComponentRenderStates.clear();
+            }
+        }
+    }
+
+    /**
+     * @param index insert index
+     * @param  data  data object
+     * insert data at current index
+     * */
+    public boolean insertData(int index, Object data){
+        listData.add(index, data);
+        boolean renderStateChange = false;
+        for(int i=listData.size(); i>= index; i--){
+            CellRenderState state = renderStates.remove(i);
+            if(state != null){
+                renderStates.put(i + 1, state);
+                renderStateChange = true;
+            }
+        }
+        return renderStateChange;
+    }
+
+    /**
+     *
+     * @param index insert index
+     * @param  data  data object
+     * insert data at current index
+     * */
+    public boolean insertRange(int index, JSONArray data){
+        listData.addAll(index, data);
+        boolean renderStateChange = false;
+        for(int i = listData.size()-1; i >= index; i--){
+            CellRenderState state = renderStates.remove(i);
+            if(state != null){
+                renderStates.put(i + 1, state);
+                renderStateChange = true;
+            }
+        }
+        return renderStateChange;
+    }
+
+    /**
+     * @param  data  data object
+     * @param index insert index
+     * update data, reset new render state,
+     * return true if only data changed, false if viewType changed
+     * */
+    public boolean  updateData(Object data, int index){
+        boolean onlyDataChange = TextUtils.equals(templateList.getTemplateKey(index), templateList.getTemplateKey(data));
+        listData.set(index, data);
+        if(!onlyDataChange){
+            //structure changed, reset render state
+            cleanRenderState(renderStates.remove(index));
+        }else{
+            CellRenderState renderState = renderStates.get(index);
+            if(renderState != null){
+                renderState.hasDataUpdate = true;
+            }
+        }
+        return onlyDataChange;
+    }
+
+    /**
+     * @param index
+     * remove data, and its render state  and  virtual's data
+     * */
+    public void  removeData(Integer index){
+        listData.remove((int)index); //remove by index
+        cleanRenderState(renderStates.remove(index));
+        int count = listData.size() + 1;
+        for(int i=index + 1; i < count; i++){
+            CellRenderState state = renderStates.remove(i);
+            if(state != null){
+                renderStates.put(i-1, state);
+            }
+        }
+    }
+
+    /**
+     *  clean render state, if has virtual component, call virtual component detach lifecycle
+     * */
+    private void  cleanRenderState(CellRenderState renderState){
+        if(renderState == null){
+            return;
+        }
+        if(renderState.hasVirtualComponents()){
+            Collection<String> virtualComponentIds =  renderState.getVirtualComponentIds().values();
+            for(String virtualComponentId : virtualComponentIds){
+                if(virtualComponentRenderStates != null){
+                    virtualComponentRenderStates.remove(virtualComponentId);
+                }
+                WXBridgeManager.getInstance().asyncCallJSEventVoidResult(WXBridgeManager.METHD_COMPONENT_HOOK_SYNC,
+                        templateList.getInstanceId(),
+                        null,
+                        virtualComponentId, VirtualComponentLifecycle.LIFECYCLE, VirtualComponentLifecycle.DETACH, null);
+
+            }
+        }
+    }
+
+
+    /**
+     * create virtualComponentId
+     * */
+    public static String createVirtualComponentId(String listRef, String viewTreeKey, long itemId){
+        return  listRef + VIRTUAL_COMPONENT_SEPRATOR  + viewTreeKey + VIRTUAL_COMPONENT_SEPRATOR + itemId;
+    }
+
+    /**
+     * get list ref from virtualComponentId
+     * */
+    public static String getListRef(String virtualComponentId){
+        if(virtualComponentId == null){
+            return null;
+        }
+        return virtualComponentId.split(VIRTUAL_COMPONENT_SEPRATOR)[0];
+    }
+    
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellRenderContext.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellRenderContext.java
new file mode 100644
index 0000000..9e1c1ca
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellRenderContext.java
@@ -0,0 +1,79 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import org.apache.weex.el.parse.ArrayStack;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Created by furture on 2018/1/23.
+ * render context for cell template
+ */
+public class CellRenderContext {
+    /**
+     * code execute stack
+     * */
+    public ArrayStack stack = new ArrayStack();
+    /**
+     * init context data
+     * */
+    public Map map = new HashMap(8);
+
+
+    /**
+     * component data context
+     * */
+    public CellRenderState renderState;
+
+    /**
+     * current position
+     * */
+    public int position;
+
+    /**
+     * current list component
+     * */
+    public WXRecyclerTemplateList templateList;
+
+
+    /**
+     * get current render state
+     * */
+    public CellRenderState getRenderState() {
+        if(renderState != null) {
+            renderState =  templateList.getCellDataManager().getRenderState(position);
+        }
+        return renderState;
+    }
+
+
+    public void clear(){
+        if(stack.getList().size() > 0) {
+            stack.getList().clear();
+        }
+        if(map.size() > 0) {
+            map.clear();
+        }
+        renderState  = null;
+        position = 0;
+        templateList = null;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellRenderState.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellRenderState.java
new file mode 100644
index 0000000..1fc0593
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/CellRenderState.java
@@ -0,0 +1,122 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import android.support.v7.widget.RecyclerView;
+
+import org.apache.weex.el.parse.ArrayStack;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Created by furture on 2018/1/24.
+ * render state for one cell, manage it's render state
+ */
+public class CellRenderState {
+
+    /**
+     * dirty for current position, for example virtual component has update
+     * */
+    boolean hasVirtualCompoentUpdate = false;
+
+    /**
+     * has date update
+     * */
+    boolean hasDataUpdate = false;
+
+    /**
+     * position changed
+     * */
+    boolean hasPositionChange = false;
+
+    /**
+     *  may use position, when position changed should be rendered
+     * */
+    int  position;
+
+    /**
+     * unique itemId for current position, generate via key core
+     * */
+    long itemId = RecyclerView.NO_ID;
+
+
+
+    /**
+     * virtualCompoentId for cell, key is viewTreeKey, value is virutalComponentId.
+     * lazy init,
+     * */
+    private Map<String, String> virtualComponentIds;
+    private Map<String, Object> virtualComponentDatas;
+
+
+    /**
+     * mark once statements has rendered
+     * */
+    private Map<String, ArrayStack> onceComponentStates;
+
+
+    public Map<String, String> getVirtualComponentIds() {
+        if(virtualComponentIds == null){
+            virtualComponentIds = new HashMap<>(8);
+        }
+        return virtualComponentIds;
+    }
+
+    /**
+     * return current cell has virtual component
+     * */
+    public boolean hasVirtualComponents(){
+        return virtualComponentIds != null && virtualComponentIds.size() > 0;
+    }
+
+    public Map<String, Object> getVirtualComponentDatas() {
+        if(virtualComponentDatas == null){
+            virtualComponentDatas = new HashMap<>(4);
+        }
+        return virtualComponentDatas;
+    }
+
+    public Map<String, ArrayStack> getOnceComponentStates() {
+        if(onceComponentStates == null){
+            onceComponentStates = new HashMap<>();
+        }
+        return onceComponentStates;
+    }
+
+    public boolean isDirty() {
+        return hasDataUpdate
+                || hasVirtualCompoentUpdate
+                || hasPositionChange;
+    }
+
+    public boolean isHasDataUpdate() {
+        return hasDataUpdate;
+    }
+
+
+
+    public void  resetDirty(){
+        hasDataUpdate = false;
+        hasVirtualCompoentUpdate = false;
+        hasPositionChange = false;
+    }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/PositionRef.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/PositionRef.java
new file mode 100644
index 0000000..3af1e37
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/PositionRef.java
@@ -0,0 +1,71 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import com.alibaba.fastjson.JSONAware;
+
+/**
+ * position render state, when render state change, position changed
+ * Created by furture on 2018/2/2.
+ */
+public class PositionRef extends  Number implements JSONAware {
+
+    private CellRenderState renderState;
+
+    public PositionRef(CellRenderState renderState) {
+        this.renderState = renderState;
+    }
+
+    @Override
+    public int intValue() {
+        return getPosition();
+    }
+
+    @Override
+    public long longValue() {
+        return getPosition();
+    }
+
+    @Override
+    public float floatValue() {
+        return getPosition();
+    }
+
+    @Override
+    public double doubleValue() {
+        return getPosition();
+    }
+
+    private int getPosition(){
+        if(renderState == null){
+            return  -1;
+        }
+        return renderState.position;
+    }
+
+    @Override
+    public String toString() {
+        return String.valueOf(getPosition());
+    }
+
+    @Override
+    public String toJSONString() {
+        return String.valueOf(getPosition());
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/Selector.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/Selector.java
new file mode 100644
index 0000000..4564c96
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/Selector.java
@@ -0,0 +1,119 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import android.text.TextUtils;
+
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.component.list.WXCell;
+
+import java.util.List;
+
+/**
+ * Created by furture on 2018/7/24.
+ */
+
+public class Selector {
+
+    /**
+     * @param  selector  [att=xx]
+     * query elements match selector, current only support attr selector
+     * */
+    public static void queryElementAll(WXComponent component, String selector, List<WXComponent> componentList){
+        if(TextUtils.isEmpty(selector)){
+            return;
+        }
+        selector = selector.replaceAll("\\[|]", "");
+        String[] args = selector.split("=");
+        if(args.length <= 0){
+            return;
+        }
+        String key = args[0];
+        String value = null;
+        if(args.length > 1){
+            value = args[1].trim();
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            for(int i=0; i<container.getChildCount(); i++){
+                queryElementAllByAttrs(container.getChild(i), key, value, componentList);
+            }
+        }
+    }
+
+
+    public static void closest(WXComponent component, String selector,List<WXComponent> componentList){
+        if(TextUtils.isEmpty(selector)){
+            return;
+        }
+        selector = selector.replaceAll("\\[|]", "");
+        String[] args = selector.split("=");
+        if(args.length <= 0){
+            return;
+        }
+        String key = args[0];
+        String value = null;
+        if(args.length > 1){
+            value = args[1].trim();
+        }
+        closestByAttrs(component, key, value, componentList);
+    }
+
+    private static void closestByAttrs(WXComponent component, String key, String value, List<WXComponent> componentList){
+        if(matchAttrs(component, key, value)){
+            componentList.add(component);
+        }
+        if(component instanceof WXCell || component instanceof  WXRecyclerTemplateList){
+            return;
+        }
+        queryElementAllByAttrs(component.getParent(), key, value, componentList);
+    }
+
+
+    private static void queryElementAllByAttrs(WXComponent component, String key, String value, List<WXComponent> componentList){
+        if(matchAttrs(component, key, value)){
+            componentList.add(component);
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            for(int i=0; i<container.getChildCount(); i++){
+                queryElementAllByAttrs(container.getChild(i), key, value, componentList);
+            }
+        }
+    }
+
+
+    private static boolean matchAttrs(WXComponent component, String key, String value){
+        if(component.isWaste()){
+            return false;
+        }
+        if(!component.getAttrs().containsKey(key)){
+            return false;
+        }
+        if(TextUtils.isEmpty(value)){
+            return true;
+        }
+        Object attrValue = component.getAttrs().get(key);
+        if(attrValue == null){
+            return false;
+        }
+        return value.equals(attrValue.toString());
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateCache.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateCache.java
new file mode 100644
index 0000000..1021ea7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateCache.java
@@ -0,0 +1,32 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import org.apache.weex.ui.component.list.WXCell;
+
+import java.util.concurrent.ConcurrentLinkedQueue;
+
+/**
+ * preload cell cache
+ * Created by furture on 2017/9/29.
+ */
+class TemplateCache {
+    ConcurrentLinkedQueue<WXCell> cells = new ConcurrentLinkedQueue<>();
+    boolean isLoadIng = false;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateDom.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateDom.java
new file mode 100644
index 0000000..3ab9d33
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateDom.java
@@ -0,0 +1,227 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import android.support.v4.view.ViewCompat;
+import android.view.View;
+
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Created by furture on 2018/6/27.
+ */
+
+public class TemplateDom {
+
+    public static final String KEY_RESET_ANIMATION = "resetAnimation";
+    public static final String KEY_ATTRS = "attrs";
+    public static final String KEY_TYPE = "type";
+    public static final String KEY_VIRTUAL_DOM_REF = "ref";
+    public static final String VIRTUAL_DOM_IDENTIFY = "[[VirtualElement]]";
+
+
+    public static final String ATTRS_KEY_REF = "ref";
+
+    public static final String ATTACH_CELL_SLOT = "_attach_slot";
+    public static final String DETACH_CELL_SLOT = "_detach_slot";
+
+    public static final char SEPARATOR = '@';
+
+
+    public static String genKeyVirtualDomRef(String listRef, int position, String key){
+        return listRef + SEPARATOR + position + SEPARATOR  +  key;
+    }
+
+    public static WXComponent findVirtualComponentByVRef(String pageId, String virtualRef) {
+        try{
+
+            String[]  segments = virtualRef.split(SEPARATOR + "");
+            String listRef = segments[0]; // list ref
+            WXComponent component = WXSDKManager
+                .getInstance().getWXRenderManager().getWXComponent(pageId, listRef);
+            if(!(component instanceof WXRecyclerTemplateList)){
+                return null;
+            }
+            WXRecyclerTemplateList templateList = (WXRecyclerTemplateList) component;
+            if(templateList.getHostView() == null || templateList.getHostView().getInnerView() == null){
+                return null;
+            }
+            int position = Integer.parseInt(segments[1]); // position
+            WXRecyclerView recyclerView = templateList.getHostView().getInnerView();
+            TemplateViewHolder itemHolder = (TemplateViewHolder) recyclerView.findViewHolderForAdapterPosition(position);
+            if(itemHolder == null){
+                return null;
+            }
+
+            WXCell cell = itemHolder.getTemplate();
+            String viewKey = segments[2]; //viewkey
+            WXComponent target = findComponentByViewTreeKey(cell, viewKey);
+            return  target;
+        }catch (Exception e){
+            return  null;
+        }
+    }
+
+    /**
+     * find all component that contains ref attr
+     * */
+    public static Map<String,Object> findAllComponentRefs(String listRef, int position , WXComponent component){
+        Map<String,Object> refs = new HashMap<>();
+        findAllComponentRefs(listRef, position, component, refs);
+        Map<String,Object> refsMap = new HashMap<>();
+        refsMap.put("refs", refs);
+        refsMap.put("position", position);
+        refsMap.put("listRef", listRef);
+        return refsMap;
+    }
+
+    private static void findAllComponentRefs(String listRef, int position, WXComponent component, Map<String,Object> refs){
+        if(component.isWaste()){
+            return;
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            for(int i=0; i<container.getChildCount(); i++){
+                WXComponent child = container.getChild(i);
+                findAllComponentRefs(listRef, position, child, refs);
+            }
+        }
+        WXAttr attrs = component.getAttrs();
+        if(attrs != null
+                && attrs.get(TemplateDom.ATTRS_KEY_REF) == null){
+            return;
+        }
+        String ref  = attrs.get(TemplateDom.ATTRS_KEY_REF).toString();
+        List<Object> refList = (List<Object>) refs.get(ref);
+        if(refList == null){
+            refList = new ArrayList<>();
+            refs.put(ref, refList);
+        }
+        Map map = toMap(listRef, position, component);
+        refList.add(map);
+    }
+
+
+    public static Map toMap(String listRef, int position, WXComponent component){
+        Map map = new HashMap();
+        map.put(TemplateDom.KEY_ATTRS, component.getAttrs());
+        map.put(TemplateDom.KEY_TYPE, component.getComponentType());
+        map.put(TemplateDom.KEY_VIRTUAL_DOM_REF, TemplateDom.genKeyVirtualDomRef(listRef, position, component.getViewTreeKey()));
+        map.put(VIRTUAL_DOM_IDENTIFY, true);
+        return map;
+    }
+
+
+    public static boolean isVirtualDomRef(String ref){
+        if(ref != null){
+            return  ref.indexOf(SEPARATOR) > 0;
+        }
+        return  false;
+    }
+
+
+    public static void resetAnimaiton(View view){
+        if(view == null){
+            return;
+        }
+        if(ViewCompat.getTranslationX(view) != 0){
+            ViewCompat.setTranslationX(view, 0);
+        }
+
+        if(ViewCompat.getTranslationY(view) != 0){
+            ViewCompat.setTranslationY(view, 0);
+        }
+
+        if(ViewCompat.getTranslationZ(view) != 0){
+            ViewCompat.setTranslationZ(view, 0);
+        }
+
+        if(ViewCompat.getScaleX(view) != 1.0f){
+            ViewCompat.setScaleX(view, 1.0f);
+        }
+
+        if(ViewCompat.getScaleY(view) != 1.0f){
+            ViewCompat.setScaleY(view, 1.0f);
+        }
+
+        if(ViewCompat.getRotationX(view) != 0){
+            ViewCompat.setRotationX(view, 0);
+        }
+
+        if(ViewCompat.getRotationY(view) != 0){
+            ViewCompat.setRotationY(view, 0);
+        }
+
+        if(ViewCompat.getElevation(view) != 0){
+            ViewCompat.setElevation(view, 0);
+        }
+    }
+
+
+    /**
+     * find child list, has same ref
+     * */
+    public static final  WXComponent findComponentByViewTreeKey(WXComponent component, String viewKey){
+        if(component.getViewTreeKey().equals(viewKey)){
+            return component;
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            for(int i=0; i<container.getChildCount(); i++){
+                WXComponent element = container.getChild(i);
+                if(findComponentByViewTreeKey(element, viewKey) != null){
+                    return element;
+                }
+            }
+
+        }
+        return null;
+    }
+
+    /**
+     * find child by ref
+     * */
+    private  static WXComponent findChildByAttrsRef(WXComponent component, String ref){
+        if(component.getAttrs() != null && ref.equals(component.getAttrs().get(TemplateDom.ATTRS_KEY_REF))){
+            return component;
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            for(int i=0; i<container.getChildCount(); i++){
+                WXComponent child = findChildByAttrsRef(container.getChild(i), ref);
+                if(child != null){
+                    return  child;
+                }
+            }
+        }
+        return  null;
+    }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateStickyHelper.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateStickyHelper.java
new file mode 100644
index 0000000..e0630f5
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateStickyHelper.java
@@ -0,0 +1,250 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import android.support.v4.util.ArrayMap;
+import android.support.v7.widget.LinearLayoutManager;
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.FrameLayout;
+
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.view.refresh.wrapper.BounceRecyclerView;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * StickyHelper For Template List
+ * Created by furture on 2017/8/24.
+ */
+public class TemplateStickyHelper {
+    private WXRecyclerTemplateList recyclerTemplateList;
+    private List<Integer> stickyPositions;
+    private ArrayMap<Integer, TemplateViewHolder>   stickyHolderCache;
+    private List<String> mStickyTypes;
+
+
+    public TemplateStickyHelper(WXRecyclerTemplateList recyclerTemplateList) {
+        this.recyclerTemplateList = recyclerTemplateList;
+        this.stickyPositions = new ArrayList<>();
+        this.stickyHolderCache = new ArrayMap();
+        this.mStickyTypes = new ArrayList<>(8);
+    }
+
+    /**
+     * dispatch scroll event, sticky  header
+     * */
+    public void onBeforeScroll(int dx, int dy) {
+        if(stickyPositions == null || stickyPositions.size() == 0){
+           return;
+        }
+        BounceRecyclerView bounceRecyclerView = recyclerTemplateList.getHostView();
+        RecyclerView recyclerView = recyclerTemplateList.getHostView().getInnerView();
+        RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
+        int firstVisiblePosition = -1;
+        int lastVisiblePosition = -1;
+        if (layoutManager instanceof LinearLayoutManager) {
+            firstVisiblePosition = ((LinearLayoutManager) layoutManager).findFirstVisibleItemPosition();
+            lastVisiblePosition  = ((LinearLayoutManager) layoutManager).findLastVisibleItemPosition();
+        }else if (layoutManager instanceof StaggeredGridLayoutManager) {
+            int [] firstVisibleItemPositions = new int[3];//max 3 column
+            firstVisiblePosition = ((StaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(firstVisibleItemPositions)[0];
+            lastVisiblePosition = ((StaggeredGridLayoutManager) layoutManager).findLastVisibleItemPositions(firstVisibleItemPositions)[0];
+        }
+        if(firstVisiblePosition < 0){
+            return;
+        }
+
+        TemplateViewHolder firstVisibleItemHolder = (TemplateViewHolder) recyclerView.findViewHolderForAdapterPosition(firstVisiblePosition);
+        if(firstVisibleItemHolder == null){
+            return;
+        }
+
+        //find match sticky position
+        int matchStickyPosition = -1;
+        for (Integer headerPosition : stickyPositions){
+            if(headerPosition == null){
+                continue;
+            }
+            if(headerPosition <= firstVisiblePosition){
+                matchStickyPosition = Math.max(matchStickyPosition, headerPosition);
+            }else{
+                break;
+            }
+        }
+        if(matchStickyPosition < 0){
+            //remove holder for match position not found
+            View stickyFakeView = bounceRecyclerView.getChildAt(bounceRecyclerView.getChildCount() - 1);
+            if(stickyFakeView.getTag() instanceof TemplateViewHolder){
+                TemplateViewHolder stickyFakeViewHolder = (TemplateViewHolder) stickyFakeView.getTag();
+                bounceRecyclerView.removeView(stickyFakeViewHolder.itemView);
+                stickyFakeViewHolder.itemView.setTranslationY(0);
+                if(stickyFakeViewHolder.getComponent() != null
+                        && stickyFakeViewHolder.getComponent().getEvents().contains(Constants.Event.UNSTICKY)){
+                    stickyFakeViewHolder.getComponent().fireEvent(Constants.Event.UNSTICKY);
+                }
+            }
+
+            /**check has sticky cell not visible */
+            for(int i=0; i<recyclerView.getChildCount(); i++) {
+                View itemView = recyclerView.getChildAt(i);
+                TemplateViewHolder itemHolder = (TemplateViewHolder) recyclerView.getChildViewHolder(itemView);
+                if (itemHolder == null) {
+                    continue;
+                }
+                int adapterPosition = itemHolder.getAdapterPosition();
+                if (!stickyPositions.contains(adapterPosition)) {
+                    continue;
+                }
+                if(itemView.getVisibility() != View.VISIBLE) {
+                    itemView.setVisibility(View.VISIBLE);
+                }
+            }
+            return;
+        }
+
+        //onCreate holder for match position if not exist
+        View stickyFakeView = bounceRecyclerView.getChildAt(bounceRecyclerView.getChildCount() - 1);
+        if(!(stickyFakeView.getTag() instanceof TemplateViewHolder)
+                || ((TemplateViewHolder) stickyFakeView.getTag()).getHolderPosition() != matchStickyPosition){
+
+             //remove previous sticky header
+            if(stickyFakeView.getTag() instanceof TemplateViewHolder &&
+                    ((TemplateViewHolder) stickyFakeView.getTag()).getHolderPosition() != matchStickyPosition){
+                TemplateViewHolder stickyFakeViewHolder = (TemplateViewHolder) stickyFakeView.getTag();
+                bounceRecyclerView.removeView(stickyFakeViewHolder.itemView);
+                stickyFakeViewHolder.itemView.setTranslationY(0);
+                if(stickyFakeViewHolder.getComponent() != null
+                        && stickyFakeViewHolder.getComponent().getEvents().contains(Constants.Event.UNSTICKY)){
+                    stickyFakeViewHolder.getComponent().fireEvent(Constants.Event.UNSTICKY);
+                }
+            }
+
+            //onCreate new sticky
+            int stickyHolderType = recyclerTemplateList.getItemViewType(matchStickyPosition);
+            TemplateViewHolder fakeStickyHolder = stickyHolderCache.get(stickyHolderType);
+            if(fakeStickyHolder == null){
+                fakeStickyHolder = recyclerTemplateList.onCreateViewHolder(recyclerView, stickyHolderType);
+                stickyHolderCache.put(stickyHolderType, fakeStickyHolder);
+            }
+            recyclerTemplateList.onBindViewHolder(fakeStickyHolder, matchStickyPosition);
+            fakeStickyHolder.itemView.setTranslationY(0);
+            fakeStickyHolder.itemView.setTag(fakeStickyHolder);
+            FrameLayout.LayoutParams params = new FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT);
+            fakeStickyHolder.getComponent().clearPreLayout();
+            if(fakeStickyHolder.itemView.getParent() != null){
+                ViewGroup parent = (ViewGroup) fakeStickyHolder.itemView.getParent();
+                parent.removeView(fakeStickyHolder.itemView);
+            }
+            bounceRecyclerView.addView(fakeStickyHolder.itemView, params);
+            fakeStickyHolder.getComponent().setLayout(fakeStickyHolder.getComponent());
+            stickyFakeView = fakeStickyHolder.itemView;
+            if(fakeStickyHolder.getComponent() != null
+                    && fakeStickyHolder.getComponent().getEvents().contains(Constants.Event.STICKY)){
+                fakeStickyHolder.getComponent().fireEvent(Constants.Event.STICKY);
+            }
+        }
+        TemplateViewHolder stickyFakeViewHolder = (TemplateViewHolder) stickyFakeView.getTag();
+        for(int i=0; i<recyclerView.getChildCount(); i++){
+            View itemView = recyclerView.getChildAt(i);
+            TemplateViewHolder itemHolder = (TemplateViewHolder) recyclerView.getChildViewHolder(itemView);
+            if(itemHolder == null){
+                continue;
+            }
+            int adapterPosition = itemHolder.getAdapterPosition();
+            if(!stickyPositions.contains(adapterPosition)){
+                continue;
+            }
+            if(adapterPosition == stickyFakeViewHolder.getHolderPosition()){
+                if(itemView.getVisibility() != View.INVISIBLE) {
+                    itemView.setVisibility(View.INVISIBLE);
+                }
+            }else{
+                if(itemView.getVisibility() != View.VISIBLE) {
+                    itemView.setVisibility(View.VISIBLE);
+                }
+            }
+        }
+
+        if(firstVisibleItemHolder.getComponent().isSticky()){
+            if(firstVisibleItemHolder.itemView.getY() < 0){
+                if(firstVisibleItemHolder.itemView.getVisibility() != View.INVISIBLE) {
+                    firstVisibleItemHolder.itemView.setVisibility(View.INVISIBLE);
+                }
+                if(stickyFakeView.getVisibility() != View.VISIBLE) {
+                    stickyFakeView.setVisibility(View.VISIBLE);
+                }
+                stickyFakeView.bringToFront();
+            }else{
+                if(firstVisibleItemHolder.itemView.getVisibility() != View.VISIBLE) {
+                    firstVisibleItemHolder.itemView.setVisibility(View.VISIBLE);
+                }
+                if(stickyFakeView.getVisibility() != View.GONE) {
+                    stickyFakeView.setVisibility(View.GONE);
+                }
+            }
+        }else{
+            if(stickyFakeView.getVisibility() != View.VISIBLE){
+                stickyFakeView.setVisibility(View.VISIBLE);
+            }
+        }
+
+        //handle sticky is related, find next sticky position on screen
+        int nextVisiblePostion = firstVisiblePosition + 1;
+        if(lastVisiblePosition > 0){
+            for(int i=nextVisiblePostion; i<= lastVisiblePosition; i++){
+                if(stickyPositions.contains(i)){
+                    nextVisiblePostion = i;
+                    break;
+                }
+            }
+        }
+        if(!stickyPositions.contains(nextVisiblePostion)){
+            if(stickyFakeViewHolder.itemView.getTranslationY() < 0){
+                stickyFakeViewHolder.itemView.setTranslationY(0);
+            }
+            return;
+        }
+        TemplateViewHolder nextStickyHolder = (TemplateViewHolder) recyclerView.findViewHolderForAdapterPosition(nextVisiblePostion);
+        if(nextStickyHolder == null
+                || nextStickyHolder.getComponent() == null){
+            return;
+        }
+        int translationY = (int)(nextStickyHolder.itemView.getY() - stickyFakeViewHolder.itemView.getMeasuredHeight());
+        if(translationY <= 0){
+            stickyFakeViewHolder.itemView.setTranslationY(translationY);
+        }else{
+            stickyFakeViewHolder.itemView.setTranslationY(0);
+        }
+    }
+
+    public List<Integer> getStickyPositions() {
+        if(stickyPositions == null){
+            stickyPositions = new ArrayList<>();
+        }
+        return stickyPositions;
+    }
+
+    public List<String> getStickyTypes() {
+        return mStickyTypes;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateViewHolder.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateViewHolder.java
new file mode 100644
index 0000000..0742a80
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/TemplateViewHolder.java
@@ -0,0 +1,79 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import android.os.AsyncTask;
+import android.view.View;
+
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.ui.view.listview.adapter.ListBaseViewHolder;
+
+/**
+ * Created by furture on 2017/8/17.
+ */
+
+public class TemplateViewHolder extends ListBaseViewHolder {
+
+    /**
+     * strong reference, prevent recycled
+     * */
+    private WXCell template;
+
+    private WXRecyclerTemplateList templateList;
+
+    private int holderPosition = -1;
+
+    public AsyncTask<Void, Void, Void> asyncTask;
+
+    public Object  data;
+
+    /**
+     * header position
+     * */
+
+    public TemplateViewHolder(WXRecyclerTemplateList templateList, WXCell component, int viewType) {
+        super(component, viewType);
+        this.template = component;
+        this.templateList = templateList;
+    }
+
+    public TemplateViewHolder(WXRecyclerTemplateList templateList, View view, int viewType) {
+        super(view, viewType);
+        this.templateList = templateList;
+    }
+
+
+
+
+    public int getHolderPosition() {
+        return holderPosition;
+    }
+
+    public void setHolderPosition(int holderPosition) {
+        this.holderPosition = holderPosition;
+    }
+
+    public WXCell getTemplate() {
+        return template;
+    }
+
+    public WXRecyclerTemplateList getTemplateList() {
+        return templateList;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/VirtualComponentLifecycle.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/VirtualComponentLifecycle.java
new file mode 100644
index 0000000..30fbfcf
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/VirtualComponentLifecycle.java
@@ -0,0 +1,45 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+
+/**
+ * Created by furture on 2018/2/1.
+ */
+
+public class VirtualComponentLifecycle {
+
+    /**
+     * lifecycle
+     * */
+    public static final  String LIFECYCLE = "lifecycle";
+
+
+    /**
+     * virtual component lifecycle
+     * */
+    public static final  String CREATE = "create";
+
+    public static final  String ATTACH = "attach";
+
+    public static final  String SYNSTATE = "syncState";
+
+    public static final  String DETACH = "detach";
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/WXRecyclerTemplateList.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/WXRecyclerTemplateList.java
new file mode 100644
index 0000000..4cd5311
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/WXRecyclerTemplateList.java
@@ -0,0 +1,2019 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template;
+
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.graphics.Point;
+import android.graphics.PointF;
+import android.os.Build;
+import android.os.Looper;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v4.util.ArrayMap;
+import android.support.v7.widget.GridLayoutManager;
+import android.support.v7.widget.LinearLayoutManager;
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+import android.text.TextUtils;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewTreeObserver;
+import android.widget.FrameLayout;
+import android.widget.LinearLayout;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.annotation.Component;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.ICheckBindingScroller;
+import org.apache.weex.common.OnWXScrollListener;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.el.parse.ArrayStack;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.AppearanceHelper;
+import org.apache.weex.ui.component.Scrollable;
+import org.apache.weex.ui.component.WXBaseRefresh;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXComponentProp;
+import org.apache.weex.ui.component.WXLoading;
+import org.apache.weex.ui.component.WXRefresh;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.component.binding.Layouts;
+import org.apache.weex.ui.component.binding.Statements;
+import org.apache.weex.ui.component.helper.ScrollStartEndHelper;
+import org.apache.weex.ui.component.list.RecyclerTransform;
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+import org.apache.weex.ui.view.listview.adapter.IOnLoadMoreListener;
+import org.apache.weex.ui.view.listview.adapter.IRecyclerAdapterListener;
+import org.apache.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
+import org.apache.weex.ui.view.listview.adapter.WXRecyclerViewOnScrollListener;
+import org.apache.weex.ui.view.refresh.wrapper.BounceRecyclerView;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+import java.util.Set;
+import java.util.concurrent.ConcurrentHashMap;
+import org.apache.weex.common.Constants.Name;
+
+/**
+ * weex template list supported, high performance recycler-list
+ * https://github.com/Hanks10100/weex-native-directive
+ * Created by jianbai.gbj on 2017/8/17.
+ */
+@Component(lazyload = false)
+public class WXRecyclerTemplateList extends WXVContainer<BounceRecyclerView> implements
+    IRecyclerAdapterListener<TemplateViewHolder>, IOnLoadMoreListener, Scrollable {
+
+    /**
+     * trace log for template list
+     * */
+    public static final boolean ENABLE_TRACE_LOG = false;
+
+    public static final String TAG = "WXRecyclerTemplateList";
+
+    private static final String EMPTY_HOLDER_TEMPLATE_KEY  = "";
+    private static final String NAME_HAS_FIXED_SIZE = "hasFixedSize";
+    private static final String NAME_ITEM_VIEW_CACHE_SIZE = "itemViewCacheSize";
+    private static final String NAME_TEMPLATE_CACHE_SIZE = "templateCacheSize";
+
+    // TODO
+//    private WXRecyclerDomObject mDomObject;
+    protected int mLayoutType = WXRecyclerView.TYPE_LINEAR_LAYOUT;
+    protected int mColumnCount = 1;
+    protected float mColumnGap = 0;
+    protected float mColumnWidth = 0;
+    private float mPaddingLeft;
+    private float mPaddingRight;
+
+    private WXRecyclerViewOnScrollListener mViewOnScrollListener = new WXRecyclerViewOnScrollListener(this);
+    private int mListCellCount = 0;
+    private boolean mForceLoadmoreNextTime = false;
+    private RecyclerView.ItemAnimator mItemAnimator;
+
+    /**
+     * default orientation
+     * */
+    private  int orientation = Constants.Orientation.VERTICAL;
+
+    /**
+     * offset reported
+     * */
+    private boolean isScrollable = true;
+    private int mOffsetAccuracy = 10;
+    private Point mLastReport = new Point(-1, -1);
+    private boolean mHasAddScrollEvent = false;
+
+
+    private CellDataManager cellDataManager;
+    private String listDataKey = Constants.Name.Recycler.LIST_DATA;
+    private String listDataItemKey = null;
+    private String listDataIndexKey = null;
+    private ArrayMap<String, Integer> mTemplateViewTypes;
+
+
+    private Map<String, WXCell> mTemplateSources;
+    private String  listDataTemplateKey = Constants.Name.Recycler.SLOT_TEMPLATE_CASE;
+    private Runnable listUpdateRunnable;
+    private ConcurrentHashMap<String, TemplateCache> mTemplatesCache;
+    private int templateCacheSize = 2;
+
+
+    /**
+     * case default cell and key
+     * */
+    private WXCell defaultTemplateCell;
+    private String defaultTemplateKey = "@default_template_cell";
+
+    /**
+     * scroll start and scroll end event
+     * */
+    private ScrollStartEndHelper mScrollStartEndHelper;
+
+
+    /**
+     * sticky helper
+     * */
+    private TemplateStickyHelper mStickyHelper;
+
+
+    /**
+     * appear and disappear event managaer
+     * */
+    private ArrayMap<Integer, List<AppearanceHelper>> mAppearHelpers = new ArrayMap<>();
+
+    /**
+     * disappear event will be fire,
+     * fist layer map key position,
+     * send layer map key String ref
+     * three layer map key view hash code, value is event arguments
+     * */
+    private ArrayMap<Integer, Map<String,Map<Integer, List<Object>>>> mDisAppearWatchList = new ArrayMap<>();
+
+    private CellRenderContext cellRenderContext = new CellRenderContext();
+
+    private Runnable mAppearChangeRunnable = null;
+    private static final long APPEAR_CHANGE_RUNNABLE_DELAY = 50;
+
+    /**
+     * has append tree done
+     * */
+    private boolean hasAppendTreeDone = false;
+
+    /**
+     * has layout done
+     * */
+    private boolean hasLayoutDone = false;
+
+    public WXRecyclerTemplateList(
+        WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+        super(instance, parent, basicComponentData);
+        initRecyclerTemplateList(instance, basicComponentData, parent);
+    }
+
+    private void initRecyclerTemplateList(WXSDKInstance instance, BasicComponentData basicComponentData,
+                                          WXVContainer parent){
+
+        updateRecyclerAttr();
+
+        mTemplateViewTypes = new ArrayMap<>();
+        mTemplateViewTypes.put(EMPTY_HOLDER_TEMPLATE_KEY, 0); //empty view, when template was not sended
+        mTemplateSources = new HashMap<>();
+        mTemplatesCache = new ConcurrentHashMap<>();
+        mStickyHelper = new TemplateStickyHelper(this);
+        orientation =  basicComponentData.getAttrs().getOrientation();
+        listDataTemplateKey = WXUtils.getString(getAttrs().get(Constants.Name.Recycler.LIST_DATA_TEMPLATE_SWITCH_KEY), Constants.Name.Recycler.SLOT_TEMPLATE_CASE);
+        listDataItemKey = WXUtils.getString(getAttrs().get(Constants.Name.Recycler.LIST_DATA_ITEM), listDataItemKey);
+        listDataIndexKey = WXUtils.getString(getAttrs().get(Constants.Name.Recycler.LIST_DATA_ITEM_INDEX), listDataIndexKey);
+        cellDataManager = new CellDataManager(this);
+        cellDataManager.listData = parseListDataToJSONArray(getAttrs().get(Constants.Name.Recycler.LIST_DATA));
+        /**
+         * we have separate cell with list, post add cell in dom thread ensure
+         * list has layout and can archive better user experience and better load time,
+         * which reduce waste cell layout when list layout changes.
+         * */
+        // TODO
+//        if(mDomObject != null
+//                && mDomObject.getCellList() != null
+//                && mDomObject.getCellList().size() > 0){
+//            Runnable runnable =  new Runnable() {
+//                // @Override
+//                public void run() {
+//                    if(isDestoryed()){
+//                        return;
+//                    }
+//                    long start = System.currentTimeMillis();
+//                    if(mDomObject != null && mDomObject.getCellList() != null){
+//                        for(int i=0; i<mDomObject.getCellList().size(); i++){
+//                            addChild(ComponentUtils.buildTree(mDomObject.getCellList().get(i),  WXRecyclerTemplateList.this));
+//                        }
+//                    }
+//                    if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG){
+//                        WXLogUtils.d(TAG, "TemplateList BuildDomTree Used " + (System.currentTimeMillis() - start));
+//                    }
+//                }
+//            };
+//            WXSDKManager.getInstance().getWXDomManager().post(runnable);
+//        }
+    }
+
+    @Override
+    protected BounceRecyclerView initComponentHostView(@NonNull Context context) {
+        final BounceRecyclerView bounceRecyclerView = new BounceRecyclerView(context,mLayoutType,mColumnCount,mColumnGap, getOrientation());
+        WXAttr attrs = getAttrs();
+        String transforms = (String) attrs.get(Constants.Name.TRANSFORM);
+        if (transforms != null) {
+            bounceRecyclerView.getInnerView().addItemDecoration(
+                RecyclerTransform.parseTransforms(getOrientation(), transforms));
+        }
+        mItemAnimator = bounceRecyclerView.getInnerView().getItemAnimator();
+
+        if(attrs.get(NAME_TEMPLATE_CACHE_SIZE) != null){
+            templateCacheSize =  WXUtils.getInteger(attrs.get(NAME_TEMPLATE_CACHE_SIZE), templateCacheSize);
+        }
+
+        boolean hasFixedSize = false;
+        int itemViewCacheSize = 2;
+        if(attrs.get(NAME_ITEM_VIEW_CACHE_SIZE) != null){
+            itemViewCacheSize = WXUtils.getNumberInt(getAttrs().get(NAME_ITEM_VIEW_CACHE_SIZE), itemViewCacheSize);
+        }
+        if(attrs.get(NAME_HAS_FIXED_SIZE) != null){
+            hasFixedSize =  WXUtils.getBoolean(attrs.get(NAME_HAS_FIXED_SIZE), hasFixedSize);
+        }
+        RecyclerViewBaseAdapter recyclerViewBaseAdapter = new RecyclerViewBaseAdapter<>(this);
+        recyclerViewBaseAdapter.setHasStableIds(true);
+        bounceRecyclerView.getInnerView().setItemAnimator(null);
+        if(itemViewCacheSize != 2) {
+            bounceRecyclerView.getInnerView().setItemViewCacheSize(itemViewCacheSize);
+        }
+        if(bounceRecyclerView.getSwipeLayout()  != null){
+            if(WXUtils.getBoolean(getAttrs().get("nestedScrollingEnabled"), false)) {
+                bounceRecyclerView.getSwipeLayout().setNestedScrollingEnabled(true);
+            }
+        }
+        bounceRecyclerView.getInnerView().setHasFixedSize(hasFixedSize);
+        bounceRecyclerView.setRecyclerViewBaseAdapter(recyclerViewBaseAdapter);
+        bounceRecyclerView.setOverScrollMode(View.OVER_SCROLL_NEVER);
+        bounceRecyclerView.getInnerView().clearOnScrollListeners();
+        bounceRecyclerView.getInnerView().addOnScrollListener(mViewOnScrollListener);
+        bounceRecyclerView.getInnerView().addOnScrollListener(new RecyclerView.OnScrollListener() {
+            @Override
+            public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
+                super.onScrollStateChanged(recyclerView, newState);
+                getScrollStartEndHelper().onScrollStateChanged(newState);
+                List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
+                if (listeners != null && listeners.size() > 0) {
+                    for (OnWXScrollListener listener : listeners) {
+                        if (listener != null) {
+                            View topView = recyclerView.getChildAt(0);
+                            if (topView != null) {
+                                int y = topView.getTop();
+                                listener.onScrollStateChanged(recyclerView, 0, y, newState);
+                            }
+                        }
+                    }
+                }
+            }
+
+            @Override
+            public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
+                super.onScrolled(recyclerView, dx, dy);
+                List<OnWXScrollListener> listeners = getInstance().getWXScrollListeners();
+                if (listeners != null && listeners.size() > 0) {
+                    try {
+                        for (OnWXScrollListener listener : listeners) {
+                            if (listener != null) {
+                                if (listener instanceof ICheckBindingScroller) {
+                                    if (((ICheckBindingScroller) listener).isNeedScroller(getRef(), null)) {
+                                        listener.onScrolled(recyclerView, dx, dy);
+                                    }
+                                } else {
+                                    listener.onScrolled(recyclerView, dx, dy);
+                                }
+                            }
+                        }
+                    } catch (Exception e) {
+                        e.printStackTrace();
+                    }
+                }
+            }
+        });
+        bounceRecyclerView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
+            @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
+            @Override
+            public void onGlobalLayout() {
+                BounceRecyclerView view;
+                if ((view = getHostView()) == null)
+                    return;
+                mViewOnScrollListener.onScrolled(view.getInnerView(), 0, 0);
+                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+                    view.getViewTreeObserver().removeOnGlobalLayoutListener(this);
+                } else {
+                    view.getViewTreeObserver().removeGlobalOnLayoutListener(this);
+                }
+            }
+        });
+        listUpdateRunnable = new Runnable() {
+            @Override
+            public void run() {
+                /**
+                 * compute sticky position
+                 * */
+                if(mStickyHelper != null){
+                    if(mStickyHelper.getStickyTypes().size() > 0){
+                        mStickyHelper.getStickyPositions().clear();
+                        if(cellDataManager.listData != null){
+                            for(int i = 0; i< cellDataManager.listData.size(); i++){
+                                WXCell cell = getSourceTemplate(i);
+                                if(cell == null){
+                                    continue;
+                                }
+                                if(cell.isSticky()){
+                                    mStickyHelper.getStickyPositions().add(i);
+                                }
+                            }
+                        }
+                    }
+                }
+                if(getHostView() != null && getHostView().getRecyclerViewBaseAdapter() != null){
+                    getHostView().getRecyclerViewBaseAdapter().notifyDataSetChanged();
+                }
+                if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG){
+                    WXLogUtils.d(TAG, "WXTemplateList notifyDataSetChanged");
+                }
+            }
+        };
+        return bounceRecyclerView;
+    }
+
+
+
+
+    @Override
+    protected void onHostViewInitialized(BounceRecyclerView host) {
+        super.onHostViewInitialized(host);
+        WXRecyclerView recyclerView = host.getInnerView();
+        if (recyclerView == null || recyclerView.getAdapter() == null) {
+            WXLogUtils.e(TAG, "RecyclerView is not found or Adapter is not bound");
+            return;
+        }
+    }
+
+    /**
+     * Measure the size of the recyclerView.
+     *
+     * @param width  the expected width
+     * @param height the expected height
+     * @return the result of measurement
+     */
+    @Override
+    protected MeasureOutput measure(int width, int height) {
+        int screenH = WXViewUtils.getScreenHeight(WXEnvironment.sApplication);
+        int weexH = WXViewUtils.getWeexHeight(getInstanceId());
+        int outHeight = height > (weexH >= screenH ? screenH : weexH) ? weexH - getAbsoluteY() : height;
+        return super.measure(width, outHeight);
+    }
+
+
+    @Override
+    public void bindStickStyle(WXComponent component) {
+        WXComponent template = findParentType(component, WXCell.class);
+        if(template == null){
+            return;
+        }
+        if(mStickyHelper == null){
+            return;
+        }
+        if(!mStickyHelper.getStickyTypes().contains(template.getRef())){
+            mStickyHelper.getStickyTypes().add(template.getRef());
+            notifyUpdateList();
+        }
+    }
+
+    @Override
+    public void unbindStickStyle(WXComponent component) {
+        WXComponent template = findParentType(component, WXCell.class);
+        if(template == null
+                || mStickyHelper == null){
+            return;
+        }
+        if(mStickyHelper.getStickyTypes().contains(template.getRef())){
+            mStickyHelper.getStickyTypes().remove(template.getRef());
+            notifyUpdateList();
+        }
+    }
+
+    private @Nullable
+    WXCell findCell(WXComponent component) {
+        if(component instanceof WXCell){
+            return (WXCell) component;
+        }
+        WXComponent parent;
+        if (component == null || (parent = component.getParent()) == null) {
+            return null;
+        }
+        return findCell(parent);
+    }
+
+    private void setAppearanceWatch(WXComponent component, int event, boolean enable) {
+        if(cellDataManager.listData == null
+                || mAppearHelpers == null
+                || TextUtils.isEmpty(component.getRef())){
+            return;
+        }
+        WXCell cell = findCell(component);
+        int type = getCellTemplateItemType(cell);
+        if(type < 0){
+            return;
+        }
+        List<AppearanceHelper>  mAppearListeners = mAppearHelpers.get(type);
+        if(mAppearListeners == null){
+            mAppearListeners = new ArrayList<>();
+            mAppearHelpers.put(type, mAppearListeners);
+        }
+        AppearanceHelper item = null;
+        for(AppearanceHelper mAppearListener : mAppearListeners){
+            if(component.getRef().equals(mAppearListener.getAwareChild().getRef())){
+                item = mAppearListener;
+                break;
+            }
+        }
+        if (item != null) {
+            item.setWatchEvent(event, enable);
+        }else {
+            item = new AppearanceHelper(component,  type);
+            item.setWatchEvent(event, enable);
+            mAppearListeners.add(item);
+        }
+    }
+
+    @Override
+    public void bindAppearEvent(WXComponent component) {
+        setAppearanceWatch(component, AppearanceHelper.APPEAR, true);
+        if(mAppearChangeRunnable == null){
+            mAppearChangeRunnable =  new Runnable() {
+                @Override
+                public void run() {
+                    if(mAppearChangeRunnable != null) {
+                        notifyAppearStateChange(0, 0, 0, 0);
+                    }
+                }
+            };
+        }
+        if (getHostView() != null) {
+            getHostView().removeCallbacks(mAppearChangeRunnable);
+            getHostView().postDelayed(mAppearChangeRunnable, APPEAR_CHANGE_RUNNABLE_DELAY);
+        }
+    }
+
+    @Override
+    public void bindDisappearEvent(WXComponent component) {
+        setAppearanceWatch(component, AppearanceHelper.DISAPPEAR, true);
+        if(mAppearChangeRunnable == null){
+            mAppearChangeRunnable =  new Runnable() {
+                @Override
+                public void run() {
+                    if(mAppearChangeRunnable != null) {
+                        notifyAppearStateChange(0, 0, 0, 0);
+                    }
+                }
+            };
+        }
+        if (getHostView() != null) {
+            getHostView().removeCallbacks(mAppearChangeRunnable);
+            getHostView().postDelayed(mAppearChangeRunnable, APPEAR_CHANGE_RUNNABLE_DELAY);
+        }
+    }
+
+    @Override
+    public void unbindAppearEvent(WXComponent component) {
+        setAppearanceWatch(component, AppearanceHelper.APPEAR, false);
+    }
+
+    @Override
+    public void unbindDisappearEvent(WXComponent component) {
+        setAppearanceWatch(component, AppearanceHelper.DISAPPEAR, false);
+    }
+
+
+    @JSMethod(uiThread = true)
+    public void queryElement(String virtualRef, String selector, JSCallback callback){
+        try{
+            String[]  segments = virtualRef.split(TemplateDom.SEPARATOR + "");
+            String listRef = segments[0];
+            int position = Integer.parseInt(segments[1]); // position
+            WXComponent component = TemplateDom.findVirtualComponentByVRef(getInstanceId(), virtualRef);
+            if(component == null){
+                return;
+            }
+            if(getHostView() == null || getHostView().getInnerView() == null){
+                return;
+            }
+            List<WXComponent>  componentList  = new ArrayList<>(4);
+            Selector.queryElementAll(component, selector, componentList);
+            if(componentList.size() > 0){
+                callback.invoke(TemplateDom.toMap(listRef, position, componentList.get(0)));
+            }else{
+                callback.invoke(new HashMap<>(4));
+            }
+        }catch (Exception e){
+            callback.invoke(new HashMap<>(4));
+            WXLogUtils.e(TAG, e);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void queryElementAll(String virtualRef,  String selector, JSCallback callback){
+        List datas = new ArrayList();
+        try{
+            String[]  segments = virtualRef.split(TemplateDom.SEPARATOR + "");
+            String listRef = segments[0];
+            int position = Integer.parseInt(segments[1]); // position
+            WXComponent component = TemplateDom.findVirtualComponentByVRef(getInstanceId(), virtualRef);
+            if(component == null){
+                return;
+            }
+            if(getHostView() == null || getHostView().getInnerView() == null){
+                return;
+            }
+            List<WXComponent>  componentList  = new ArrayList<>(4);
+            Selector.queryElementAll(component, selector, componentList);
+            for(WXComponent child : componentList){
+                datas.add(TemplateDom.toMap(listRef, position, child));
+            }
+            callback.invoke(datas);
+        }catch (Exception e){
+            callback.invoke(datas);
+            WXLogUtils.e(TAG, e);
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void closest(String virtualRef,  String selector, JSCallback callback){
+        try{
+            String[]  segments = virtualRef.split(TemplateDom.SEPARATOR + "");
+            String listRef = segments[0];
+            int position = Integer.parseInt(segments[1]); // position
+            WXComponent component = TemplateDom.findVirtualComponentByVRef(getInstanceId(), virtualRef);
+            if(component == null){
+                return;
+            }
+            if(getHostView() == null || getHostView().getInnerView() == null){
+                return;
+            }
+            List<WXComponent>  componentList  = new ArrayList<>(4);
+            Selector.closest(component, selector, componentList);
+            if(componentList.size() > 0){
+                callback.invoke(TemplateDom.toMap(listRef, position, componentList.get(0)));
+            }else{
+                callback.invoke(new HashMap<>(4));
+            }
+        }catch (Exception e){
+            callback.invoke(new HashMap<>(4));
+            WXLogUtils.e(TAG, e);
+        }
+    }
+
+
+
+    @JSMethod(uiThread = true)
+    public void scrollToElement(String virtualRef, Map<String, Object> options){
+        scrollTo(virtualRef, options);
+    }
+
+
+    @JSMethod(uiThread = true)
+    public void scrollTo(String virtualRef, Map<String, Object> options){
+        int position = -1;
+        try{
+            if(virtualRef.indexOf(TemplateDom.SEPARATOR) > 0){
+                String[]  segments = virtualRef.split(TemplateDom.SEPARATOR + "");
+                position = Integer.parseInt(segments[0]);
+            }else{
+                position = (int) Float.parseFloat(virtualRef);
+            }
+            if (position >= 0) {
+                boolean smooth = true;
+                float offsetFloat = 0;
+                if(options != null) {
+                    smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
+                    String offsetStr = options.get(Constants.Name.OFFSET) == null ? "0" : options.get(Constants.Name.OFFSET).toString();
+                    smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
+                    if (offsetStr != null) {
+                        try {
+                            offsetFloat = WXViewUtils.getRealPxByWidth(Float.parseFloat(offsetStr), getInstance().getInstanceViewPortWidth());
+                        }catch (Exception e ){
+                            WXLogUtils.e("Float parseFloat error :"+e.getMessage());
+                        }
+                    }
+                }
+                final int offset = (int) offsetFloat;
+
+                final int pos = position;
+                BounceRecyclerView bounceRecyclerView = getHostView();
+                if (bounceRecyclerView == null) {
+                    return;
+                }
+                final WXRecyclerView view = bounceRecyclerView.getInnerView();
+                view.scrollTo(smooth, pos, offset, getOrientation());
+            }
+        }catch (Exception e){
+            WXLogUtils.e(TAG, e);
+        }
+    }
+
+
+    @Override
+    public void scrollTo(WXComponent component, Map<String, Object> options) {
+        float offsetFloat = 0;
+        boolean smooth = true;
+        int position = -1;
+        int typeIndex = -1;
+        if (options != null) {
+            String offsetStr = options.get(Constants.Name.OFFSET) == null ? "0" : options.get(Constants.Name.OFFSET).toString();
+            smooth = WXUtils.getBoolean(options.get(Constants.Name.ANIMATED), true);
+            if (offsetStr != null) {
+                try {
+                    offsetFloat = WXViewUtils.getRealPxByWidth(Float.parseFloat(offsetStr), getInstance().getInstanceViewPortWidth());
+                }catch (Exception e ){
+                    WXLogUtils.e("Float parseFloat error :"+e.getMessage());
+                }
+            }
+            position = WXUtils.getNumberInt(options.get(Constants.Name.Recycler.CELL_INDEX), -1);
+            typeIndex = WXUtils.getNumberInt(options.get(Constants.Name.Recycler.TYPE_INDEX), -1);
+        }
+        WXCell cell = findCell(component);
+        if(typeIndex >= 0){
+            if(cellDataManager.listData != null && component.getRef() != null){
+                int typePosition = 0;
+                for(int i = 0; i< cellDataManager.listData.size(); i++){
+                    WXCell template = getSourceTemplate(i);
+                    if(template == null){
+                        continue;
+                    }
+                    if(cell.getRef().equals(template.getRef())){
+                        typePosition ++;
+                    }
+                    if(typePosition > typeIndex){
+                        position = i;
+                        break;
+                    }
+                }
+                if(position < 0){
+                    position = cellDataManager.listData.size() - 1;
+                }
+            }
+        }
+
+        final int offset = (int) offsetFloat;
+        BounceRecyclerView bounceRecyclerView = getHostView();
+        if (bounceRecyclerView == null) {
+            return;
+        }
+        if (position >= 0) {
+            final int pos = position;
+            final WXRecyclerView view = bounceRecyclerView.getInnerView();
+            view.scrollTo(smooth, pos, offset, getOrientation());
+        }
+    }
+
+    @Override
+    public int getScrollY() {
+        BounceRecyclerView bounceRecyclerView = getHostView();
+        return bounceRecyclerView == null ? 0 : bounceRecyclerView.getInnerView().getScrollY();
+    }
+
+    @Override
+    public int getScrollX() {
+        BounceRecyclerView bounceRecyclerView = getHostView();
+        return bounceRecyclerView == null ? 0 : bounceRecyclerView.getInnerView().getScrollX();
+    }
+
+    public int getOrientation() {
+        return orientation;
+    }
+
+    @Override
+    public boolean isScrollable() {
+        return isScrollable;
+    }
+
+
+
+    @Override
+    public void addChild(WXComponent child) {
+        this.addChild(child, -1);
+    }
+
+    @Override
+    protected int getChildrenLayoutTopOffset() {
+        return 0;
+    }
+
+    @Override
+    public void addChild(WXComponent child, int index) {
+        /**
+         *  dom object in component is not tree, build tree
+         * */
+        if(!(child instanceof WXCell)) {
+            super.addChild(child, index);
+        }
+        if(child instanceof WXBaseRefresh){
+            return;
+        }
+        if(child instanceof WXCell){
+            if(child.getAttrs() != null){
+                Object templateId = child.getAttrs().get(Constants.Name.Recycler.SLOT_TEMPLATE_CASE);
+                String key = WXUtils.getString(templateId, null);
+                if(getAttrs().containsKey(Constants.Name.Recycler.LIST_DATA_TEMPLATE_SWITCH_KEY)){
+                    if(defaultTemplateCell == null){
+                        defaultTemplateCell = (WXCell) child;
+                        if(!TextUtils.isEmpty(key)){
+                            defaultTemplateKey = key;
+                        }else{
+                            key = defaultTemplateKey;
+                            child.getAttrs().put(Constants.Name.Recycler.SLOT_TEMPLATE_CASE, key);
+                        }
+                    }
+                }else{
+                    if(defaultTemplateCell == null
+                            || child.getAttrs().containsKey(Constants.Name.Recycler.SLOT_TEMPLATE_DEFAULT)){
+                        defaultTemplateCell = (WXCell) child;
+                        if(!TextUtils.isEmpty(key)){
+                            defaultTemplateKey = key;
+                        }else{
+                            key = defaultTemplateKey;
+                            child.getAttrs().put(Constants.Name.Recycler.SLOT_TEMPLATE_CASE, key);
+                        }
+                    }
+                }
+                if(key != null){
+                    // TODO
+//                    if(child.getDomObject() instanceof  WXCellDomObject
+//                            && getDomObject() instanceof  WXRecyclerDomObject){
+//                        WXCellDomObject domObject = (WXCellDomObject) child.getDomObject();
+//                        domObject.setRecyclerDomObject((WXRecyclerDomObject) getDomObject());
+//                    }
+                    mTemplateSources.put(key, (WXCell) child);
+                    if(mTemplateViewTypes.get(key) == null){
+                        mTemplateViewTypes.put(key, mTemplateViewTypes.size());
+                    }
+                }
+            }
+
+            ((WXCell) child).setCellAppendTreeListener(new WXCell.CellAppendTreeListener() {
+                @Override
+                public void onAppendTreeDone() {
+                    checkAppendDone(false);
+                }
+            });
+        }
+    }
+
+
+    /**
+     * check all the cell has append tree done, then show list
+     * */
+    private void  checkAppendDone(boolean listDone){
+        if(mTemplateSources.size() == 0){
+            return;
+        }
+        Set<Map.Entry<String,WXCell>> cells = mTemplateSources.entrySet();
+        for(Map.Entry<String,WXCell> entry : cells){
+            if(!entry.getValue().isAppendTreeDone()){
+                return;
+            }
+        }
+        hasAppendTreeDone = true;
+        if(hasLayoutDone) {
+            notifyUpdateList();
+        }
+    }
+
+    @Override
+    protected void setHostLayoutParams(BounceRecyclerView host, int width, int height, int left, int right, int top, int bottom) {
+        super.setHostLayoutParams(host, width, height, left, right, top, bottom);
+        if(!hasLayoutDone){
+            hasLayoutDone = true;
+            hasAppendTreeDone = true;
+            notifyUpdateList();
+        }
+    }
+
+
+    /**
+     * RecyclerView manage its children in a way that different from {@link WXVContainer}. Therefore,
+     * {@link WXVContainer#addSubView(View, int)} is an empty implementation in {@link
+     * WXRecyclerView}
+     */
+    @Override
+    public void addSubView(View child, int index) {
+
+    }
+
+
+    /**
+     * all child is template, none need onCreate child except loading and refresh.
+     * */
+    @Override
+    public void createChildViewAt(int index) {
+        int indexToCreate = index;
+        if (indexToCreate < 0) {
+            indexToCreate = childCount() - 1;
+            if (indexToCreate < 0) {
+                return;
+            }
+        }
+        final WXComponent child = getChild(indexToCreate);
+        if (child instanceof WXBaseRefresh) {
+            child.createView();
+            setRefreshOrLoading(child);
+        }
+    }
+
+    @Override
+    public void remove(WXComponent child, boolean destroy) {
+        removeFooterOrHeader(child);
+        super.remove(child, destroy);
+    }
+
+
+
+    @Override
+    public void computeVisiblePointInViewCoordinate(PointF pointF) {
+        RecyclerView view = getHostView().getInnerView();
+        pointF.set(view.computeHorizontalScrollOffset(), view.computeVerticalScrollOffset());
+    }
+
+    @Override
+    protected boolean setProperty(String key, Object param) {
+        switch (key) {
+            case Constants.Name.Recycler.LIST_DATA:{
+                     setListData(param);
+                }
+                return true;
+            case Constants.Name.Recycler.LIST_DATA_ITEM:
+                listDataItemKey = WXUtils.getString(param, listDataItemKey);
+                return true;
+            case Constants.Name.Recycler.LIST_DATA_ITEM_INDEX:
+                listDataIndexKey = WXUtils.getString(param, listDataIndexKey);
+                return true;
+            case Constants.Name.Recycler.LIST_DATA_TEMPLATE_SWITCH_KEY:
+            case Constants.Name.Recycler.SLOT_TEMPLATE_CASE:
+                listDataTemplateKey = WXUtils.getString(param, Constants.Name.Recycler.SLOT_TEMPLATE_CASE);
+                return true;
+            case Name.LOADMOREOFFSET:
+                return true;
+            case Constants.Name.SCROLLABLE:
+                boolean scrollable = WXUtils.getBoolean(param, true);
+                setScrollable(scrollable);
+                return true;
+            case Constants.Name.SCROLL_DIRECTION:
+                if(param != null) {
+                    setScrollDirection(param.toString());
+                }
+                return true;
+            case Constants.Name.SHOW_SCROLLBAR:
+                Boolean result = WXUtils.getBoolean(param,null);
+                if (result != null)
+                    setShowScrollbar(result);
+                return true;
+            case NAME_ITEM_VIEW_CACHE_SIZE:
+                return true;
+            case NAME_HAS_FIXED_SIZE:
+                return true;
+            case Constants.Name.OFFSET_ACCURACY:
+                int accuracy = WXUtils.getInteger(param, 10);
+                setOffsetAccuracy(accuracy);
+                return true;
+        }
+        return super.setProperty(key, param);
+    }
+
+
+    @WXComponentProp(name = Constants.Name.OFFSET_ACCURACY)
+    public void setOffsetAccuracy(int accuracy) {
+        float real = WXViewUtils.getRealPxByWidth(accuracy, getInstance().getInstanceViewPortWidth());
+        this.mOffsetAccuracy = (int) real;
+    }
+
+
+    private void updateRecyclerAttr(){
+        mLayoutType = getAttrs().getLayoutType();
+        mColumnCount = getAttrs().getColumnCount();
+        if (mColumnCount <= 0 && mLayoutType != WXRecyclerView.TYPE_LINEAR_LAYOUT) {
+            Map<String, String> ext = new ArrayMap<>();
+            ext.put("componentType", getComponentType());
+            ext.put("attribute", getAttrs().toString());
+            ext.put("stackTrace", Arrays.toString(Thread.currentThread().getStackTrace()));
+            WXExceptionUtils.commitCriticalExceptionRT(getInstanceId(),
+                WXErrorCode.WX_RENDER_ERR_LIST_INVALID_COLUMN_COUNT, "columnCount",
+                String.format(Locale.ENGLISH,
+                    "You are trying to set the list/recycler/vlist/waterfall's column to %d, which is illegal. The column count should be a positive integer",
+                    mColumnCount),
+                ext);
+            mColumnCount = Constants.Value.COLUMN_COUNT_NORMAL;
+        }
+        mColumnGap = getAttrs().getColumnGap();
+        mColumnWidth = getAttrs().getColumnWidth();
+        mPaddingLeft = getPadding().get(CSSShorthand.EDGE.LEFT);
+        mPaddingRight = getPadding().get(CSSShorthand.EDGE.RIGHT);
+
+    }
+
+
+    @WXComponentProp(name = Constants.Name.SCROLL_DIRECTION)
+    public void setScrollDirection(String direction){
+        if(orientation != getAttrs().getOrientation()) {
+            orientation = getAttrs().getOrientation();
+            updateRecyclerAttr();
+            WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+            wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap, getOrientation());
+
+        }
+    }
+
+    @WXComponentProp(name = Constants.Name.COLUMN_WIDTH)
+    public void setColumnWidth(int columnCount)  {
+        if(getAttrs().getColumnWidth() != mColumnWidth){
+            updateRecyclerAttr();
+            WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+            wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap, getOrientation());
+        }
+    }
+
+    @WXComponentProp(name = Constants.Name.SHOW_SCROLLBAR)
+    public void setShowScrollbar(boolean show) {
+        if(getHostView() == null || getHostView().getInnerView() == null){
+            return;
+        }
+        if (getOrientation() == Constants.Orientation.VERTICAL) {
+            getHostView().getInnerView().setVerticalScrollBarEnabled(show);
+        } else {
+            getHostView().getInnerView().setHorizontalScrollBarEnabled(show);
+        }
+    }
+
+    @WXComponentProp(name = Constants.Name.COLUMN_COUNT)
+    public void setColumnCount(int columnCount){
+        if(getAttrs().getColumnCount() != mColumnCount){
+            updateRecyclerAttr();
+            WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+            wxRecyclerView.initView(getContext(), mLayoutType,mColumnCount,mColumnGap,getOrientation());
+        }
+    }
+
+    @WXComponentProp(name = Constants.Name.COLUMN_GAP)
+    public void setColumnGap(float columnGap) throws InterruptedException {
+        if(getAttrs().getColumnGap() != mColumnGap) {
+            updateRecyclerAttr();
+            WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+            wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
+        }
+    }
+
+    @WXComponentProp(name = Constants.Name.SCROLLABLE)
+    public void setScrollable(boolean scrollable) {
+        WXRecyclerView inner = getHostView().getInnerView();
+        inner.setScrollable(scrollable);
+    }
+
+    @JSMethod
+    public void setListData(Object param){
+        param = parseListDataToJSONArray(param);
+        boolean update = cellDataManager.listData != param;
+        if(param instanceof  JSONArray){
+            if(update){
+                cellDataManager.setListData((JSONArray) param);
+                notifyUpdateList();
+            }
+        }
+    }
+
+    @JSMethod
+    public void  appendData(JSONArray data){
+        if(data == null || data.size() == 0){
+            return;
+        }
+        if(cellDataManager.listData == null){
+            cellDataManager.listData = new JSONArray();
+        }
+        int position = cellDataManager.listData.size();
+        if(position < 0){
+            position = 0;
+        }
+        if(data instanceof  JSONArray){
+            cellDataManager.listData.addAll(data);
+        }
+        getHostView().getRecyclerViewBaseAdapter().notifyItemRangeInserted(position, data.size());
+    }
+
+    @JSMethod
+    public void  insertData(int index, Object data){
+        if(data == null){
+            return;
+        }
+
+        if(cellDataManager.listData == null || index > cellDataManager.listData.size()){
+            return;
+        }
+        boolean renderStateChanged = cellDataManager.insertData(index, data);
+        if(renderStateChanged){
+            notifyUpdateList();
+        }else{
+            getHostView().getRecyclerViewBaseAdapter().notifyItemInserted(index);
+        }
+    }
+
+    @JSMethod
+    public void  appendRange(int index, JSONArray data){
+         insertRange(index, data);
+    }
+
+
+    /**
+     * when update data, list maybe contains sticky, may use position, when position changed should be rendered
+     * so use notifyUpdateList is better
+     * */
+
+    @JSMethod
+    public void  insertRange(int index, JSONArray data){
+        if(data == null || data.size() == 0){
+            return;
+        }
+        if(cellDataManager.listData == null || index > cellDataManager.listData.size()){
+            return;
+        }
+        boolean renderStateChange = cellDataManager.insertRange(index, data);
+        if(renderStateChange){
+            notifyUpdateList();
+        }else{
+            getHostView().getRecyclerViewBaseAdapter().notifyItemRangeInserted(index, data.size());
+        }
+
+    }
+
+    @JSMethod
+    public void  updateData(int index, Object data){
+        if(data == null){
+            return;
+        }
+        if(cellDataManager.listData == null || index >= cellDataManager.listData.size()){
+            return;
+        }
+        boolean onlyDataChange = cellDataManager.updateData(data, index);
+        if(onlyDataChange) {
+            getHostView().getRecyclerViewBaseAdapter().notifyItemChanged(index, data);
+        }else{
+            notifyUpdateList();
+        }
+    }
+
+    @JSMethod
+    public void  removeData(int index, int count){
+        if(cellDataManager.listData == null
+                || index >= cellDataManager.listData.size()){
+            return;
+        }
+        if(count <= 0){
+            count = 1;
+        }
+        int removeCount = 0;
+        while (count > 0 && index < cellDataManager.listData.size()){
+            cellDataManager.removeData(index);
+            count--;
+            removeCount++;
+        }
+        if(removeCount > 0) {
+            notifyUpdateList();
+        }
+    }
+
+
+    @JSMethod
+    public void resetLoadmore() {
+        mForceLoadmoreNextTime = true;
+        mListCellCount = 0;
+    }
+
+
+    @Override
+    public void updateProperties(Map<String, Object> props) {
+        super.updateProperties(props);
+        if(props.containsKey(Constants.Name.PADDING)
+                || props.containsKey(Constants.Name.PADDING_LEFT)
+                || props.containsKey(Constants.Name.PADDING_RIGHT)){
+
+            if(mPaddingLeft != getPadding().get(CSSShorthand.EDGE.LEFT)
+                    || mPaddingRight != getPadding().get(CSSShorthand.EDGE.RIGHT)) {
+                updateRecyclerAttr();
+                WXRecyclerView wxRecyclerView = getHostView().getInnerView();
+                wxRecyclerView.initView(getContext(), mLayoutType, mColumnCount, mColumnGap, getOrientation());
+            }
+        }
+    }
+
+
+
+    @Override
+    public void addEvent(String type) {
+        super.addEvent(type);
+        if (ScrollStartEndHelper.isScrollEvent(type)
+                && getHostView() != null
+                && getHostView().getInnerView() != null
+                && !mHasAddScrollEvent) {
+            mHasAddScrollEvent = true;
+            WXRecyclerView innerView = getHostView().getInnerView();
+            innerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
+                private int offsetXCorrection, offsetYCorrection;
+                private boolean mFirstEvent = true;
+
+                @Override
+                public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
+                    super.onScrolled(recyclerView, dx, dy);
+                    RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
+                    if (!layoutManager.canScrollVertically()) {
+                        return;
+                    }
+                    int offsetX = recyclerView.computeHorizontalScrollOffset();
+                    int offsetY = recyclerView.computeVerticalScrollOffset();
+
+                    if (dx == 0 && dy == 0) {
+                        offsetXCorrection = offsetX;
+                        offsetYCorrection = offsetY;
+                        offsetX = 0;
+                        offsetY = 0;
+                    } else {
+                        offsetX = offsetX - offsetXCorrection;
+                        offsetY = offsetY - offsetYCorrection;
+                    }
+                    getScrollStartEndHelper().onScrolled(offsetX, offsetY);
+                    if(!getEvents().contains(Constants.Event.SCROLL)){
+                        return;
+                    }
+                    if (mFirstEvent) {
+                        //skip first event
+                        mFirstEvent = false;
+                        return;
+                    }
+
+                    if (shouldReport(offsetX, offsetY)) {
+                        fireScrollEvent(recyclerView, offsetX, offsetY);
+                    }
+                }
+            });
+        }
+    }
+
+    private void fireScrollEvent(RecyclerView recyclerView, int offsetX, int offsetY) {
+        fireEvent(Constants.Event.SCROLL, getScrollEvent(recyclerView, offsetX, offsetY));
+    }
+
+    public Map<String, Object> getScrollEvent(RecyclerView recyclerView, int offsetX, int offsetY){
+        offsetY = -calcContentOffset(recyclerView);
+        int contentWidth = recyclerView.getMeasuredWidth() + recyclerView.computeHorizontalScrollRange();
+        int contentHeight = calcContentSize();
+
+        Map<String, Object> event = new HashMap<>(3);
+        Map<String, Object> contentSize = new HashMap<>(3);
+        Map<String, Object> contentOffset = new HashMap<>(3);
+
+        contentSize.put(Constants.Name.WIDTH, WXViewUtils.getWebPxByWidth(contentWidth, getInstance().getInstanceViewPortWidth()));
+        contentSize.put(Constants.Name.HEIGHT, WXViewUtils.getWebPxByWidth(contentHeight, getInstance().getInstanceViewPortWidth()));
+
+        contentOffset.put(Constants.Name.X, - WXViewUtils.getWebPxByWidth(offsetX, getInstance().getInstanceViewPortWidth()));
+        contentOffset.put(Constants.Name.Y, - WXViewUtils.getWebPxByWidth(offsetY, getInstance().getInstanceViewPortWidth()));
+        event.put(Constants.Name.CONTENT_SIZE, contentSize);
+        event.put(Constants.Name.CONTENT_OFFSET, contentOffset);
+        event.put(Constants.Name.ISDRAGGING, recyclerView.getScrollState() == RecyclerView.SCROLL_STATE_DRAGGING);
+        return event;
+    }
+
+
+
+    private boolean shouldReport(int offsetX, int offsetY) {
+        if (mLastReport.x == -1 && mLastReport.y == -1) {
+            mLastReport.x = offsetX;
+            mLastReport.y = offsetY;
+            return true;
+        }
+
+        int gapX = Math.abs(mLastReport.x - offsetX);
+        int gapY = Math.abs(mLastReport.y - offsetY);
+
+        if (gapX >= mOffsetAccuracy || gapY >= mOffsetAccuracy) {
+            mLastReport.x = offsetX;
+            mLastReport.y = offsetY;
+            return true;
+        }
+
+        return false;
+    }
+
+
+    /**
+     * Setting refresh view and loading view
+     *
+     * @param child the refresh_view or loading_view
+     */
+    private boolean setRefreshOrLoading(final WXComponent child) {
+        if (child instanceof WXRefresh && getHostView() != null) {
+            getHostView().setOnRefreshListener((WXRefresh) child);
+            getHostView().postDelayed(WXThread.secure(new Runnable() {
+                @Override
+                public void run() {
+                    getHostView().setHeaderView(child);
+                }
+            }), 100);
+            return true;
+        }
+
+        if (child instanceof WXLoading && getHostView() != null) {
+            getHostView().setOnLoadingListener((WXLoading) child);
+            getHostView().postDelayed(WXThread.secure(new Runnable() {
+                @Override
+                public void run() {
+                    getHostView().setFooterView(child);
+                }
+            }), 100);
+            return true;
+        }
+        return false;
+    }
+
+
+    private void removeFooterOrHeader(WXComponent child) {
+        if (child instanceof WXLoading) {
+            getHostView().removeFooterView(child);
+        } else if (child instanceof WXRefresh) {
+            getHostView().removeHeaderView(child);
+        }
+    }
+
+    @Override
+    public ViewGroup.LayoutParams getChildLayoutParams(WXComponent child, View hostView, int width, int height, int left, int right, int top, int bottom) {
+        ViewGroup.MarginLayoutParams params = (ViewGroup.MarginLayoutParams) hostView.getLayoutParams();
+        if (child instanceof WXBaseRefresh && params == null) {
+            params = new LinearLayout.LayoutParams(width, height);
+        } else if (params == null) {
+            params = new RecyclerView.LayoutParams(width, height);
+        } else {
+            params.width = width;
+            params.height = height;
+
+            this.setMarginsSupportRTL(params, left, 0, right, 0);
+        }
+        return params;
+    }
+
+
+    @Override
+    public void destroy() {
+        synchronized (this){
+            if(getHostView() != null){
+                if(mAppearChangeRunnable != null) {
+                    getHostView().removeCallbacks(mAppearChangeRunnable);
+                    mAppearChangeRunnable = null;
+                }
+                getHostView().removeCallbacks(listUpdateRunnable);
+                if(getHostView().getInnerView() != null){
+                    getHostView().getInnerView().setAdapter(null);
+                }
+            }
+            if(cellDataManager.listData != null){
+                cellDataManager.setListData(null);
+            }
+            if(mStickyHelper != null){
+                mStickyHelper = null;
+            }
+            if(mTemplateViewTypes != null){
+                mTemplateViewTypes.clear();
+            }
+            if(mTemplateSources != null){
+                mTemplateSources.clear();
+            }
+            if(mAppearHelpers != null){
+                mAppearHelpers.clear();
+            }
+            if(mDisAppearWatchList != null){
+                mDisAppearWatchList.clear();
+            }
+            super.destroy();
+        }
+    }
+
+
+
+    @Override
+    public void onViewRecycled(TemplateViewHolder holder) {}
+
+    @Override
+    public void onBindViewHolder(final TemplateViewHolder templateViewHolder, int position) {
+        if(templateViewHolder == null){
+            return;
+        }
+        WXCell component = templateViewHolder.getTemplate();
+        if(component == null){
+            return;
+        }
+        if(templateViewHolder.getHolderPosition() >= 0){
+            fireEvent(TemplateDom.DETACH_CELL_SLOT, TemplateDom.findAllComponentRefs(getRef(), position, component));
+        }
+        long start = System.currentTimeMillis();
+        templateViewHolder.setHolderPosition(position);
+        Object data = cellDataManager.listData.get(position);
+        CellRenderState cellRenderState = cellDataManager.getRenderState(position);
+        if((component.getRenderData() == data && (cellRenderState == null || !cellRenderState.isDirty()))){
+            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG){
+                WXLogUtils.d(TAG,  position + " position "+ getTemplateKey(position) + " onBindViewHolder none data update "
+                        + " component " + component.hashCode());
+            }
+            fireEvent(TemplateDom.ATTACH_CELL_SLOT, TemplateDom.findAllComponentRefs(getRef(), position, component));
+            return;  //none update just return
+        }else{
+            List<WXComponent> updates = doRenderTemplate(component, position);
+            Statements.doInitCompontent(updates);
+            component.setRenderData(data);
+            Layouts.doLayoutAsync(templateViewHolder, true);
+            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG){
+                WXLogUtils.d(TAG,  position + " position "+ getTemplateKey(position) + " onBindViewHolder used " + (System.currentTimeMillis() - start)
+                  + " component " + component.hashCode());
+            }
+        }
+    }
+
+    @Override
+    public TemplateViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
+        String template = mTemplateViewTypes.keyAt(viewType);
+        WXCell source = mTemplateSources.get(template);
+        if(source == null){
+            FrameLayout view = new FrameLayout(getContext());
+            view.setLayoutParams(new FrameLayout.LayoutParams(0, 0));
+            return new TemplateViewHolder(this, view, viewType);
+        }
+        WXCell component =  getCellTemplateFromCache(template);
+        boolean cacheHit = true;
+        if(component == null){
+            cacheHit = false;
+            if(!source.isSourceUsed()){
+                source.setSourceUsed(true);
+                renderTemplateCellWithData(source);
+                component = source;
+                if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
+                    WXLogUtils.d(TAG, template + " onCreateViewHolder source");
+                }
+            }
+        }
+        if(component == null) {
+            long start = System.currentTimeMillis();
+            component = (WXCell) copyComponentFromSourceCell(source);
+            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
+                WXLogUtils.d(TAG, template + " onCreateViewHolder copy used " + (System.currentTimeMillis() - start));
+            }
+        }
+        if(component.isLazy() || component.getHostView() == null) {
+            doCreateCellViewBindData(component, template, false);
+            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
+                WXLogUtils.d(TAG, template + " onCreateViewHolder  cache hit " + cacheHit   + " view not idle init");
+            }
+        }else{
+            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
+                WXLogUtils.d(TAG, template + " onCreateViewHolder  cache hit " + cacheHit + " view idle init " + component.hashCode()
+                 + "  " + source.hashCode());
+            }
+        }
+        TemplateViewHolder templateViewHolder = new TemplateViewHolder(this, component, viewType);
+        return  templateViewHolder;
+    }
+
+
+
+    /**
+     * @param position
+     * when template not send, return an invalid id, use empty view holder.
+     * when template has sended, use real template id to refresh view, use real view holder.
+     * */
+    @Override
+    public int getItemViewType(int position) {
+        String template = getTemplateKey(position);
+        int type =  mTemplateViewTypes.indexOfKey(template);
+        if(type < 0){
+            type = mTemplateViewTypes.indexOfKey(EMPTY_HOLDER_TEMPLATE_KEY);
+        }
+        return type;
+    }
+
+
+    /**
+     * create code context for render component and do render
+     * */
+    private List<WXComponent> doRenderTemplate(WXCell cell, int position){
+        this.cellRenderContext.clear();
+        Object item = cellDataManager.listData.get(position);
+        CellRenderState cellRenderState = cellDataManager.getRenderState(position);
+        cellRenderContext.renderState = cellRenderState;
+        cellRenderContext.templateList = this;
+        cellRenderContext.position = position;
+
+        ArrayStack stack = cellRenderContext.stack;
+        Map map = cellRenderContext.map;
+        if(cellDataManager.listData != null){
+            stack.push(map);
+            map.put(listDataKey, cellDataManager.listData);
+            if(!TextUtils.isEmpty(listDataIndexKey)) {
+                map.put(listDataIndexKey, new PositionRef(cellRenderState));
+            }
+            if(!TextUtils.isEmpty(listDataItemKey)) {
+                map.put(listDataItemKey, item);
+            }else{
+                stack.push(item);
+            }
+        }
+        if(cellRenderState.itemId <= 0){
+            getItemId(position);
+        }
+        List<WXComponent> updates = Statements.doRender(cell, this.cellRenderContext);
+        if(cellRenderState.isDirty()){
+            cellRenderState.resetDirty();
+        }
+        return  updates;
+    }
+
+    public ArrayStack copyStack(CellRenderContext context, ArrayStack stack){
+        ArrayStack onceStack = new ArrayStack();
+        for(int index=0;  index <  stack.size(); index++) {
+            Object value = stack.get(index);
+            if(value instanceof  Map){
+                value  = new HashMap((Map) value);
+            }
+            onceStack.push(value);
+        }
+        return onceStack;
+    }
+
+
+    /**
+     * return tepmlate key for position
+     * */
+    public String getTemplateKey(int position){
+        Object data =  safeGetListData(position);
+        return getTemplateKey(data);
+    }
+
+    /**
+     * return template key for position never be null
+     * */
+    public String getTemplateKey(Object data){
+        String template = null;
+        if(data instanceof  JSONObject) {
+            template = ((JSONObject)data).getString(listDataTemplateKey);
+        }
+        if(TextUtils.isEmpty(template)){
+            if(defaultTemplateCell != null){
+                template  = defaultTemplateKey;
+            }else {
+                template = "";
+            }
+        }
+        return  template;
+    }
+
+    /**
+     * get source template
+     * */
+    public WXCell getSourceTemplate(int position){
+        String template = getTemplateKey(position);
+        return mTemplateSources.get(template);
+    }
+
+
+
+    /**
+     * get template key from cell; -1 for  cann't find  type
+     * */
+    private int getCellTemplateItemType(WXCell cell){
+        if(cell == null){
+            return  -1;
+        }
+        if(cell.getAttrs() != null){
+            Object templateId = cell.getAttrs().get(Constants.Name.Recycler.SLOT_TEMPLATE_CASE);
+            String template = WXUtils.getString(templateId, null);
+            if(cell == defaultTemplateCell){
+                template = defaultTemplateKey;
+            }
+            int type =  mTemplateViewTypes.indexOfKey(template);
+            if(type < 0){
+                return -1;
+            }
+            return  type;
+        }
+        return  0;
+    }
+
+    @Override
+    public int getItemCount() {
+        if(!hasLayoutDone){
+            return 0;
+        }
+        if(!hasAppendTreeDone){
+            return 0;
+        }
+        if(cellDataManager.listData == null){
+            return  0;
+        }
+        if(mTemplateViewTypes == null || mTemplateViewTypes.size() <= 1){
+            return 0;
+        }
+        if(mTemplateSources == null || mTemplateSources.size() == 0){
+            return  0;
+        }
+        return cellDataManager.listData.size();
+    }
+
+    @Override
+    public boolean onFailedToRecycleView(TemplateViewHolder holder) {
+        return false;
+    }
+
+
+    /**
+     * @param position
+     * when template not send by javascript, return an invalid id, force  use empty view holder.
+     * when template has sended by javascript, use real template id to refresh view, use real view holder.
+     * */
+    @Override
+    public long getItemId(int position) {
+        CellRenderState renderState = cellDataManager.getRenderState(position);
+        if(renderState.itemId <=  0){
+            String template = getTemplateKey(position);
+            if(TextUtils.isEmpty(template)){
+                return RecyclerView.NO_ID;
+            }
+            Object data = safeGetListData(position);
+            if(data instanceof  JSONObject && ((JSONObject)data).containsKey("keyItemId")){
+                renderState.itemId =  ((JSONObject)data).getLongValue("keyItemId");
+            }else{
+                long id = Math.abs(data.hashCode());
+                long itemId = (id<< 24) + position;
+                renderState.itemId = itemId;
+            }
+        }
+        return renderState.itemId;
+    }
+
+    @Override
+    public void onBeforeScroll(int dx, int dy) {
+        if(mStickyHelper != null){
+            mStickyHelper.onBeforeScroll(dx, dy);
+        }
+    }
+
+    @Override
+    public void onLoadMore(int offScreenY) {
+        try {
+            String offset = getAttrs().getLoadMoreOffset();
+
+            if (TextUtils.isEmpty(offset)) {
+                offset = "0";
+            }
+            float offsetParsed = WXViewUtils.getRealPxByWidth(Integer.parseInt(offset),getInstance().getInstanceViewPortWidth());
+
+            if (offScreenY <= offsetParsed && cellDataManager.listData != null) {
+                if (mListCellCount != cellDataManager.listData.size()
+                        || mForceLoadmoreNextTime) {
+                    fireEvent(Constants.Event.LOADMORE);
+                    mListCellCount = cellDataManager.listData.size();
+                    mForceLoadmoreNextTime = false;
+                }
+            }
+        } catch (Exception e) {
+            if (WXEnvironment.isApkDebugable()){
+                WXLogUtils.d(TAG + " onLoadMore : ", e);
+            }
+        }
+    }
+
+    /**
+     *
+     * first fire appear event.
+     * */
+    @Override
+    public void notifyAppearStateChange(int firstVisible, int lastVisible, int directionX, int directionY) {
+        if(mAppearHelpers == null
+                || mAppearHelpers.size() <= 0){
+            return;
+        }
+        if(mAppearChangeRunnable != null) {
+            getHostView().removeCallbacks(mAppearChangeRunnable);
+            mAppearChangeRunnable = null;
+        }
+        String direction = directionY > 0 ? Constants.Value.DIRECTION_UP :
+                directionY < 0 ? Constants.Value.DIRECTION_DOWN : null;
+        if (getOrientation() == Constants.Orientation.HORIZONTAL && directionX != 0) {
+            direction = directionX > 0 ? Constants.Value.DIRECTION_LEFT : Constants.Value.DIRECTION_RIGHT;
+        }
+        RecyclerView recyclerView = getHostView().getInnerView();
+        for(int position=firstVisible; position<=lastVisible; position++){
+            int type = getItemViewType(position);
+            List<AppearanceHelper> helpers = mAppearHelpers.get(type);
+            if(helpers == null){
+                continue;
+            }
+            for(AppearanceHelper helper : helpers){
+                if(!helper.isWatch()){
+                    continue;
+                }
+                TemplateViewHolder itemHolder = (TemplateViewHolder) recyclerView.findViewHolderForAdapterPosition(position);
+                if(itemHolder == null || itemHolder.getComponent() == null){
+                    break;
+                }
+                List<WXComponent> childListeners = findChildListByRef(itemHolder.getComponent(), helper.getAwareChild().getRef());
+                if(childListeners == null || childListeners.size() == 0){
+                    break;
+                }
+
+                Map<String, Map<Integer, List<Object>>> disAppearList = mDisAppearWatchList.get(position);
+                if(disAppearList == null){
+                    disAppearList = new ArrayMap<>();
+                    mDisAppearWatchList.put(position, disAppearList);
+                }
+
+                Map<Integer, List<Object>> componentDisAppearList = disAppearList.get(helper.getAwareChild().getRef());
+                if(componentDisAppearList == null){
+                    componentDisAppearList = new ArrayMap<>();
+                    disAppearList.put(helper.getAwareChild().getRef(), componentDisAppearList);
+                }
+
+                for(int m=0; m<childListeners.size(); m++){
+                    WXComponent childLisener = childListeners.get(m);
+                    if(childLisener.getHostView() == null){
+                        continue;
+                    }
+                    boolean appear = helper.isViewVisible(childLisener.getHostView());
+                    int key = childLisener.getHostView().hashCode();
+                    if(appear){
+                        if(!componentDisAppearList.containsKey(key)){
+                            childLisener.notifyAppearStateChange(Constants.Event.APPEAR, direction);
+                            List<Object> eventArgs = null;
+                            if(childLisener.getEvents() != null
+                                    && childLisener.getEvents().getEventBindingArgsValues() != null
+                                    && childLisener.getEvents().getEventBindingArgsValues().get(Constants.Event.DISAPPEAR) != null){
+                                eventArgs = childLisener.getEvents().getEventBindingArgsValues().get(Constants.Event.DISAPPEAR);
+                            }
+                            componentDisAppearList.put(key, eventArgs);
+                        }
+                    }else{
+                        if(componentDisAppearList.containsKey(key)){
+                            childLisener.notifyAppearStateChange(Constants.Event.DISAPPEAR, direction);
+                            componentDisAppearList.remove(key);
+                        }
+                    }
+                }
+            }
+        }
+
+        //handle disappear event, out of position
+        int count = getItemCount();
+        for (int position=0; position<count; position++){
+            if(position >= firstVisible && position <= lastVisible){
+                position = lastVisible + 1;
+                continue;
+            }
+            Map<String, Map<Integer, List<Object>>> map = mDisAppearWatchList.get(position);
+            if(map == null){
+                continue;
+            }
+            WXCell template = mTemplateSources.get(getTemplateKey(position));
+            if(template == null){
+                return;
+            }
+            Set<Map.Entry<String, Map<Integer, List<Object>>>> cellWatcherEntries = map.entrySet();
+            for(Map.Entry<String,Map<Integer, List<Object>>> cellWatcherEntry : cellWatcherEntries){
+                String ref = cellWatcherEntry.getKey();
+                WXComponent component = findChildByRef(template, ref);
+                if(component == null){
+                    continue;
+                }
+                Map<Integer, List<Object>> eventWatchers = cellWatcherEntry.getValue();
+                if(eventWatchers == null || eventWatchers.size() == 0){
+                    continue;
+                }
+                WXEvent events = component.getEvents();
+                Set<Map.Entry<Integer, List<Object>>> eventWatcherEntries = eventWatchers.entrySet();
+                for(Map.Entry<Integer, List<Object>> eventWatcherEntry : eventWatcherEntries){
+                    events.putEventBindingArgsValue(Constants.Event.DISAPPEAR, eventWatcherEntry.getValue());
+                    component.notifyAppearStateChange(Constants.Event.DISAPPEAR, direction);
+                }
+                eventWatchers.clear();
+            }
+            mDisAppearWatchList.remove(position);
+        }
+    }
+
+
+    private Object safeGetListData(int position){
+        try{
+            return cellDataManager.listData.get(position);
+        }catch (Exception e){return  JSONObject.parseObject("{}");}
+    }
+
+    public void  notifyUpdateList(){
+        if(getHostView() == null
+                || getHostView().getInnerView() == null
+                || listUpdateRunnable == null){
+            return;
+        }
+        if(Looper.getMainLooper().getThread().getId() != Thread.currentThread().getId()){
+            getHostView().removeCallbacks(listUpdateRunnable);
+            getHostView().post(listUpdateRunnable);
+        }else{
+            listUpdateRunnable.run();
+        }
+    }
+
+    private int calcContentSize() {
+        int totalHeight = 0;
+        if(cellDataManager.listData == null){
+            return totalHeight;
+        }
+        for (int i = 0; i < cellDataManager.listData.size(); i++) {
+            WXCell child = getSourceTemplate(i);
+            if (child != null) {
+                totalHeight += child.getLayoutHeight();
+            }
+        }
+        return totalHeight;
+    }
+
+    public int calcContentOffset(RecyclerView recyclerView) {
+        RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
+        if (layoutManager instanceof LinearLayoutManager) {
+            int firstVisibleItemPosition = ((LinearLayoutManager) layoutManager).findFirstVisibleItemPosition();
+            int offset = 0;
+            for (int i=0;i<firstVisibleItemPosition;i++) {
+                WXCell cell = getSourceTemplate(i);
+                if(cell == null){
+                    continue;
+                }
+                offset -= cell.getLayoutHeight();
+            }
+
+            if (layoutManager instanceof GridLayoutManager) {
+                int spanCount = ((GridLayoutManager) layoutManager).getSpanCount();
+                offset = offset / spanCount;
+            }
+            View firstVisibleView = layoutManager.findViewByPosition(firstVisibleItemPosition);
+            if(firstVisibleView != null) {
+                offset += firstVisibleView.getTop();
+            }
+            return offset;
+        } else if (layoutManager instanceof StaggeredGridLayoutManager) {
+            int spanCount = ((StaggeredGridLayoutManager) layoutManager).getSpanCount();
+            int firstVisibleItemPosition = ((StaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(null)[0];
+            int offset = 0;
+            for (int i=0;i<firstVisibleItemPosition;i++) {
+                WXCell cell = getSourceTemplate(i);
+                if(cell == null){
+                    continue;
+                }
+                offset -= cell.getLayoutHeight();
+            }
+            offset = offset / spanCount;
+
+            View firstVisibleView = layoutManager.findViewByPosition(firstVisibleItemPosition);
+            if(firstVisibleView != null) {
+                offset += firstVisibleView.getTop();
+            }
+            return offset;
+        }
+        return -1;
+    }
+
+    /**
+     * find certain class type parent
+     * */
+    public WXComponent findParentType(WXComponent component, Class type){
+        if(type.isAssignableFrom(component.getClass())){
+            return component;
+        }
+        if(component.getParent() != null) {
+            findTypeParent(component.getParent(), type);
+        }
+        return  null;
+    }
+
+
+    /**
+     * find child by ref
+     * */
+    public WXComponent findChildByRef(WXComponent component, String ref){
+        if(ref.equals(component.getRef())){
+            return component;
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            for(int i=0; i<container.getChildCount(); i++){
+                WXComponent child = findChildByRef(container.getChild(i), ref);
+                if(child != null){
+                    return  child;
+                }
+            }
+        }
+        return  null;
+    }
+
+    /**
+     * find child list, has same ref
+     * */
+    public List<WXComponent> findChildListByRef(WXComponent component, String ref){
+        WXComponent child = findChildByRef(component, ref);
+        if(child == null){
+            return  null;
+        }
+        List<WXComponent> componentList = new ArrayList<>();
+        WXVContainer container = child.getParent();
+        if(container != null && (!(container instanceof WXRecyclerTemplateList))){
+            for(int i=0; i<container.getChildCount(); i++){
+                WXComponent element = container.getChild(i);
+                if(ref.equals(element.getRef())){
+                    componentList.add(element);
+                }
+            }
+        }else{
+            componentList.add(child);
+        }
+        return  componentList;
+    }
+
+
+
+    /**
+     * find child by ref
+     * */
+    public WXComponent findChildByAttrsRef(WXComponent component, String ref){
+        if(component.getAttrs() != null && ref.equals(component.getAttrs().get(TemplateDom.ATTRS_KEY_REF))){
+            return component;
+        }
+        if(component instanceof WXVContainer){
+            WXVContainer container = (WXVContainer) component;
+            for(int i=0; i<container.getChildCount(); i++){
+                WXComponent child = findChildByAttrsRef(container.getChild(i), ref);
+                if(child != null){
+                    return  child;
+                }
+            }
+        }
+        return  null;
+    }
+
+
+
+    /**
+     * @param  template  template name
+     * get cell template component from cache, if cell component not load
+     * start load cell template
+     * */
+    private WXCell getCellTemplateFromCache(final String template){
+        TemplateCache cache = mTemplatesCache.get(template);
+        WXCell component =  null;
+        if(cache != null && cache.cells != null && cache.cells.size() > 0){
+            component = cache.cells.poll();
+        }
+        if(cache == null ||  !cache.isLoadIng){
+            if(cache == null){
+                cache = new TemplateCache();
+                mTemplatesCache.put(template, cache);
+            }
+            cache.isLoadIng = true;
+            WXCell source = mTemplateSources.get(template);
+            if(source != null){
+                boolean allowPreload = WXUtils.getBoolean(source.getAttrs().get("preload"), true);
+                if(allowPreload) {
+                    AsyncCellLoadTask asyncCellLoadTask = new AsyncCellLoadTask(template, source, this);
+                    asyncCellLoadTask.startTask();
+                }
+            }
+        }
+        return  component;
+    }
+
+    /**
+     * copy cell component from source, init render data, and return source
+     * if none data, return null
+     * */
+    public WXComponent copyComponentFromSourceCell(WXCell cell){
+        renderTemplateCellWithData(cell);
+        WXCell component = (WXCell) Statements.copyComponentTree(cell);
+        return component;
+    }
+
+    /**
+     *  render  init with  cell with one data,
+     *  if template has already render with data, done nothing
+     *  @param  cell
+     * */
+    private synchronized void renderTemplateCellWithData(WXCell cell){
+        if(cell.getRenderData() == null){
+            if(cellDataManager.listData != null && cellDataManager.listData.size() > 0){
+                synchronized (this){
+                    if(cell.getRenderData() == null){
+                        Statements.parseStatementsToken(cell);
+                        for(int i = 0; i< cellDataManager.listData.size(); i++){
+                            if(cell == getSourceTemplate(i)){
+                                Object data = cellDataManager.listData.get(i);
+                                doRenderTemplate(cell, i);
+                                Layouts.doLayoutSync(cell, getLayoutWidth(), getLayoutHeight());
+                                cell.setRenderData(data);
+                                break;
+                            }
+                        }
+                    }
+                }
+            }
+        }
+    }
+
+
+    /**
+     * create view for lazy cell and bind data
+     * */
+    public static void doCreateCellViewBindData(WXCell component, String template, boolean inPreload){
+        if(component.isLazy() || component.getHostView() == null){
+            long start = System.currentTimeMillis();
+            Statements.initLazyComponent(component, null);
+            if(WXEnvironment.isOpenDebugLog() && ENABLE_TRACE_LOG) {
+                WXLogUtils.d(TAG, " doCreateCellViewBindData " + template + " in preload "+ inPreload + " used " + (System.currentTimeMillis() - start));
+            }
+        }
+    }
+
+    public ScrollStartEndHelper getScrollStartEndHelper() {
+        if(mScrollStartEndHelper == null){
+            mScrollStartEndHelper = new ScrollStartEndHelper(this);
+        }
+        return mScrollStartEndHelper;
+    }
+
+    public int getTemplateCacheSize() {
+        return templateCacheSize;
+    }
+
+    public ConcurrentHashMap<String, TemplateCache> getTemplatesCache() {
+        if(mTemplatesCache == null){
+            mTemplatesCache = new ConcurrentHashMap<>();
+        }
+        return mTemplatesCache;
+    }
+
+
+    public CellDataManager getCellDataManager() {
+        return cellDataManager;
+    }
+
+
+    private JSONArray parseListDataToJSONArray(Object value){
+        try{
+            if(value instanceof  JSONArray){
+                return (JSONArray) value;
+            }
+            if(value instanceof String){
+                JSONArray array = JSONArray.parseArray(getAttrs().get(Constants.Name.Recycler.LIST_DATA).toString());
+                return array;
+            }
+        }catch (Exception e){
+            WXLogUtils.e(TAG, "parseListDataException" + e.getMessage());
+        }
+        return new JSONArray();
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/jni/NativeRenderLayoutDirection.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/jni/NativeRenderLayoutDirection.java
new file mode 100644
index 0000000..1fdde01
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/jni/NativeRenderLayoutDirection.java
@@ -0,0 +1,25 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template.jni;
+
+public class NativeRenderLayoutDirection {
+    public static final int inherit = 0;
+    public static final int ltr = 1;
+    public static final int rtl = 2;
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/jni/NativeRenderObjectUtils.java b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/jni/NativeRenderObjectUtils.java
new file mode 100644
index 0000000..6031a9f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/list/template/jni/NativeRenderObjectUtils.java
@@ -0,0 +1,77 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.list.template.jni;
+
+import org.apache.weex.base.CalledByNative;
+import org.apache.weex.ui.component.WXComponent;
+
+/**
+ * Created by furture on 2018/5/3.
+ */
+
+public class NativeRenderObjectUtils {
+
+
+    /**
+     * getRenderObject
+     * */
+    public static native long nativeGetRenderObject(String instanceId, String ref);
+
+    /**
+     * render object layout
+     * */
+    public static native void nativeUpdateRenderObjectStyle(long ptr, String key, String value);
+    public static native void nativeUpdateRenderObjectAttr(long ptr, String key, String value);
+
+    /**
+     * copy render object
+     * */
+    public static native long nativeCopyRenderObject(long ptr);
+
+    /**
+     * layout render object
+     * */
+    public static native int nativeLayoutRenderObject(long ptr, float width, float height);
+
+    public static native int nativeRenderObjectGetLayoutDirectionFromPathNode(long ptr);
+    /**
+     * get child length
+     * */
+    public static native void nativeAddChildRenderObject(long parent, long child);
+
+    /**
+     * get component, tranverse child and update component
+     * */
+    public static native boolean nativeRenderObjectHasNewLayout(long ptr);
+    public static native int nativeRenderObjectChildCount(long ptr);
+    public static native long nativeRenderObjectGetChild(long ptr, int index);
+    public static native void nativeRenderObjectUpdateComponent(long ptr, WXComponent component);
+    public static native void nativeRenderObjectChildWaste(long ptr, boolean waster);
+
+
+    /**
+     * component size
+     * */
+    @CalledByNative
+    public static void updateComponentSize(WXComponent component, float top, float bottom, float left, float right, float height, float width){
+        component.updateDemission(top, bottom, left, right, height, width);
+        component.applyLayoutOnly();
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/OnActivePseudoListner.java b/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/OnActivePseudoListner.java
new file mode 100644
index 0000000..8585fe6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/OnActivePseudoListner.java
@@ -0,0 +1,26 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.pesudo;
+
+/**
+ * Created by sospartan on 05/01/2017.
+ */
+public interface OnActivePseudoListner {
+  void updateActivePseudo(boolean isSet);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/PesudoStatus.java b/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/PesudoStatus.java
new file mode 100644
index 0000000..0a9af49
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/PesudoStatus.java
@@ -0,0 +1,132 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.pesudo;
+
+import android.support.annotation.Nullable;
+import android.support.v4.util.ArrayMap;
+
+import org.apache.weex.common.Constants;
+
+import java.util.Map;
+import org.apache.weex.common.Constants.PSEUDO;
+
+/**
+ * Created by sospartan on 05/01/2017.
+ */
+
+public class PesudoStatus {
+
+  /**
+   * See {@link PSEUDO}
+   */
+  private int[] mStatuses = new int[4];
+
+  private static final int UNSET = 0;
+  private static final int SET = 1;
+
+  static final int CLASS_ACTIVE = 0;
+  static final int CLASS_FOCUS = 1;
+  static final int CLASS_ENABLED = 2;
+  static final int CLASS_DISABLED = 3;
+
+  public PesudoStatus(){
+    for (int i = 0; i < mStatuses.length; i++) {
+        mStatuses[i] = UNSET;
+    }
+  }
+
+  /**
+   *
+   * @param clzName See {@link PSEUDO}
+   * @param status
+   */
+  public void setStatus(String clzName,boolean status){
+    switch (clzName){
+      case Constants.PSEUDO.ACTIVE:
+        setStatus(PesudoStatus.CLASS_ACTIVE,status);
+        break;
+      case Constants.PSEUDO.DISABLED:
+        setStatus(PesudoStatus.CLASS_DISABLED,status);
+        break;
+      case Constants.PSEUDO.ENABLED:
+        setStatus(PesudoStatus.CLASS_ENABLED,status);
+        break;
+      case Constants.PSEUDO.FOCUS:
+        setStatus(PesudoStatus.CLASS_FOCUS,status);
+        break;
+    }
+  }
+
+  void setStatus(int clz,boolean status){
+    mStatuses[clz] = status?SET:UNSET;
+  }
+
+  public boolean isSet(int clz){
+    return mStatuses[clz] == SET;
+  }
+
+  public @Nullable String getStatuses(){
+    StringBuilder sb = new StringBuilder();
+    if(isSet(CLASS_ACTIVE)){
+      sb.append(Constants.PSEUDO.ACTIVE);
+    }
+    if(isSet(CLASS_DISABLED)){
+      sb.append(Constants.PSEUDO.DISABLED);
+    }
+    //enabled is ignored
+
+    if(isSet(CLASS_FOCUS) && !isSet(CLASS_DISABLED)){
+      sb.append(Constants.PSEUDO.FOCUS);
+    }
+    return sb.length()==0?null:sb.toString();
+  }
+
+  public Map<String,Object> updateStatusAndGetUpdateStyles(String clzName,
+                                                           boolean status,
+                                                           Map<String, Map<String,Object>> pesudoStyles,
+                                                           Map<String,Object> originalStyles){
+    String prevStatusesStr = getStatuses();//before change
+    setStatus(clzName,status);
+    String statusesStr = getStatuses();//after change
+
+    Map<String,Object> updateStyles = pesudoStyles.get(statusesStr);
+    Map<String,Object> prevUpdateStyles = pesudoStyles.get(prevStatusesStr);
+
+    /**
+     * NEW INSTANCE, DO NOT USE MAP OBJECT FROM pesudoStyles
+     */
+    Map<String,Object> resultStyles = new ArrayMap<>();
+    if(prevUpdateStyles != null){
+      resultStyles.putAll(prevUpdateStyles);
+    }
+
+    //reset
+    for (String key : resultStyles.keySet()) {
+      resultStyles.put(key, originalStyles.containsKey(key) ? originalStyles.get(key) : "");
+    }
+
+    //apply new update
+    if(updateStyles != null) {
+      for (Map.Entry<String, Object> entry : updateStyles.entrySet()) {
+        resultStyles.put(entry.getKey(), entry.getValue());
+      }
+    }
+    return resultStyles;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/TouchActivePseudoListener.java b/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/TouchActivePseudoListener.java
new file mode 100644
index 0000000..eb92540
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/pesudo/TouchActivePseudoListener.java
@@ -0,0 +1,50 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.component.pesudo;
+
+import android.annotation.SuppressLint;
+import android.view.MotionEvent;
+import android.view.View;
+
+/**
+ * Created by sospartan on 05/01/2017.
+ */
+public class TouchActivePseudoListener implements View.OnTouchListener {
+  private OnActivePseudoListner mOnActivePseudoListner;
+  private boolean mIsConsumeOnTouch;
+
+  public TouchActivePseudoListener(OnActivePseudoListner l, boolean consumeInTouch) {
+    mOnActivePseudoListner = l;
+    mIsConsumeOnTouch = consumeInTouch;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouch(View v, MotionEvent event) {
+    int action = event.getAction();
+    if (mOnActivePseudoListner != null) {
+      if (action == MotionEvent.ACTION_DOWN || action == MotionEvent.ACTION_POINTER_DOWN) {
+        mOnActivePseudoListner.updateActivePseudo(true);
+      } else if (action == MotionEvent.ACTION_CANCEL || action == MotionEvent.ACTION_UP || action == MotionEvent.ACTION_POINTER_UP) {
+        mOnActivePseudoListner.updateActivePseudo(false);
+      }
+    }
+    return mIsConsumeOnTouch;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/WXRichText.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/WXRichText.java
new file mode 100755
index 0000000..0e8180a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/WXRichText.java
@@ -0,0 +1,159 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext;
+
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+import android.text.Spannable;
+import android.text.SpannableStringBuilder;
+import android.text.Spanned;
+import android.text.SpannedString;
+import android.text.TextUtils;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.layout.measurefunc.TextContentBoxMeasurement;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXText;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.component.richtext.node.RichTextNode;
+import org.apache.weex.ui.component.richtext.node.RichTextNodeManager;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+
+public class WXRichText extends WXText {
+  private List<RichTextNode> nodes = new LinkedList<>();
+
+  static class RichTextContentBoxMeasurement extends TextContentBoxMeasurement {
+
+    public RichTextContentBoxMeasurement(WXComponent component) {
+      super(component);
+    }
+
+    @NonNull
+    @Override
+    protected Spanned createSpanned(String text) {
+      if(!TextUtils.isEmpty(text)) {
+        if (mComponent.getInstance() != null & mComponent.getInstance().getUIContext() != null &&
+                !TextUtils.isEmpty(mComponent.getInstanceId())) {
+          Spannable spannable = RichTextNode.parse(
+                  mComponent.getInstance().getUIContext(),
+                  mComponent.getInstanceId(),
+                  mComponent.getRef(),
+                  text);
+          updateSpannable(spannable, RichTextNode.createSpanFlag(0));
+          return spannable;
+        } else {
+          return new SpannedString("");
+        }
+      }
+      else {
+        Spannable spannable = ((WXRichText)mComponent).toSpan();
+        updateSpannable(spannable, RichTextNode.createSpanFlag(0));
+        return spannable;
+        }
+    }
+  }
+
+  public static class Creator implements ComponentCreator {
+
+    public WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+      return new WXRichText(instance, parent, basicComponentData);
+    }
+  }
+
+  public WXRichText(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+    setContentBoxMeasurement(new RichTextContentBoxMeasurement(this));
+  }
+  public void AddChildNode(String ref, String nodeType,String parentRef, Map<String,String> styles,Map<String,String> attrs) {
+    if(getInstance() != null && getInstance().getUIContext() != null && !TextUtils.isEmpty(getInstanceId()) &&
+            !TextUtils.isEmpty(ref) && !TextUtils.isEmpty(nodeType)) {
+      RichTextNode child = RichTextNodeManager.createRichTextNode(getInstance().getUIContext(), getInstanceId(), getRef(), ref, nodeType, styles, attrs);
+      if (TextUtils.isEmpty(parentRef)) {
+        nodes.add(child);
+      } else {
+        RichTextNode parent = findRichNode(parentRef);
+        if (parent != null) {
+          parent.addChildNode(child);
+        }
+      }
+    }
+  }
+  private Spannable toSpan(){
+    SpannableStringBuilder spannableStringBuilder = new SpannableStringBuilder();
+    if(nodes != null && !nodes.isEmpty()){
+      for(RichTextNode node:nodes){
+        spannableStringBuilder.append(node.toSpan(1));
+      }
+    }
+    return spannableStringBuilder;
+  }
+
+  public void removeChildNode(String parentRef,String ref) {
+    if (nodes != null && !nodes.isEmpty()) {
+      if (parentRef.equals("")) {
+        for (RichTextNode node : nodes) {
+          if (TextUtils.equals(node.getRef(), ref)) {
+            nodes.remove(node);
+          }
+        }
+      } else {
+        RichTextNode parent = findRichNode(parentRef);
+        if (parent != null) {
+          parent.removeChildNode(ref);
+        }
+      }
+    }
+  }
+  public void updateChildNodeStyles(String ref,Map<String,Object> styles){
+    RichTextNode node = findRichNode(ref);
+    if(node != null){
+      node.updateStyles(styles);
+    }
+  }
+  public void updateChildNodeAttrs(String ref,Map<String,Object> attrs){
+    RichTextNode node = findRichNode(ref);
+    if(node != null){
+      node.updateAttrs(attrs);
+    }
+  }
+  private RichTextNode findRichNode(String ref){
+    if(!TextUtils.isEmpty(ref)) {
+      RichTextNode theNode;
+      if (nodes != null && !nodes.isEmpty()) {
+        for (RichTextNode node : nodes) {
+          if ((theNode = node.findRichNode(ref)) != null)
+            return theNode;
+        }
+      }
+    }
+    return null;
+  }
+
+  @Override
+  protected WXRichTextView initComponentHostView(@NonNull Context context) {
+    return new WXRichTextView(context);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/WXRichTextView.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/WXRichTextView.java
new file mode 100644
index 0000000..7ca9e8b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/WXRichTextView.java
@@ -0,0 +1,116 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.graphics.drawable.Drawable;
+import android.text.Layout;
+import android.text.Selection;
+import android.text.Spannable;
+import android.text.Spanned;
+import android.text.style.ClickableSpan;
+import android.view.MotionEvent;
+import android.widget.TextView;
+
+import org.apache.weex.ui.component.richtext.span.ImgSpan;
+import org.apache.weex.ui.view.WXTextView;
+
+public class WXRichTextView extends WXTextView {
+
+  public WXRichTextView(Context context) {
+    super(context);
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent event) {
+    boolean superResult = super.onTouchEvent(event);
+    boolean handled = false;
+    if (isEnabled() && getTextLayout() != null && getText() instanceof Spannable) {
+      Spannable spannable = (Spannable) getText();
+      handled = updateSelection(event, spannable);
+    }
+    return handled || superResult;
+  }
+
+  @Override
+  protected boolean verifyDrawable(Drawable who) {
+    super.verifyDrawable(who);
+    return true;
+  }
+
+  @Override
+  public void setTextLayout(Layout layout) {
+    super.setTextLayout(layout);
+    if (layout.getText() instanceof Spanned) {
+      Spanned spanned = (Spanned) layout.getText();
+      ImgSpan[] imgSpan = spanned.getSpans(0, spanned.length(), ImgSpan.class);
+      if (imgSpan != null) {
+        for (ImgSpan span : imgSpan) {
+          span.setView(this);
+        }
+      }
+    }
+  }
+
+  /**
+   * Mostly copied from
+   * {@link android.text.method.LinkMovementMethod#onTouchEvent(TextView, Spannable, MotionEvent)}.
+   */
+  private boolean updateSelection(MotionEvent event, Spannable buffer) {
+    int action = event.getActionMasked();
+
+    if (action == MotionEvent.ACTION_UP ||
+        action == MotionEvent.ACTION_DOWN) {
+      int x = (int) event.getX();
+      int y = (int) event.getY();
+
+      x -= getPaddingLeft();
+      y -= getPaddingTop();
+
+      x += getScrollX();
+      y += getScrollY();
+
+      Layout layout = getTextLayout();
+      int line = layout.getLineForVertical(y);
+      int off = layout.getOffsetForHorizontal(line, x);
+
+      ClickableSpan[] link = buffer.getSpans(off, off, ClickableSpan.class);
+
+      if (link.length != 0) {
+        if (action == MotionEvent.ACTION_UP) {
+          link[0].onClick(this);
+        } else {
+          Selection.setSelection(buffer,
+                                 buffer.getSpanStart(link[0]),
+                                 buffer.getSpanEnd(link[0]));
+        }
+
+        return true;
+      } else {
+        Selection.removeSelection(buffer);
+      }
+    }
+
+    return false;
+  }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/ANode.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/ANode.java
new file mode 100755
index 0000000..5ecd963
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/ANode.java
@@ -0,0 +1,79 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.node;
+
+import android.content.Context;
+import android.text.SpannableStringBuilder;
+
+import org.apache.weex.ui.component.richtext.span.ASpan;
+import org.apache.weex.ui.component.richtext.span.ItemClickSpan;
+
+import java.util.Map;
+
+class ANode extends RichTextNode {
+
+  static class ANodeCreator implements RichTextNodeCreator<ANode> {
+
+    @Override
+    public ANode createRichTextNode(Context context, String instanceId, String componentRef) {
+      return new ANode(context, instanceId, componentRef);
+    }
+    @Override
+    public ANode createRichTextNode(Context context,String instanceId,String componentRef,String ref,
+                                      Map<String,Object> styles, Map<String,Object> attrs){
+      return new ANode(context,instanceId,componentRef,ref,styles,attrs);
+    }
+
+  }
+
+  public static final String NODE_TYPE = "a";
+  public static final String HREF = "href";
+
+  private ANode(Context context, String instanceId, String componentRef) {
+    super(context, instanceId, componentRef);
+  }
+  private ANode(Context context, String instanceId, String componentRef, String ref, Map<String,Object> styles, Map<String,Object> attrs) {
+    super(context, instanceId, componentRef, ref, styles, attrs);
+  }
+
+  @Override
+  public String toString() {
+    return "";
+  }
+
+  @Override
+  protected boolean isInternalNode() {
+    return true;
+  }
+
+  @Override
+  protected void updateSpans(SpannableStringBuilder spannableStringBuilder, int level) {
+    super.updateSpans(spannableStringBuilder, level);
+      if (attr != null && attr.containsKey(PSEUDO_REF)) {
+          ItemClickSpan itemClickSpan = new ItemClickSpan(mInstanceId, mComponentRef, attr.get(
+              PSEUDO_REF).toString());
+          spannableStringBuilder.setSpan(itemClickSpan, 0, spannableStringBuilder.length(),
+                  createSpanFlag(level));
+      } else if (attr != null && attr.containsKey(HREF)) {
+          ASpan aSpan = new ASpan(mInstanceId, attr.get(HREF).toString());
+          spannableStringBuilder.setSpan(aSpan, 0, spannableStringBuilder.length(),
+                  createSpanFlag(level));
+      }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/ImgNode.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/ImgNode.java
new file mode 100755
index 0000000..c836297
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/ImgNode.java
@@ -0,0 +1,121 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.node;
+
+import static org.apache.weex.utils.WXViewUtils.getRealPxByWidth;
+
+import android.content.Context;
+import android.graphics.drawable.Drawable;
+import android.net.Uri;
+import android.support.annotation.NonNull;
+import android.text.SpannableStringBuilder;
+import org.apache.weex.WXSDKEngine;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.DrawableStrategy;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.component.richtext.span.ImgSpan;
+import org.apache.weex.ui.component.richtext.span.ItemClickSpan;
+import org.apache.weex.utils.ImgURIUtil;
+import org.apache.weex.utils.WXUtils;
+
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+
+class ImgNode extends RichTextNode {
+
+  static class ImgNodeCreator implements RichTextNodeCreator<ImgNode> {
+
+    @Override
+    public ImgNode createRichTextNode(Context context, String instanceId, String componentRef) {
+      return new ImgNode(context, instanceId, componentRef);
+    }
+    @Override
+    public ImgNode createRichTextNode(Context context,String instanceId,String componentRef,String ref,
+                                       Map<String,Object> styles, Map<String,Object> attrs){
+      return new ImgNode(context,instanceId,componentRef,ref,styles,attrs);
+    }
+  }
+
+  public static final String NODE_TYPE = "image";
+
+  private ImgNode(Context context, String instanceId, String componentRef) {
+    super(context, instanceId, componentRef);
+  }
+  private ImgNode(Context context, String instanceId, String componentRef, String ref, Map<String,Object> styles, Map<String,Object> attrs) {
+    super(context, instanceId, componentRef, ref, styles, attrs);
+  }
+
+  @Override
+  public String toString() {
+    return "\uFEFF";
+  }
+
+  @Override
+  protected boolean isInternalNode() {
+    return false;
+  }
+
+  @Override
+  protected void updateSpans(SpannableStringBuilder spannableStringBuilder, int level) {
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
+    if (WXSDKEngine.getDrawableLoader() != null &&
+        style.containsKey(Constants.Name.WIDTH) &&
+        style.containsKey(Constants.Name.HEIGHT) &&
+        attr.containsKey(Constants.Name.SRC) &&
+        instance != null) {
+      List<Object> spans = new LinkedList<>();
+      spans.add(createImgSpan(instance));
+
+      if (attr.containsKey(PSEUDO_REF)) {
+        spans.add(new ItemClickSpan(mInstanceId, mComponentRef,
+            attr.get(PSEUDO_REF).toString()));
+      }
+
+      for (Object span : spans) {
+        spannableStringBuilder.setSpan(
+            span, 0, spannableStringBuilder.length(), createSpanFlag(level));
+      }
+    }
+  }
+
+  @NonNull
+  private ImgSpan createImgSpan(WXSDKInstance instance) {
+    int width = (int) getRealPxByWidth(WXUtils.getFloat(style.get(Constants.Name.WIDTH)),
+        instance.getInstanceViewPortWidth());
+    int height = (int) getRealPxByWidth(WXUtils.getFloat(style.get(Constants.Name.HEIGHT)),
+        instance.getInstanceViewPortWidth());
+    ImgSpan imageSpan = new ImgSpan(width, height);
+
+    String url = attr.get(Constants.Name.SRC).toString();
+    Uri rewrited = instance.rewriteUri(Uri.parse(url), URIAdapter.IMAGE);
+    if (Constants.Scheme.LOCAL.equals(rewrited.getScheme())) {
+      Drawable localDrawable = ImgURIUtil.getDrawableFromLoaclSrc(mContext, rewrited);
+      imageSpan.setDrawable(localDrawable, false);
+    } else {
+      DrawableStrategy drawableStrategy = new DrawableStrategy();
+      drawableStrategy.width = width;
+      drawableStrategy.height = height;
+      WXSDKEngine.getDrawableLoader().setDrawable(rewrited.toString(), imageSpan, drawableStrategy);
+    }
+    return imageSpan;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNode.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNode.java
new file mode 100755
index 0000000..d0a6e60
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNode.java
@@ -0,0 +1,291 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.node;
+
+import static org.apache.weex.dom.WXStyle.UNSET;
+
+import android.content.Context;
+import android.graphics.Color;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v4.util.ArrayMap;
+import android.text.Spannable;
+import android.text.SpannableString;
+import android.text.SpannableStringBuilder;
+import android.text.Spanned;
+import android.text.TextUtils;
+import android.text.style.AbsoluteSizeSpan;
+import android.text.style.BackgroundColorSpan;
+import android.text.style.ForegroundColorSpan;
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.WXCustomStyleSpan;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXResourceUtils;
+import java.util.ArrayList;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+
+public abstract class RichTextNode {
+
+    public static final String TYPE = "type";
+    public static final String STYLE = "style";
+    public static final String ATTR = "attr";
+    public static final String CHILDREN = "children";
+    public static final String VALUE = Constants.Name.VALUE;
+    public static final String ITEM_CLICK="itemclick";
+    public static final String PSEUDO_REF="pseudoRef";
+    private static final int MAX_LEVEL = Spanned.SPAN_PRIORITY >> Spanned.SPAN_PRIORITY_SHIFT;
+
+    protected final Context mContext;
+    protected final String mInstanceId;
+    protected final String mComponentRef;
+    protected final String mRef;
+    protected Map<String, Object> style;
+    protected Map<String, Object> attr;
+    protected List<RichTextNode> children;
+
+    protected RichTextNode(Context context, String instanceId, String componentRef) {
+        mContext = context;
+        mInstanceId = instanceId;
+        mComponentRef = componentRef;
+        mRef = null;
+    }
+    protected RichTextNode(Context context, String instanceId, String componentRef, String ref, Map<String,Object> styles, Map<String,Object> attrs) {
+        mContext = context;
+        mInstanceId = instanceId;
+        mComponentRef = componentRef;
+        mRef = ref;
+        if(styles != null){
+            style = styles;
+        }
+        else {
+            style = new ArrayMap<>(0);
+        }
+        if (attrs != null) {
+            attr = attrs;
+        } else {
+            attr = new ArrayMap<>(0);
+        }
+        children = new LinkedList<>();
+    }
+
+    public static
+    @NonNull
+    Spannable parse(@NonNull Context context, @NonNull String instanceId, @NonNull String componentRef, String json) {
+        JSONArray jsonArray = JSON.parseArray(json);
+        JSONObject jsonObject;
+        List<RichTextNode> nodes;
+        RichTextNode node;
+        if (jsonArray != null && !jsonArray.isEmpty()) {
+            nodes = new ArrayList<>(jsonArray.size());
+            for (int i = 0; i < jsonArray.size(); i++) {
+                jsonObject = jsonArray.getJSONObject(i);
+                if (jsonObject != null) {
+                    node = RichTextNodeManager.createRichTextNode(context, instanceId, componentRef, jsonObject);
+                    if (node != null) {
+                        nodes.add(node);
+                    }
+                }
+            }
+            return parse(nodes);
+        }
+        return new SpannableString("");
+    }
+
+    public static int createSpanFlag(int level) {
+        return createPriorityFlag(level) | Spanned.SPAN_INCLUSIVE_EXCLUSIVE;
+    }
+
+    @Override
+    public abstract String toString();
+
+    protected abstract boolean isInternalNode();
+
+    public String getRef(){
+        return mRef;
+    }
+
+    final void parse(@NonNull Context context, @NonNull String instanceId, @NonNull String componentRef, JSONObject jsonObject) {
+        JSONObject jsonStyle, jsonAttr, child;
+        JSONArray jsonChildren;
+        RichTextNode node;
+        if ((jsonStyle = jsonObject.getJSONObject(STYLE)) != null) {
+            style = new ArrayMap<>();
+            style.putAll(jsonStyle);
+        } else {
+            style = new ArrayMap<>(0);
+        }
+
+        if ((jsonAttr = jsonObject.getJSONObject(ATTR)) != null) {
+            attr = new ArrayMap<>(jsonAttr.size());
+            attr.putAll(jsonAttr);
+        } else {
+            attr = new ArrayMap<>(0);
+        }
+
+        if ((jsonChildren=jsonObject.getJSONArray(CHILDREN))!=null) {
+            children = new ArrayList<>(jsonChildren.size());
+            for (int i = 0; i < jsonChildren.size(); i++) {
+                child = jsonChildren.getJSONObject(i);
+                node = RichTextNodeManager.createRichTextNode(context, instanceId, componentRef, child);
+                if (node != null) {
+                    children.add(node);
+                }
+            }
+        } else {
+            children = new ArrayList<>(0);
+        }
+    }
+    public void addChildNode(RichTextNode child){
+        if(children == null){
+            children = new LinkedList<>();
+        }
+        if(child != null && isInternalNode()){
+            children.add(child);
+        }
+    }
+    public void removeChildNode(String ref){
+        if(children != null && !children.isEmpty() && !TextUtils.isEmpty(ref)){
+            try {
+                for (RichTextNode child : children) {
+                    if (TextUtils.equals(child.mRef, ref)) {
+                        children.remove(child);
+                    }
+                }
+            }catch(Exception e){
+                WXLogUtils.getStackTrace(e);
+            }
+        }
+    }
+    public void updateStyles(Map<String,Object> styles){
+        if(styles != null && !styles.isEmpty()){
+            style.putAll(styles);
+        }
+    }
+    public void updateAttrs(Map<String,Object> attrs){
+        if(attr != null && !attrs.isEmpty()){
+            attr.putAll(attrs);
+        }
+    }
+
+    protected void updateSpans(SpannableStringBuilder spannableStringBuilder, int level) {
+        WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
+        if (style != null && instance != null) {
+            List<Object> spans = new LinkedList<>();
+
+            WXCustomStyleSpan customStyleSpan = createCustomStyleSpan();
+            if (customStyleSpan != null) {
+                spans.add(customStyleSpan);
+            }
+
+            if (style.containsKey(Constants.Name.FONT_SIZE)) {
+                spans.add(new AbsoluteSizeSpan(WXStyle.getFontSize(style, instance.getInstanceViewPortWidth())));
+            }
+
+            if (style.containsKey(Constants.Name.BACKGROUND_COLOR)) {
+                int color = WXResourceUtils.getColor(style.get(Constants.Name.BACKGROUND_COLOR).toString(),
+                    Color.TRANSPARENT);
+                if (color != Color.TRANSPARENT) {
+                    spans.add(new BackgroundColorSpan(color));
+                }
+            }
+
+            if (style.containsKey(Constants.Name.COLOR)) {
+                spans.add(new ForegroundColorSpan(WXResourceUtils.getColor(WXStyle.getTextColor(style))));
+            }
+
+            int spanFlag = createSpanFlag(level);
+            for (Object span : spans) {
+                spannableStringBuilder.setSpan(span, 0, spannableStringBuilder.length(), spanFlag);
+            }
+        }
+    }
+
+    private static int createPriorityFlag(int level) {
+        return level <= MAX_LEVEL ?
+            (MAX_LEVEL - level) << Spanned.SPAN_PRIORITY_SHIFT :
+            MAX_LEVEL << Spanned.SPAN_PRIORITY_SHIFT;
+    }
+
+
+    private static
+    @NonNull
+    Spannable parse(@NonNull List<RichTextNode> list) {
+        SpannableStringBuilder spannableStringBuilder = new SpannableStringBuilder();
+        for (RichTextNode richTextNode : list) {
+            spannableStringBuilder.append(richTextNode.toSpan(1));
+        }
+        return spannableStringBuilder;
+    }
+
+    public Spannable toSpan(int level) {
+        SpannableStringBuilder spannableStringBuilder = new SpannableStringBuilder();
+        spannableStringBuilder.append(toString());
+        if (isInternalNode() && children != null) {
+            for (RichTextNode child : children) {
+                spannableStringBuilder.append(child.toSpan(level + 1));
+            }
+        }
+        updateSpans(spannableStringBuilder, level);
+        return spannableStringBuilder;
+    }
+
+    private
+    @Nullable
+    WXCustomStyleSpan createCustomStyleSpan() {
+        int fontWeight = UNSET, fontStyle = UNSET;
+        String fontFamily = null;
+        if (style.containsKey(Constants.Name.FONT_WEIGHT)) {
+            fontWeight = WXStyle.getFontWeight(style);
+        }
+        if (style.containsKey(Constants.Name.FONT_STYLE)) {
+            fontStyle = WXStyle.getFontStyle(style);
+        }
+        if (style.containsKey(Constants.Name.FONT_FAMILY)) {
+            fontFamily = WXStyle.getFontFamily(style);
+        }
+        if (fontWeight != UNSET
+            || fontStyle != UNSET
+            || fontFamily != null) {
+            return new WXCustomStyleSpan(fontStyle, fontWeight, fontFamily);
+        } else {
+            return null;
+        }
+    }
+    public RichTextNode findRichNode(String ref){
+        RichTextNode theNode;
+        if(mRef != null && TextUtils.equals(mRef,ref)){
+            return this;
+        }
+        if(children != null && !children.isEmpty()){
+            for (RichTextNode child:children) {
+                if((theNode = child.findRichNode(ref)) != null)
+                    return theNode;
+            }
+        }
+        return null;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNodeCreator.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNodeCreator.java
new file mode 100755
index 0000000..a1d3313
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNodeCreator.java
@@ -0,0 +1,29 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.node;
+
+import android.content.Context;
+
+import java.util.Map;
+
+public interface RichTextNodeCreator<T extends RichTextNode> {
+
+  T createRichTextNode(Context context, String instanceId, String componentRef);
+  T createRichTextNode(Context context,String instanceId,String componentRef,String ref,Map<String,Object> styles, Map<String,Object> attrs);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNodeManager.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNodeManager.java
new file mode 100755
index 0000000..24c69f9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/RichTextNodeManager.java
@@ -0,0 +1,73 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.node;
+
+import android.content.Context;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.v4.util.ArrayMap;
+
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.Map;
+
+public class RichTextNodeManager {
+
+  private final static Map<String, RichTextNodeCreator>
+      registeredTextNodes = new ArrayMap<>();
+
+  static {
+    registeredTextNodes.put(SpanNode.NODE_TYPE, new SpanNode.SpanNodeCreator());
+    registeredTextNodes.put(ImgNode.NODE_TYPE, new ImgNode.ImgNodeCreator());
+    registeredTextNodes.put(ANode.NODE_TYPE, new ANode.ANodeCreator());
+  }
+
+  public static void registerTextNode(String text, RichTextNodeCreator type) {
+    registeredTextNodes.put(text, type);
+  }
+
+  @Nullable
+  static RichTextNode createRichTextNode(@NonNull Context context, @NonNull String instanceId,
+      @NonNull String componentRef, @Nullable JSONObject jsonObject) {
+    RichTextNode instance = null;
+    try {
+      if (jsonObject != null) {
+        instance = registeredTextNodes.get(jsonObject.getString(RichTextNode.TYPE))
+            .createRichTextNode(context, instanceId, componentRef);
+        instance.parse(context, instanceId, componentRef, jsonObject);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("Richtext", WXLogUtils.getStackTrace(e));
+      instance = null;
+    }
+    return instance;
+  }
+  public static RichTextNode createRichTextNode(Context context,String instanceId,String componentRef,String ref,
+                                         String nodeType,Map<String,String> styles,Map<String,String> attrs){
+    RichTextNode instance;
+    try{
+      instance = registeredTextNodes.get(nodeType).createRichTextNode(context,instanceId,componentRef,ref,styles,attrs);
+    }catch (Exception e){
+      WXLogUtils.e("Richtext", WXLogUtils.getStackTrace(e));
+      instance = null;
+    }
+    return instance;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/SpanNode.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/SpanNode.java
new file mode 100755
index 0000000..6f0d499
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/node/SpanNode.java
@@ -0,0 +1,75 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.node;
+
+import android.content.Context;
+import android.text.SpannableStringBuilder;
+
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.TextDecorationSpan;
+import org.apache.weex.dom.WXStyle;
+
+import java.util.Map;
+
+class SpanNode extends RichTextNode {
+
+  static class SpanNodeCreator implements RichTextNodeCreator<SpanNode> {
+
+    @Override
+    public SpanNode createRichTextNode(Context context, String instanceId, String componentRef) {
+      return new SpanNode(context, instanceId, componentRef);
+    }
+
+    @Override
+    public SpanNode createRichTextNode(Context context,String instanceId,String componentRef,String ref,
+                                       Map<String,Object> styles, Map<String,Object> attrs){
+      return new SpanNode(context,instanceId,componentRef,ref,styles,attrs);
+    }
+  }
+
+  public static final String NODE_TYPE = "span";
+
+  private SpanNode(Context context, String instanceId, String componentRef) {
+    super(context, instanceId, componentRef);
+  }
+  private SpanNode(Context context, String instanceId, String componentRef, String ref, Map<String,Object> styles,Map<String,Object> attrs) {
+    super(context, instanceId, componentRef, ref, styles, attrs);
+  }
+
+  @Override
+  public String toString() {
+    if (attr == null || !attr.containsKey(Constants.Name.VALUE)) {
+      return "";
+    } else {
+      return attr.get(Constants.Name.VALUE).toString();
+    }
+  }
+
+  @Override
+  protected boolean isInternalNode() {
+    return true;
+  }
+
+  @Override
+  protected void updateSpans(SpannableStringBuilder spannableStringBuilder, int level) {
+    super.updateSpans(spannableStringBuilder, level);
+    spannableStringBuilder.setSpan(new TextDecorationSpan(WXStyle.getTextDecoration(style)), 0,
+        spannableStringBuilder.length(), createSpanFlag(level));
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ASpan.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ASpan.java
new file mode 100644
index 0000000..2a4e7b4
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ASpan.java
@@ -0,0 +1,47 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.span;
+
+import android.text.TextPaint;
+import android.text.style.ClickableSpan;
+import android.view.View;
+import org.apache.weex.utils.ATagUtil;
+
+public class ASpan extends ClickableSpan {
+
+  private String mInstanceId, mURL;
+
+  public ASpan(String instanceId, String url) {
+    mInstanceId = instanceId;
+    mURL = url;
+  }
+
+  @Override
+  public void onClick(View widget) {
+    ATagUtil.onClick(widget, mInstanceId, mURL);
+  }
+
+  /**
+   Override super method and do nothing. As no default color or text-decoration is needed.
+   */
+  @Override
+  public void updateDrawState(TextPaint ds) {
+
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ImgSpan.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ImgSpan.java
new file mode 100644
index 0000000..d27b202
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ImgSpan.java
@@ -0,0 +1,96 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.span;
+
+import android.graphics.Canvas;
+import android.graphics.Paint;
+import android.graphics.drawable.Drawable;
+import android.text.style.ReplacementSpan;
+import android.view.View;
+
+import org.apache.weex.adapter.IDrawableLoader.StaticTarget;
+
+
+public class ImgSpan extends ReplacementSpan implements StaticTarget {
+
+  private int width, height;
+  private Drawable mDrawable;
+  private View mView;
+
+  public ImgSpan(int width, int height) {
+    this.width = width;
+    this.height = height;
+  }
+
+  /**
+   * Mostly copied from
+   *
+   * {@link android.text.style.DynamicDrawableSpan#getSize(Paint, CharSequence, int, int, Paint.FontMetricsInt)},
+   * but not use Drawable to calculate size;
+   */
+  @Override
+  public int getSize(Paint paint, CharSequence text, int start, int end, Paint.FontMetricsInt fm) {
+    if (fm != null) {
+      fm.ascent = -height;
+      fm.descent = 0;
+
+      fm.top = fm.ascent;
+      fm.bottom = 0;
+    }
+    return width;
+  }
+
+  /**
+   * Mostly copied from
+   * {@link android.text.style.DynamicDrawableSpan#draw(Canvas, CharSequence, int, int, float, int, int, int, Paint)},
+   * except for vertical alignment.
+   */
+  @Override
+  public void draw(Canvas canvas, CharSequence text, int start, int end, float x, int top, int y, int bottom, Paint paint) {
+    if (mDrawable != null) {
+      canvas.save();
+      int transY = bottom - mDrawable.getBounds().bottom;
+      transY -= paint.getFontMetricsInt().descent;
+      canvas.translate(x, transY);
+      mDrawable.draw(canvas);
+      canvas.restore();
+    }
+  }
+
+  @Override
+  public void setDrawable(Drawable drawable, boolean resetBounds) {
+    mDrawable = drawable;
+    if(resetBounds) {
+      mDrawable.setBounds(0, 0, width, height);
+    }
+    setCallback();
+    mDrawable.invalidateSelf();
+  }
+
+  public void setView(View view) {
+    mView = view;
+    setCallback();
+  }
+
+  private void setCallback() {
+    if (mDrawable != null && mView != null) {
+      mDrawable.setCallback(mView);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ItemClickSpan.java b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ItemClickSpan.java
new file mode 100644
index 0000000..6e6286c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/component/richtext/span/ItemClickSpan.java
@@ -0,0 +1,51 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.component.richtext.span;
+
+
+import android.text.style.ClickableSpan;
+import android.view.View;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.ui.component.richtext.node.RichTextNode;
+import org.apache.weex.utils.WXDataStructureUtil;
+import java.util.Map;
+
+public class ItemClickSpan extends ClickableSpan {
+
+  private final String mPseudoRef;
+  private final String mInstanceId;
+  private final String mComponentRef;
+
+  public ItemClickSpan(String instanceId, String componentRef, String pseudoRef) {
+    this.mPseudoRef = pseudoRef;
+    this.mInstanceId = instanceId;
+    this.mComponentRef = componentRef;
+  }
+
+  @Override
+  public void onClick(View widget) {
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(mInstanceId);
+    if (instance != null && !instance.isDestroy()) {
+      Map<String, Object> param = WXDataStructureUtil.newHashMapWithExpectedSize(1);
+      param.put(RichTextNode.PSEUDO_REF, mPseudoRef);
+      instance.fireEvent(mComponentRef, RichTextNode.ITEM_CLICK, param);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/config/AutoScanConfigRegister.java b/android/sdk/src/main/java/org/apache/weex/ui/config/AutoScanConfigRegister.java
new file mode 100644
index 0000000..26477d0
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/config/AutoScanConfigRegister.java
@@ -0,0 +1,141 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.config;
+
+import android.content.res.AssetManager;
+import android.text.TextUtils;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKEngine;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.utils.WXFileUtils;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.io.IOException;
+
+/**
+ * Created by furture on 2018/2/7.
+ */
+
+public class AutoScanConfigRegister {
+
+    private static long scanDelay = 0;
+
+    public static final  String TAG  = "WeexScanConfigRegister";
+
+
+    /**
+     * auto scan config files and do auto config from files, none need center register
+     * */
+    public static void doScanConfig(){
+        if(scanDelay > 0){
+            WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(new Runnable() {
+                @Override
+                public void run() {
+                    doScanConfigAsync();
+                }
+            }, scanDelay);
+        }else{
+            doScanConfigAsync();
+        }
+    }
+
+    public static void doScanConfigAsync(){
+        Thread thread = new Thread(new Runnable() {
+            @Override
+            public void run() {
+                doScanConfigSync();
+            }
+        });
+        thread.setName("AutoScanConfigRegister");
+        thread.start();
+    }
+
+    private static void doScanConfigSync(){
+        if(WXEnvironment.sApplication == null){
+            return;
+        }
+        try{
+            AssetManager assetManager = WXEnvironment.sApplication.getApplicationContext().getAssets();
+
+            String[] configFiles = new String[0];
+            try {
+                configFiles = assetManager.list("");
+            } catch (IOException e) {
+                WXLogUtils.e(TAG, e);
+            }
+            if(configFiles == null || configFiles.length == 0){
+                return;
+            }
+            for(String configFile : configFiles){
+                if(TextUtils.isEmpty(configFile)){
+                    continue;
+                }
+                if(configFile.startsWith("weex_config_") && configFile.endsWith(".json")){
+                    String name = configFile;
+                    if(TextUtils.isEmpty(name)){
+                        return;
+                    }
+                    try {
+                        String config = WXFileUtils.loadAsset(name, WXEnvironment.getApplication());
+                        if (TextUtils.isEmpty(config)) {
+                            continue;
+                        }
+                        if (WXEnvironment.isApkDebugable()) {
+                            WXLogUtils.d(TAG, configFile + " find config " + config);
+                        }
+                        JSONObject object = JSON.parseObject(config);
+                        if (object.containsKey("modules")) {
+                            JSONArray array = object.getJSONArray("modules");
+                            for (int i = 0; i < array.size(); i++) {
+                                ConfigModuleFactory configModuleFactory = ConfigModuleFactory.fromConfig(array.getJSONObject(i));
+                                if (configModuleFactory == null) {
+                                    continue;
+                                }
+                                WXSDKEngine.registerModule(configModuleFactory.getName(), configModuleFactory, false);
+                            }
+                        }
+
+                        if (object.containsKey("components")) {
+                            JSONArray array = object.getJSONArray("components");
+                            for (int i = 0; i < array.size(); i++) {
+                                ConfigComponentHolder configComponentHolder = ConfigComponentHolder.fromConfig(array.getJSONObject(i));
+                                if (configComponentHolder == null) {
+                                    return;
+                                }
+                                WXSDKEngine.registerComponent(configComponentHolder, configComponentHolder.isAppendTree(), configComponentHolder.getType());
+                            }
+                        }
+                    }catch (Throwable e){
+                        WXLogUtils.e(TAG, e);
+                    }
+                }
+            }
+        }catch (Exception eout){
+            WXLogUtils.e(TAG, eout);
+        }
+    }
+
+    public static void setScanDelay(long scanDelay) {
+        AutoScanConfigRegister.scanDelay = scanDelay;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/config/ConfigComponentHolder.java b/android/sdk/src/main/java/org/apache/weex/ui/config/ConfigComponentHolder.java
new file mode 100644
index 0000000..16759eb
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/config/ConfigComponentHolder.java
@@ -0,0 +1,162 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.config;
+
+import android.text.TextUtils;
+import android.util.Pair;
+
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.bridge.Invoker;
+import org.apache.weex.ui.ComponentCreator;
+import org.apache.weex.ui.IFComponentHolder;
+import org.apache.weex.ui.SimpleComponentHolder;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.lang.reflect.InvocationTargetException;
+import java.util.Map;
+
+/**
+ * Created by furture on 2018/2/7.
+ */
+public class ConfigComponentHolder implements IFComponentHolder {
+
+
+    public static final String TAG = AutoScanConfigRegister.TAG;
+    private Map<String, Invoker> mPropertyInvokers;
+    private Map<String, Invoker> mMethodInvokers;
+
+    private ClassLoader mClassLoader;
+
+    private String mType;
+    private boolean mAppendTree;
+    private String mClassName;
+    private String[] methods;
+    private Class mClass;
+
+    public ConfigComponentHolder(String mType, boolean mAppendTree, String mClassName, String[] methods) {
+        this.mType = mType;
+        this.mAppendTree = mAppendTree;
+        this.mClassName = mClassName;
+        this.methods = methods;
+    }
+
+    @Override
+    public void loadIfNonLazy() {
+    }
+
+    private synchronized boolean generate(){
+        if(mClass == null){
+            return false;
+        }
+
+        Pair<Map<String, Invoker>, Map<String, Invoker>> methodPair = SimpleComponentHolder.getMethods(mClass);
+        mPropertyInvokers = methodPair.first;
+        mMethodInvokers = methodPair.second;
+        return true;
+    }
+
+
+
+    @Override
+    public synchronized WXComponent createInstance(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) throws IllegalAccessException, InvocationTargetException, InstantiationException {
+        if(mClass == null || mClassLoader != instance.getContext().getClassLoader()){
+            mClass = WXSDKManager
+                .getInstance().getClassLoaderAdapter().getComponentClass(mType, mClassName, instance);
+            mClassLoader = instance.getContext().getClassLoader();
+        }
+        ComponentCreator creator = new SimpleComponentHolder.ClazzComponentCreator(mClass);
+        WXComponent component = creator.createInstance(instance, parent, basicComponentData);
+
+        component.bindHolder(this);
+        return component;
+    }
+
+    @Override
+    public synchronized Invoker getPropertyInvoker(String name){
+        if (mPropertyInvokers == null && !generate()) {
+            return null;
+        }
+
+        return mPropertyInvokers.get(name);
+    }
+
+    @Override
+    public Invoker getMethodInvoker(String name) {
+        if(mMethodInvokers == null && !generate()){
+            return null;
+        }
+        return mMethodInvokers.get(name);
+    }
+
+    @Override
+    public String[] getMethods() {
+        if(methods == null){
+            //generate failed
+            return new String[0];
+        }
+        return methods;
+    }
+
+
+    public static final ConfigComponentHolder fromConfig(JSONObject config){
+        if(config == null){
+            return null;
+        }
+        try{
+            String type = config.getString("name");
+            boolean appendTree  = config.getBooleanValue("appendTree");
+            String className = config.getString("className");
+            JSONArray methods =  null;
+            if(config.containsKey("methods")) {
+                methods = config.getJSONArray("methods");
+            }
+            if(TextUtils.isEmpty(type) || TextUtils.isEmpty(className)){
+                return null;
+            }
+            String[]  arrays = new String[0];
+            if(methods != null){
+                arrays = new String[methods.size()];
+                methods.toArray(arrays);
+            }
+            if(WXEnvironment.isApkDebugable()){
+                WXLogUtils.d(TAG, "resolve component " + type + " className " + className +  " methods " + methods);
+            }
+            return new ConfigComponentHolder(type, appendTree, className, arrays);
+        }catch (Exception e){
+            WXLogUtils.e(TAG, e);
+            return null;
+        }
+
+    }
+
+    public boolean isAppendTree() {
+        return mAppendTree;
+    }
+
+    public String getType() {
+        return mType;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/config/ConfigModuleFactory.java b/android/sdk/src/main/java/org/apache/weex/ui/config/ConfigModuleFactory.java
new file mode 100644
index 0000000..c3973ee
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/config/ConfigModuleFactory.java
@@ -0,0 +1,157 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.config;
+
+import android.text.TextUtils;
+
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.Invoker;
+import org.apache.weex.bridge.MethodInvoker;
+import org.apache.weex.bridge.ModuleFactory;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.common.WXModuleAnno;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.lang.annotation.Annotation;
+import java.lang.reflect.Method;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * Created by furture on 2018/2/7.
+ */
+
+public class ConfigModuleFactory<T extends WXModule> implements ModuleFactory<T> {
+
+    public static final String TAG = AutoScanConfigRegister.TAG;
+
+    private String mName;
+    private String mClassName;
+    private String[] methods;
+    private Class<T> mClazz;
+    private Map<String, Invoker> mMethodMap;
+
+    private ClassLoader mClassLoader;
+
+    public ConfigModuleFactory(String mName, String mClassName, String[] methods) {
+        this.mName = mName;
+        this.mClassName = mClassName;
+        this.methods = methods;
+    }
+
+    @Override
+    public String[] getMethods() {
+        if(methods == null){
+            return new String[0];
+        }
+        return methods;
+    }
+
+    @Override
+    public Invoker getMethodInvoker(String name) {
+        if (mMethodMap == null) {
+            generateMethodMap();
+        }
+        return mMethodMap.get(name);
+    }
+
+    @Override
+    public T buildInstance() throws IllegalAccessException, InstantiationException {
+        if(mClazz == null){
+            mClazz = (Class<T>) WXSDKManager
+                .getInstance().getClassLoaderAdapter().getModuleClass(mName, mClassName, WXEnvironment
+                    .getApplication().getApplicationContext());
+        }
+        return mClazz.newInstance();
+    }
+
+    public T buildInstance(WXSDKInstance instance) throws IllegalAccessException, InstantiationException {
+        if(instance == null){
+            return buildInstance();
+        }
+        if(mClazz == null || mClassLoader != instance.getContext().getClassLoader()){
+            mClazz = (Class<T>) WXSDKManager.getInstance().getClassLoaderAdapter().getModuleClass(mName, mClassName, instance.getContext());
+            mClassLoader = instance.getContext().getClassLoader();
+        }
+        return mClazz.newInstance();
+    }
+
+
+    private void generateMethodMap() {
+        if(WXEnvironment.isApkDebugable()) {
+             WXLogUtils.d(TAG, "extractMethodNames:" + mClazz.getSimpleName());
+        }
+        HashMap<String, Invoker> methodMap = new HashMap<>();
+        try {
+            for (Method method : mClazz.getMethods()) {
+                // iterates all the annotations available in the method
+                for (Annotation anno : method.getDeclaredAnnotations()) {
+                    if (anno != null) {
+                        if(anno instanceof JSMethod) {
+                            JSMethod methodAnnotation = (JSMethod) anno;
+                            String name = JSMethod.NOT_SET.equals(methodAnnotation.alias())? method.getName():methodAnnotation.alias();
+                            methodMap.put(name, new MethodInvoker(method, methodAnnotation.uiThread()));
+                            break;
+                        }else if(anno instanceof WXModuleAnno) {
+                            WXModuleAnno methodAnnotation = (WXModuleAnno)anno;
+                            methodMap.put(method.getName(), new MethodInvoker(method,methodAnnotation.runOnUIThread()));
+                            break;
+                        }
+                    }
+                }
+            }
+        } catch (Throwable e) {
+            WXLogUtils.e("[WXModuleManager] extractMethodNames:", e);
+        }
+        mMethodMap = methodMap;
+    }
+
+
+    public static ConfigModuleFactory fromConfig(JSONObject config){
+        try{
+            if(config == null){
+                return null;
+            }
+
+            String name = config.getString("name");
+            String className = config.getString("className");
+            JSONArray methods = config.getJSONArray("methods");
+            if(TextUtils.isEmpty(name) || TextUtils.isEmpty(className)){
+                return null;
+            }
+            String[]  arrays = new String[methods.size()];
+            if(WXEnvironment.isApkDebugable()){
+                WXLogUtils.d(TAG, " resolve module " + name + " className " + className +  " methods " + methods);
+            }
+            return new ConfigModuleFactory(name, className, methods.toArray(arrays));
+        }catch (Exception e){
+             WXLogUtils.e(TAG, e);
+             return null;
+        }
+    }
+
+    public String getName() {
+        return mName;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/flat/FlatComponent.java b/android/sdk/src/main/java/org/apache/weex/ui/flat/FlatComponent.java
new file mode 100644
index 0000000..f18b149
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/flat/FlatComponent.java
@@ -0,0 +1,35 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.flat;
+
+
+import android.support.annotation.NonNull;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+
+import org.apache.weex.ui.flat.widget.Widget;
+
+@RestrictTo(Scope.LIBRARY)
+public interface FlatComponent<T extends Widget> {
+
+  boolean promoteToView(boolean checkAncestor);
+
+  @NonNull
+  T getOrCreateFlatWidget();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/flat/FlatGUIContext.java b/android/sdk/src/main/java/org/apache/weex/ui/flat/FlatGUIContext.java
new file mode 100644
index 0000000..9bb3dda
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/flat/FlatGUIContext.java
@@ -0,0 +1,146 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.flat;
+
+
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+import android.view.View;
+
+import org.apache.weex.common.Constants.Name;
+import org.apache.weex.common.Destroyable;
+import org.apache.weex.dom.WXAttr;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.flat.widget.AndroidViewWidget;
+import org.apache.weex.ui.flat.widget.Widget;
+
+import java.util.Map;
+import java.util.Map.Entry;
+
+//TODO The constructor of FlatGUIContext should have a flag decide whether to enable flagGUI.
+
+@RestrictTo(Scope.LIBRARY)
+public class FlatGUIContext implements Destroyable {
+
+  private Map<WXComponent, WidgetContainer> mWidgetRegistry = new ArrayMap<>();
+  private Map<WXComponent, AndroidViewWidget> mViewWidgetRegistry = new ArrayMap<>();
+  private Map<Widget, WXComponent> widgetToComponent = new ArrayMap<>();
+
+  public boolean isFlatUIEnabled(WXComponent component) {
+    return false;
+  }
+
+  public void register(@NonNull WXComponent descendant, @NonNull WidgetContainer ancestor) {
+    if (!(ancestor instanceof FlatComponent) ||
+            ((FlatComponent) ancestor).promoteToView(true)) {
+      mWidgetRegistry.put(descendant, ancestor);
+    }
+  }
+
+  public void register(@NonNull WXComponent component, @NonNull AndroidViewWidget viewWidget) {
+    mViewWidgetRegistry.put(component, viewWidget);
+  }
+
+  public void register(@NonNull Widget widget, @NonNull WXComponent component) {
+    widgetToComponent.put(widget, component);
+  }
+
+  public
+  @Nullable
+  WidgetContainer getFlatComponentAncestor(@NonNull WXComponent flatWidget) {
+    return mWidgetRegistry.get(flatWidget);
+  }
+
+  public
+  @Nullable
+  AndroidViewWidget getAndroidViewWidget(@NonNull WXComponent component) {
+    return mViewWidgetRegistry.get(component);
+  }
+
+  public boolean promoteToView(@NonNull WXComponent component, boolean checkAncestor,
+                               @NonNull Class<? extends WXComponent<?>> expectedClass) {
+    return !isFlatUIEnabled(component) ||
+            !expectedClass.equals(component.getClass()) ||
+            TextUtils.equals(component.getRef(), WXComponent.ROOT) ||
+            (checkAncestor && getFlatComponentAncestor(component) == null) ||
+            checkComponent(component);
+  }
+
+  public
+  @Nullable
+  View getWidgetContainerView(Widget widget) {
+    WXComponent component, ancestor;
+    View ret = null;
+    if ((component = getComponent(widget)) != null) {
+      if ((ancestor = getFlatComponentAncestor(component)) != null) {
+        ret = ancestor.getHostView();
+      }
+    }
+    return ret;
+  }
+
+  @Override
+  @RestrictTo(Scope.LIBRARY)
+  public void destroy() {
+    widgetToComponent.clear();
+
+    for (Entry<WXComponent, AndroidViewWidget> entry : mViewWidgetRegistry.entrySet()) {
+      entry.getValue().destroy();
+    }
+    mViewWidgetRegistry.clear();
+
+    for (Entry<WXComponent, WidgetContainer> entry : mWidgetRegistry.entrySet()) {
+      entry.getValue().unmountFlatGUI();
+    }
+    mWidgetRegistry.clear();
+  }
+
+  private @Nullable
+  WXComponent getComponent(@NonNull Widget widget) {
+    return widgetToComponent.get(widget);
+  }
+
+  private boolean checkComponent(@NonNull WXComponent component) {
+    boolean ret = false;
+    if (component != null) {
+      WXStyle style = component.getStyles();
+      WXAttr attr = component.getAttrs();
+      if (style.containsKey(Name.OPACITY) ||
+              style.containsKey(Name.TRANSFORM) ||
+              style.containsKey(Name.VISIBILITY) ||
+              attr.containsKey(Name.ELEVATION) ||
+              attr.containsKey(Name.ARIA_HIDDEN) ||
+              attr.containsKey(Name.ARIA_LABEL) ||
+              attr.containsKey(WXComponent.PROP_FIXED_SIZE) ||
+              attr.containsKey(Name.DISABLED) ||
+              style.isFixed() ||
+              style.isSticky() ||
+              !style.getPesudoStyles().isEmpty() ||
+              component.getEvents().size() > 0) {
+        ret = true;
+      }
+    }
+    return ret;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/flat/WidgetContainer.java b/android/sdk/src/main/java/org/apache/weex/ui/flat/WidgetContainer.java
new file mode 100644
index 0000000..58b8e0d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/flat/WidgetContainer.java
@@ -0,0 +1,98 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.flat;
+
+
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.util.Pair;
+import android.view.ViewGroup;
+
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.ui.action.BasicComponentData;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXVContainer;
+import org.apache.weex.ui.flat.widget.AndroidViewWidget;
+import org.apache.weex.ui.flat.widget.Widget;
+
+import java.util.LinkedList;
+import java.util.List;
+
+@RestrictTo(Scope.LIBRARY)
+public abstract class WidgetContainer<T extends ViewGroup> extends WXVContainer<T> {
+
+  protected List<Widget> widgets;
+
+  public WidgetContainer(WXSDKInstance instance, WXVContainer parent, BasicComponentData basicComponentData) {
+    super(instance, parent, basicComponentData);
+  }
+
+  protected abstract void mountFlatGUI();
+
+  protected abstract void unmountFlatGUI();
+
+  public boolean intendToBeFlatContainer() {
+    return false;
+  }
+
+  @Override
+  public void createChildViewAt(int index) {
+    if (intendToBeFlatContainer()) {
+      Pair<WXComponent, Integer> ret = rearrangeIndexAndGetChild(index);
+      if (ret.first != null) {
+        WXComponent child = ret.first;
+        Widget flatChild;
+        FlatGUIContext uiImp = getInstance().getFlatUIContext();
+        WidgetContainer parent = uiImp.getFlatComponentAncestor(this);
+        if (parent == null || uiImp.getAndroidViewWidget(this) != null) {
+          parent = this;
+        }
+        uiImp.register(child, parent);
+
+        if (child instanceof FlatComponent && !((FlatComponent) child).promoteToView(false)) {
+          flatChild = ((FlatComponent) child).getOrCreateFlatWidget();
+        } else {
+          flatChild = new AndroidViewWidget(uiImp);
+          uiImp.register(child, (AndroidViewWidget) flatChild);
+          child.createView();
+          ((AndroidViewWidget) flatChild).setContentView(child.getHostView());
+          //TODO Use a sort algorithm to decide the childIndex of AndroidViewWidget
+          parent.addSubView(child.getHostView(), -1);
+        }
+        uiImp.register(flatChild, child);
+        addFlatChild(flatChild, ret.second);
+      }
+    } else {
+      super.createChildViewAt(index);
+    }
+  }
+
+  private void addFlatChild(Widget widget, int index) {
+    if(widgets == null){
+      widgets = new LinkedList<>();
+    }
+    if (index >= widgets.size()) {
+      widgets.add(widget);
+    } else {
+      widgets.add(index, widget);
+    }
+    //TODO do a partial update, not mount the whole flatContainer.
+    mountFlatGUI();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/AndroidViewWidget.java b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/AndroidViewWidget.java
new file mode 100644
index 0000000..f2682de
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/AndroidViewWidget.java
@@ -0,0 +1,80 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.flat.widget;
+
+
+import android.graphics.Canvas;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.view.View;
+
+import org.apache.weex.common.Destroyable;
+import org.apache.weex.ui.flat.FlatGUIContext;
+
+@RestrictTo(Scope.LIBRARY)
+public class AndroidViewWidget extends BaseWidget implements Destroyable {
+
+  private @Nullable
+  View mView;
+
+  public AndroidViewWidget(@NonNull FlatGUIContext context) {
+    super(context);
+  }
+
+  public void setContentView(@Nullable View view) {
+    this.mView = view;
+  }
+
+  @Override
+  public void setContentBox(int leftOffset, int topOffset, int rightOffset, int bottomOffset) {
+    if (mView != null) {
+      mView.setPadding(leftOffset, topOffset, rightOffset, bottomOffset);
+      invalidate();
+    }
+  }
+
+  @Override
+  public void onDraw(@NonNull Canvas canvas) {
+    if (mView != null) {
+      mView.draw(canvas);
+    }
+  }
+
+  @Override
+  public void invalidate() {
+    super.invalidate();
+    if (mView != null) {
+      mView.invalidate();
+    }
+  }
+
+  public @Nullable
+  View getView() {
+    return mView;
+  }
+
+  @Override
+  public void destroy() {
+    if (mView != null) {
+      mView = null;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/BaseWidget.java b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/BaseWidget.java
new file mode 100644
index 0000000..c766a5d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/BaseWidget.java
@@ -0,0 +1,130 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.flat.widget;
+
+
+import android.graphics.Canvas;
+import android.graphics.Point;
+import android.graphics.Rect;
+import android.graphics.drawable.Drawable;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.view.View;
+import org.apache.weex.ui.flat.FlatGUIContext;
+import org.apache.weex.ui.view.border.BorderDrawable;
+import org.apache.weex.utils.WXViewUtils;
+
+@RestrictTo(Scope.LIBRARY)
+abstract class BaseWidget implements Widget {
+
+  //TODO Reconsider the field parameter in this class and the operation during draw(); Make a CPU/Memory balance.
+  //TODO use float to avoid 1px problem
+  private BorderDrawable backgroundBorder;
+  private int leftOffset, topOffset, rightOffset, bottomOffset;
+  private Rect borderBox = new Rect();
+  private Point offsetOfContainer = new Point();
+  private final @NonNull
+  FlatGUIContext context;
+
+  BaseWidget(@NonNull FlatGUIContext context){
+    this.context = context;
+  }
+
+  @Override
+  public void setLayout(int width, int height, int left, int right, int top, int bottom, Point offset) {
+    this.offsetOfContainer = offset;
+    borderBox.set(left, top, left + width, top + height);
+    if (backgroundBorder != null) {
+      setBackgroundAndBorder(backgroundBorder);
+    }
+    invalidate();
+  }
+
+  @Override
+  public void setContentBox(int leftOffset, int topOffset, int rightOffset, int bottomOffset) {
+    this.leftOffset = leftOffset;
+    this.topOffset = topOffset;
+    this.rightOffset = rightOffset;
+    this.bottomOffset = bottomOffset;
+    invalidate();
+  }
+
+  @Override
+  public void setBackgroundAndBorder(@NonNull BorderDrawable backgroundBorder) {
+    //TODO Change the code of BorderDrawable is more appropriate as it draws the borderLine from (0,0) not from getBounds
+    //TODO If the above is finished, no more traslate in draw in needed, only clip is enough.
+    this.backgroundBorder = backgroundBorder;
+    Rect backgroundBox = new Rect(borderBox);
+    backgroundBox.offset(-borderBox.left, -borderBox.top);
+    backgroundBorder.setBounds(backgroundBox);
+    setCallback(backgroundBorder);
+    invalidate();
+  }
+
+  @NonNull
+  @Override
+  public final Point getLocInFlatContainer() {
+    return offsetOfContainer;
+  }
+
+  @Nullable
+  @Override
+  public final BorderDrawable getBackgroundAndBorder() {
+    return backgroundBorder;
+  }
+
+  @NonNull
+  @Override
+  public final Rect getBorderBox() {
+    return borderBox;
+  }
+
+  @Override
+  public final void draw(@NonNull Canvas canvas) {
+    canvas.save();
+    WXViewUtils.clipCanvasWithinBorderBox(this, canvas);
+    canvas.translate(borderBox.left, borderBox.top);
+    if (backgroundBorder != null) {
+      backgroundBorder.draw(canvas);
+    }
+    canvas.clipRect(leftOffset, topOffset, borderBox.width()-rightOffset, borderBox.height() - bottomOffset);
+    canvas.translate(leftOffset, topOffset);
+    onDraw(canvas);
+    canvas.restore();
+  }
+
+  protected void invalidate() {
+    Rect dirtyRegion = new Rect(borderBox);
+    dirtyRegion.offset(offsetOfContainer.x, offsetOfContainer.y);
+    View widgetContainer;
+    if (context != null && (widgetContainer = context.getWidgetContainerView(this)) != null) {
+      widgetContainer.invalidate(dirtyRegion);
+    }
+  }
+
+  protected void setCallback(@NonNull Drawable drawable) {
+    View widgetContainer;
+    if (context != null && (widgetContainer = context.getWidgetContainerView(this)) != null) {
+      drawable.setCallback(widgetContainer);
+    }
+  }
+}
+
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/TextWidget.java b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/TextWidget.java
new file mode 100644
index 0000000..30b0faf
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/TextWidget.java
@@ -0,0 +1,50 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.flat.widget;
+
+
+import android.graphics.Canvas;
+import android.support.annotation.NonNull;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import android.text.Layout;
+
+import org.apache.weex.ui.flat.FlatGUIContext;
+
+@RestrictTo(Scope.LIBRARY)
+public class TextWidget extends BaseWidget {
+
+  private Layout mLayout;
+
+  public TextWidget(@NonNull FlatGUIContext context) {
+    super(context);
+  }
+
+  @Override
+  public void onDraw(@NonNull Canvas canvas) {
+    if (mLayout != null) {
+      mLayout.draw(canvas);
+    }
+  }
+
+  public void updateTextDrawable(Layout layout) {
+    this.mLayout = layout;
+    invalidate();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/Widget.java b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/Widget.java
new file mode 100644
index 0000000..73e3993
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/Widget.java
@@ -0,0 +1,55 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.flat.widget;
+
+
+import android.graphics.Canvas;
+import android.graphics.Point;
+import android.graphics.Rect;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+
+import org.apache.weex.ui.view.border.BorderDrawable;
+
+@RestrictTo(Scope.LIBRARY)
+public interface Widget {
+
+  public static final String TAG = "Widget";
+
+  void draw(@NonNull Canvas canvas);
+
+  void onDraw(@NonNull Canvas canvas);
+
+  void setBackgroundAndBorder(@NonNull BorderDrawable backgroundBorder);
+
+  void setLayout(int width, int height, int left, int right, int top, int bottom, Point offset);
+
+  void setContentBox(int leftOffset, int topOffset, int rightOffset, int bottomOffset);
+
+  @NonNull
+  Point getLocInFlatContainer();
+
+  @Nullable
+  BorderDrawable getBackgroundAndBorder();
+
+  @NonNull
+  Rect getBorderBox();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/WidgetGroup.java b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/WidgetGroup.java
new file mode 100644
index 0000000..9d89e9d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/flat/widget/WidgetGroup.java
@@ -0,0 +1,56 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.flat.widget;
+
+
+import android.graphics.Canvas;
+import android.support.annotation.NonNull;
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+
+import org.apache.weex.ui.flat.FlatGUIContext;
+
+import java.util.LinkedList;
+import java.util.List;
+
+@RestrictTo(Scope.LIBRARY)
+public class WidgetGroup extends BaseWidget {
+
+  private List<Widget> mChildren = new LinkedList<>();
+
+  public WidgetGroup(@NonNull FlatGUIContext context) {
+    super(context);
+  }
+
+  public void replaceAll(@NonNull List<Widget> widgets) {
+    mChildren = widgets;
+    invalidate();
+  }
+
+  public List<Widget> getChildren() {
+    return mChildren;
+  }
+
+  @Override
+  public void onDraw(@NonNull Canvas canvas) {
+    for (Widget child : mChildren) {
+      child.draw(canvas);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/module/ConsoleLogModule.java b/android/sdk/src/main/java/org/apache/weex/ui/module/ConsoleLogModule.java
new file mode 100644
index 0000000..ff1b594
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/module/ConsoleLogModule.java
@@ -0,0 +1,85 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.module;
+
+import android.support.annotation.Nullable;
+import android.support.v4.util.ArrayMap;
+import android.text.TextUtils;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.utils.LogLevel;
+import java.util.Map;
+
+
+public class ConsoleLogModule extends WXModule {
+
+  @JSMethod(uiThread = false)
+  public void switchLogLevel(@Nullable String logLevel, @Nullable JSCallback callback) {
+    LogLevel logLevelEnum = getLogLevel(logLevel);
+    Map<String, String> ret = new ArrayMap<>();
+    if (logLevelEnum != null) {
+      WXEnvironment.sLogLevel = logLevelEnum;
+      WXBridgeManager.getInstance().setLogLevel(WXEnvironment.sLogLevel.getValue(),WXEnvironment.isPerf());
+      ret.put("status", "success");
+    } else {
+      ret.put("status", "failure");
+    }
+
+    if (callback != null) {
+      callback.invoke(ret);
+    }
+
+  }
+
+  @JSMethod(uiThread = false)
+  public void setPerfMode(@Nullable String on) {
+    WXEnvironment.isPerf = "true".equals(on);
+    WXBridgeManager.getInstance().setLogLevel(WXEnvironment.sLogLevel.getValue(),WXEnvironment.isPerf());
+  }
+
+  private @Nullable LogLevel getLogLevel(@Nullable String logLevel) {
+    LogLevel logLevelEnum = null;
+    if(!TextUtils.isEmpty(logLevel)){
+      switch (logLevel){
+        case "off":
+          logLevelEnum = LogLevel.OFF;
+          break;
+        case "error":
+          logLevelEnum = LogLevel.ERROR;
+          break;
+        case "warning":
+          logLevelEnum = LogLevel.WARN;
+          break;
+        case "info":
+          logLevelEnum = LogLevel.INFO;
+          break;
+        case "debug":
+          logLevelEnum = LogLevel.DEBUG;
+          break;
+      }
+    }
+    return logLevelEnum;
+  }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/module/WXDeviceInfoModule.java b/android/sdk/src/main/java/org/apache/weex/ui/module/WXDeviceInfoModule.java
new file mode 100644
index 0000000..243a8ce
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/module/WXDeviceInfoModule.java
@@ -0,0 +1,46 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.module;
+
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.util.HashMap;
+
+public class WXDeviceInfoModule extends WXModule {
+    
+    @JSMethod(uiThread = false)
+    public void enableFullScreenHeight(final JSCallback callback,JSONObject extend){
+        if(mWXSDKInstance != null) {
+            mWXSDKInstance.setEnableFullScreenHeight(true);
+            if(callback != null) {
+                long fullScreenHeight = WXViewUtils.getScreenHeight(mWXSDKInstance.getInstanceId());
+                HashMap<String, String> ret = new HashMap();
+                ret.put("fullScreenHeight", String.valueOf(fullScreenHeight));
+                callback.invoke(ret);
+            }
+
+        }
+
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/module/WXDomModule.java b/android/sdk/src/main/java/org/apache/weex/ui/module/WXDomModule.java
new file mode 100644
index 0000000..11e5a36
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/module/WXDomModule.java
@@ -0,0 +1,207 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.module;
+
+import android.support.annotation.RestrictTo;
+import android.support.annotation.RestrictTo.Scope;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.dom.binding.JSONUtils;
+import org.apache.weex.ui.action.ActionAddRule;
+import org.apache.weex.ui.action.ActionGetComponentRect;
+import org.apache.weex.ui.action.ActionGetLayoutDirection;
+import org.apache.weex.ui.action.ActionInvokeMethod;
+import org.apache.weex.ui.action.GraphicActionBatchBegin;
+import org.apache.weex.ui.action.GraphicActionBatchEnd;
+import org.apache.weex.ui.action.GraphicActionScrollToElement;
+import org.apache.weex.ui.action.UpdateComponentDataAction;
+import org.apache.weex.utils.WXLogUtils;
+
+/**
+ * <p>
+ * Module class for dom operation.
+ * </p>
+ * <p>
+ *   This module is work different with other regular module, method is invoked directly, without reflection.
+ * </p>
+ *
+ * <p>
+ *  This class is for internal purpose,
+ *  please don't use it directly unless you know what you are doing.
+ * </p>
+ */
+@RestrictTo(Scope.LIBRARY_GROUP)
+public class WXDomModule extends WXModule {
+
+  /** package **/
+  public static final String SCROLL_TO_ELEMENT = "scrollToElement";
+  public static final String ADD_RULE = "addRule";
+  public static final String GET_COMPONENT_RECT = "getComponentRect";
+  public static final String GET_COMPONENT_DIRECTION = "getLayoutDirection";
+  public static final String WXDOM = "dom";
+  public static final String INVOKE_METHOD = "invokeMethod";
+
+  public static final String UPDATE_COMPONENT_DATA = "updateComponentData";
+
+  public static final String BATCH_BEGIN = "beginBatchMark";
+  public static final String BATCH_END = "endBatchMark";
+
+  /**
+   * Methods expose to js. Every method which will be called in js should add to this array.
+   */
+  public static final String[] METHODS = {SCROLL_TO_ELEMENT, ADD_RULE, GET_COMPONENT_RECT,
+      INVOKE_METHOD, GET_COMPONENT_DIRECTION, BATCH_BEGIN, BATCH_END};
+
+  public WXDomModule(WXSDKInstance instance){
+    mWXSDKInstance = instance;
+  }
+
+  public void callDomMethod(JSONObject task, long... parseNanos) {
+    if (task == null) {
+      return;
+    }
+    String method = (String) task.get(WXBridgeManager.METHOD);
+    JSONArray args = (JSONArray) task.get(WXBridgeManager.ARGS);
+    callDomMethod(method,args,parseNanos);
+  }
+
+  public Object callDomMethod(String method, JSONArray args, long... parseNanos) {
+
+    if (method == null) {
+      return null;
+    }
+
+    try {
+      switch (method) {
+        case GET_COMPONENT_DIRECTION: {
+          if(args == null){
+            return null;
+          }
+          new ActionGetLayoutDirection(mWXSDKInstance, args.getString(0), args.getString(1))
+                  .executeActionOnRender();
+          break;
+        }
+        case SCROLL_TO_ELEMENT:{
+          if (args == null) {
+            return null;
+          }
+          String ref = args.size() >= 1 ? args.getString(0) : null;
+          JSONObject options = args.size() >= 2 ? args.getJSONObject(1) : null;
+          new GraphicActionScrollToElement(mWXSDKInstance, ref, options)
+                  .executeActionOnRender();
+          break;
+        }
+        case ADD_RULE:{
+          if (args == null) {
+            return null;
+          }
+          new ActionAddRule(mWXSDKInstance.getInstanceId(), args.getString(0), args.getJSONObject(1))
+                  .executeAction();
+          break;
+        }
+        case GET_COMPONENT_RECT:{
+            if(args == null){
+                return null;
+            }
+            new ActionGetComponentRect(mWXSDKInstance, args.getString(0), args.getString(1))
+                    .executeActionOnRender();
+            break;
+        }
+        case INVOKE_METHOD: {
+          if(args == null){
+            return null;
+          }
+          // todo：no sure where the request com from
+          new ActionInvokeMethod(mWXSDKInstance.getInstanceId(), args.getString(0), args.getString(1), args.getJSONArray(2))
+                  .executeAction();
+          break;
+        }
+        case UPDATE_COMPONENT_DATA:
+          if(args == null || args.size() < 3){
+            return null;
+          }
+          new UpdateComponentDataAction(mWXSDKInstance, args.getString(0), JSONUtils.toJSON(args.get(1)), args.getString(2)).executeAction();
+          break;
+        case BATCH_BEGIN: {
+          if(args == null){
+            return null;
+          }
+          String ref = args.size() >= 1 ? args.getString(0) : null;
+          new GraphicActionBatchBegin(mWXSDKInstance, ref).executeActionOnRender();
+          break;
+        }
+        case BATCH_END: {
+          String ref = args.size() >= 1 ? args.getString(0) : null;
+          new GraphicActionBatchEnd(mWXSDKInstance, ref).executeActionOnRender();
+          break;
+        }
+        default:
+          WXLogUtils.e("Unknown dom action.");
+          break;
+      }
+
+      // todo TraceableAction
+//      if (WXTracing.isAvailable() && action instanceof TraceableAction) {
+//        String ref = null;
+//        String type = null;
+//        if (args.size() > 0) {
+//          if (args.size() >= 1) {
+//            if (args.get(0) instanceof String) {
+//              ref = args.getString(0);
+//            } else if (args.get(0) instanceof JSONObject) {
+//              ref = ((JSONObject) args.get(0)).getString("ref");
+//              type = ((JSONObject) args.get(0)).getString("type");
+//            }
+//          }
+//
+//          if (args.size() >= 2) {
+//            if (args.get(1) instanceof JSONObject) {
+//              ref = ((JSONObject) args.get(1)).getString("ref");
+//              type = ((JSONObject) args.get(1)).getString("type");
+//            }
+//          }
+//        }
+//        if (parseNanos != null && parseNanos.length == 1) {
+//          ((TraceableAction) action).mParseJsonNanos = parseNanos[0];
+//          ((TraceableAction) action).mStartMillis -= Stopwatch.nanosToMillis(parseNanos[0]);
+//        }
+//        ((TraceableAction) action).onStartDomExecute(mWXSDKInstance.getInstanceId(), method, ref, type, args.toJSONString());
+//      }
+    } catch (IndexOutOfBoundsException e) {
+      // no enougn args
+      e.printStackTrace();
+      WXLogUtils.e("Dom module call miss arguments.");
+    } catch (ClassCastException cce) {
+      WXLogUtils.e("Dom module call arguments format error!!");
+    }
+    return null;
+  }
+
+  public void invokeMethod(String ref, String method, JSONArray args){
+    if(ref == null || method == null){
+      return;
+    }
+
+    new ActionInvokeMethod(mWXSDKInstance.getInstanceId(), ref, method, args)
+            .executeAction();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/module/WXLocaleModule.java b/android/sdk/src/main/java/org/apache/weex/ui/module/WXLocaleModule.java
new file mode 100644
index 0000000..63cf9c2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/module/WXLocaleModule.java
@@ -0,0 +1,112 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.module;
+
+import android.content.Context;
+import android.content.res.Configuration;
+import android.content.res.Resources;
+import android.os.Build;
+import android.os.LocaleList;
+import android.text.TextUtils;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.common.WXModule;
+
+import java.util.Arrays;
+import java.util.List;
+import java.util.Locale;
+
+/**
+ * Created by moxun on 2017/9/26.
+ * <p>
+ * Ref: https://tools.ietf.org/html/bcp47
+ */
+
+public class WXLocaleModule extends WXModule {
+
+  @JSMethod(uiThread = false)
+  public String getLanguageSync() {
+    return getLanguageImpl();
+  }
+
+  @JSMethod(uiThread = false)
+  public void getLanguage(JSCallback callback) {
+    callback.invoke(getLanguageImpl());
+  }
+
+  private String getLanguageImpl() {
+    Locale locale;
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
+      locale = LocaleList.getDefault().get(0);
+    } else locale = Locale.getDefault();
+
+    String language = locale.getLanguage() + "-" + locale.getCountry();
+    return language;
+  }
+
+  @JSMethod(uiThread = false)
+  public List<String> getLanguages() {
+    String[] tags = getLanguageTags().split(",");
+    return Arrays.asList(tags);
+  }
+
+  @JSMethod(uiThread = false)
+  public void getLanguages(JSCallback callback) {
+    callback.invoke(getLanguageTags().split(","));
+  }
+
+  private String getLanguageTags() {
+    Context application = WXEnvironment.getApplication();
+    if (application != null) {
+      Resources res = application.getResources();
+      if (res != null) {
+        Configuration configuration = res.getConfiguration();
+        if (configuration != null) {
+          if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
+            LocaleList localeList = configuration.getLocales();
+            return localeList.toLanguageTags();
+          } else {
+            Locale local = configuration.locale;
+            if (local != null) {
+              return toLanguageTag(local);
+            }
+          }
+        }
+      }
+    }
+    return "";
+  }
+
+  private String toLanguageTag(Locale locale) {
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
+      return locale.toLanguageTag();
+    } else {
+      StringBuilder sb = new StringBuilder();
+      String language = locale.getLanguage();
+      String region = locale.getCountry();
+      sb.append(language);
+      if (!TextUtils.isEmpty(region)) {
+        sb.append("-").append(region);
+      }
+      return sb.toString();
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/module/WXMetaModule.java b/android/sdk/src/main/java/org/apache/weex/ui/module/WXMetaModule.java
new file mode 100644
index 0000000..5911229
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/module/WXMetaModule.java
@@ -0,0 +1,115 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.module;
+
+import android.app.Application;
+import android.content.Context;
+import android.content.pm.ApplicationInfo;
+import android.text.TextUtils;
+import android.widget.Toast;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+
+import java.net.URLDecoder;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Created by zhengshihan on 16/12/20.
+ */
+
+public class WXMetaModule extends WXModule {
+
+    public static final String WIDTH = "width";
+    public static final String DEVICE_WIDTH = "device-width";
+
+    @JSMethod(uiThread = false)
+    public void setViewport(String param) {
+        if (!TextUtils.isEmpty(param)) {
+            try {
+                param = URLDecoder.decode(param, "utf-8");
+                JSONObject jsObj = JSON.parseObject(param);
+                Context cxt = mWXSDKInstance.getContext();
+                // todo maybe getString(WIDTH) is "device-height"
+                if (DEVICE_WIDTH.endsWith(jsObj.getString(WIDTH))) {
+                    int width = (int)(WXViewUtils.getScreenWidth(cxt)/WXViewUtils.getScreenDensity(cxt));
+                    mWXSDKInstance.setInstanceViewPortWidth(width,true);
+                    WXLogUtils.d("[WXMetaModule] setViewport success[device-width]=" + width);
+                } else {
+                    int width = jsObj.getInteger(WIDTH);
+                    if (width > 0) {
+                        mWXSDKInstance.setInstanceViewPortWidth(width,true);
+                    }
+                    WXLogUtils.d("[WXMetaModule] setViewport success[width]=" + width);
+                }
+            } catch (Exception e) {
+                WXLogUtils.e("[WXMetaModule] alert param parse error ", e);
+            }
+        }
+    }
+
+    @JSMethod(uiThread = true)
+    public void openLog(String open) {
+        Application application = WXEnvironment.getApplication();
+        if(application == null){
+            return;
+        }
+        ApplicationInfo info = application.getApplicationInfo();
+        if((info.flags & ApplicationInfo.FLAG_DEBUGGABLE)!= 0){
+            if(WXUtils.getBoolean(open, true)) {
+                WXEnvironment.setApkDebugable(true);
+                if(mWXSDKInstance != null) {
+                    Toast.makeText(mWXSDKInstance.getContext(), "log open success", Toast.LENGTH_SHORT).show();
+                }
+            }else{
+                WXEnvironment.setApkDebugable(false);
+                if(mWXSDKInstance != null) {
+                    Toast.makeText(mWXSDKInstance.getContext(), "log close success", Toast.LENGTH_SHORT).show();
+                }
+            }
+        }
+    }
+
+    @JSMethod(uiThread = false)
+    public void getPageInfo(JSCallback callback) {
+        if(callback == null){
+            return;
+        }
+        List<WXSDKInstance> instances = WXSDKManager.getInstance().getWXRenderManager().getAllInstances();
+        Map<String,Object> map = new HashMap<>(4);
+        for(WXSDKInstance instance : instances){
+            if(TextUtils.isEmpty(instance.getBundleUrl())){
+                continue;
+            }
+            map.put(instance.getBundleUrl(), instance.getTemplateInfo());
+        }
+        callback.invoke(map);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/module/WXModalUIModule.java b/android/sdk/src/main/java/org/apache/weex/ui/module/WXModalUIModule.java
new file mode 100644
index 0000000..bbd0574
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/module/WXModalUIModule.java
@@ -0,0 +1,264 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.module;
+
+import android.annotation.SuppressLint;
+import android.app.Activity;
+import android.app.AlertDialog;
+import android.app.Dialog;
+import android.content.DialogInterface;
+import android.content.DialogInterface.OnClickListener;
+import android.text.TextUtils;
+import android.view.Gravity;
+import android.widget.EditText;
+import android.widget.Toast;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.JSCallback;
+import org.apache.weex.utils.WXLogUtils;
+import java.util.HashMap;
+import java.util.Map;
+import org.apache.weex.WXSDKEngine.DestroyableModule;
+
+
+/**
+ * WXModalUIModule module provide toast、alert、confirm、prompt to display the message.
+ * for example(weex JS):
+ * this.$call('modal','toast',{'message':'test toast','duration': 2.0});
+ */
+public class WXModalUIModule extends DestroyableModule {
+
+  public static final String OK = "OK";
+  public static final String CANCEL = "Cancel";
+  public static final String RESULT = "result";
+  public static final String DATA = "data";
+  public static final String MESSAGE = "message";
+  public static final String DURATION = "duration";
+  public static final String OK_TITLE = "okTitle";
+  public static final String CANCEL_TITLE = "cancelTitle";
+  public static final String DEFAULT = "default";
+  private Toast toast;
+  private Dialog activeDialog;
+
+  @SuppressLint("ShowToast")
+  @JSMethod(uiThread = true)
+  public void toast(JSONObject jsObj) {
+    if(mWXSDKInstance.getContext() == null){
+      return;
+    }
+    String message = "";
+    int duration = Toast.LENGTH_SHORT;
+    if (jsObj != null) {
+      try {
+        message = jsObj.getString(MESSAGE);
+        if(jsObj.containsKey(DURATION)) {
+          duration = jsObj.getInteger(DURATION);
+        }
+      } catch (Exception e) {
+        WXLogUtils.e("[WXModalUIModule] alert param parse error ", e);
+      }
+    }
+    if (TextUtils.isEmpty(message)) {
+      WXLogUtils.e("[WXModalUIModule] toast param parse is null ");
+      return;
+    }
+
+    if (duration > 3) {
+      duration = Toast.LENGTH_LONG;
+    } else {
+      duration = Toast.LENGTH_SHORT;
+    }
+    if (toast == null) {
+      toast = Toast.makeText(mWXSDKInstance.getContext(), message, duration);
+    } else {
+      toast.setDuration(duration);
+      toast.setText(message);
+    }
+    toast.setGravity(Gravity.CENTER, 0, 0);
+    toast.show();
+  }
+
+  @JSMethod(uiThread = true)
+  public void alert(JSONObject jsObj, final JSCallback callback) {
+
+    if (mWXSDKInstance.getContext() instanceof Activity) {
+
+      String message = "";
+      String okTitle = OK;
+      if (jsObj != null) {
+        try {
+          message = jsObj.getString(MESSAGE);
+          okTitle = jsObj.getString(OK_TITLE);
+        } catch (Exception e) {
+          WXLogUtils.e("[WXModalUIModule] alert param parse error ", e);
+        }
+      }
+      if (TextUtils.isEmpty(message)) {
+        message = "";
+      }
+      AlertDialog.Builder builder = new AlertDialog.Builder(mWXSDKInstance.getContext());
+      builder.setMessage(message);
+
+      final String okTitle_f = TextUtils.isEmpty(okTitle) ? OK : okTitle;
+      builder.setPositiveButton(okTitle_f, new OnClickListener() {
+        @Override
+        public void onClick(DialogInterface dialog, int which) {
+          if (callback != null) {
+            callback.invoke(okTitle_f);
+          }
+        }
+      });
+      AlertDialog alertDialog = builder.create();
+      alertDialog.setCanceledOnTouchOutside(false);
+      alertDialog.show();
+      tracking(alertDialog);
+    } else {
+      WXLogUtils.e("[WXModalUIModule] when call alert mWXSDKInstance.getContext() must instanceof Activity");
+    }
+  }
+
+  @JSMethod(uiThread = true)
+  public void confirm(JSONObject jsObj, final JSCallback callback) {
+
+    if (mWXSDKInstance.getContext() instanceof Activity) {
+      String message = "";
+      String okTitle = OK;
+      String cancelTitle = CANCEL;
+
+      if (jsObj != null) {
+        try {
+          message = jsObj.getString(MESSAGE);
+          okTitle = jsObj.getString(OK_TITLE);
+          cancelTitle = jsObj.getString(CANCEL_TITLE);
+        } catch (Exception e) {
+          WXLogUtils.e("[WXModalUIModule] confirm param parse error ", e);
+        }
+      }
+      if (TextUtils.isEmpty(message)) {
+        message = "";
+      }
+      AlertDialog.Builder builder = new AlertDialog.Builder(mWXSDKInstance.getContext());
+      builder.setMessage(message);
+
+      final String okTitleFinal = TextUtils.isEmpty(okTitle) ? OK : okTitle;
+      final String cancelTitleFinal = TextUtils.isEmpty(cancelTitle) ? CANCEL : cancelTitle;
+
+      builder.setPositiveButton(okTitleFinal, new OnClickListener() {
+        @Override
+        public void onClick(DialogInterface dialog, int which) {
+          if (callback != null) {
+            callback.invoke(okTitleFinal);
+          }
+        }
+      });
+      builder.setNegativeButton(cancelTitleFinal, new OnClickListener() {
+        @Override
+        public void onClick(DialogInterface dialog, int which) {
+          if (callback != null) {
+            callback.invoke(cancelTitleFinal);
+          }
+        }
+      });
+      AlertDialog alertDialog = builder.create();
+      alertDialog.setCanceledOnTouchOutside(false);
+      alertDialog.show();
+      tracking(alertDialog);
+    } else {
+      WXLogUtils.e("[WXModalUIModule] when call confirm mWXSDKInstance.getContext() must instanceof Activity");
+    }
+  }
+
+  @JSMethod(uiThread = true)
+  public void prompt(JSONObject jsObj, final JSCallback callback) {
+    if (mWXSDKInstance.getContext() instanceof Activity) {
+      String message = "";
+      String defaultValue = "";
+      String okTitle = OK;
+      String cancelTitle = CANCEL;
+
+      if (jsObj != null) {
+        try {
+          message = jsObj.getString(MESSAGE);
+          okTitle = jsObj.getString(OK_TITLE);
+          cancelTitle = jsObj.getString(CANCEL_TITLE);
+          defaultValue = jsObj.getString(DEFAULT);
+        } catch (Exception e) {
+          WXLogUtils.e("[WXModalUIModule] confirm param parse error ", e);
+        }
+      }
+
+      if (TextUtils.isEmpty(message)) {
+        message = "";
+      }
+      AlertDialog.Builder builder = new AlertDialog.Builder(mWXSDKInstance.getContext());
+      builder.setMessage(message);
+
+      final EditText editText = new EditText(mWXSDKInstance.getContext());
+      editText.setText(defaultValue);
+      builder.setView(editText);
+      final String okTitleFinal = TextUtils.isEmpty(okTitle) ? OK : okTitle;
+      final String cancelTitleFinal = TextUtils.isEmpty(cancelTitle) ? CANCEL : cancelTitle;
+      builder.setPositiveButton(okTitleFinal, new OnClickListener() {
+        @Override
+        public void onClick(DialogInterface dialog, int which) {
+          if (callback != null) {
+            Map<String, Object> result = new HashMap<String, Object>();
+            result.put(RESULT, okTitleFinal);
+            result.put(DATA, editText.getText().toString());
+            callback.invoke(result);
+          }
+        }
+      }).setNegativeButton(cancelTitleFinal, new OnClickListener() {
+        @Override
+        public void onClick(DialogInterface dialog, int which) {
+          if (callback != null) {
+            Map<String, Object> result = new HashMap<String, Object>();
+            result.put(RESULT, cancelTitleFinal);
+            result.put(DATA, editText.getText().toString());
+            callback.invoke(result);
+          }
+
+        }
+      });
+      AlertDialog alertDialog = builder.create();
+      alertDialog.setCanceledOnTouchOutside(false);
+      alertDialog.show();
+      tracking(alertDialog);
+    } else {
+      WXLogUtils.e("when call prompt mWXSDKInstance.getContext() must instanceof Activity");
+    }
+  }
+
+  private void tracking(Dialog dialog) {
+    activeDialog = dialog;
+    dialog.setOnDismissListener(new DialogInterface.OnDismissListener() {
+      @Override
+      public void onDismiss(DialogInterface dialog) {
+        activeDialog = null;
+      }
+    });
+  }
+
+  @Override
+  public void destroy() {
+    if (activeDialog != null && activeDialog.isShowing()) {
+      activeDialog.dismiss();
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/module/WXTimerModule.java b/android/sdk/src/main/java/org/apache/weex/ui/module/WXTimerModule.java
new file mode 100644
index 0000000..f0d419f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/module/WXTimerModule.java
@@ -0,0 +1,211 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.module;
+
+import android.annotation.SuppressLint;
+import android.os.Handler;
+import android.os.Message;
+import android.support.annotation.FloatRange;
+import android.support.annotation.IntDef;
+import android.support.annotation.IntRange;
+import android.support.annotation.VisibleForTesting;
+import android.util.SparseArray;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.bridge.WXBridgeManager;
+import org.apache.weex.bridge.WXHashMap;
+import org.apache.weex.bridge.WXJSObject;
+import org.apache.weex.common.Destroyable;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.utils.WXJsonUtils;
+import org.apache.weex.utils.WXLogUtils;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.util.ArrayList;
+import java.util.HashMap;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.common.WXJSBridgeMsgType;
+
+public class WXTimerModule extends WXModule implements Destroyable, Handler.Callback {
+
+  @IntDef({WXJSBridgeMsgType.MODULE_TIMEOUT, WXJSBridgeMsgType.MODULE_INTERVAL})
+  @Retention(RetentionPolicy.SOURCE)
+  @interface MessageType {}
+
+  private final static String TAG = "timer";
+  private Handler handler;
+  private SparseArray<Integer> antiIntAutoBoxing;
+
+  @SuppressLint("UseSparseArrays")
+  public WXTimerModule() {
+    handler = new Handler(WXBridgeManager.getInstance().getJSLooper(), this);
+    antiIntAutoBoxing = new SparseArray<>();
+  }
+
+
+  @JSMethod(uiThread = false)
+  public void setTimeout(@IntRange(from = 1) int funcId, @FloatRange(from = 0) float delay) {
+    if(mWXSDKInstance != null) {
+      postOrHoldMessage(WXJSBridgeMsgType.MODULE_TIMEOUT, funcId, (int) delay, WXUtils.parseInt(mWXSDKInstance.getInstanceId()));
+      if (null != mWXSDKInstance.getWXPerformance()){
+        mWXSDKInstance.getWXPerformance().timerInvokeCount++;
+      }
+      mWXSDKInstance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_TIMER_NUM,1);
+    }
+  }
+
+  @JSMethod(uiThread = false)
+  public void setInterval(@IntRange(from = 1) int funcId, @FloatRange(from = 0) float interval) {
+    if(mWXSDKInstance != null) {
+      postOrHoldMessage(WXJSBridgeMsgType.MODULE_INTERVAL, funcId, (int) interval, WXUtils.parseInt(mWXSDKInstance.getInstanceId()));
+      if (null != mWXSDKInstance.getWXPerformance()){
+        mWXSDKInstance.getWXPerformance().timerInvokeCount++;
+      }
+      mWXSDKInstance.getApmForInstance().updateFSDiffStats(WXInstanceApm.KEY_PAGE_STATS_FS_TIMER_NUM,1);
+    }
+  }
+
+  @JSMethod(uiThread = false)
+  public void clearTimeout(@IntRange(from = 1) int funcId) {
+    if (funcId <= 0) {
+      return;
+    }
+    removeOrHoldMessage(WXJSBridgeMsgType.MODULE_TIMEOUT, funcId);
+  }
+
+  @JSMethod(uiThread = false)
+  public void clearInterval(@IntRange(from = 1) int funcId) {
+    if (funcId <= 0) {
+      return;
+    }
+    removeOrHoldMessage(WXJSBridgeMsgType.MODULE_INTERVAL, funcId);
+  }
+
+  @Override
+  public void destroy() {
+    if (handler != null) {
+      if(WXEnvironment.isApkDebugable()) {
+        WXLogUtils.d(TAG, "Timer Module removeAllMessages: ");
+      }
+      handler.removeCallbacksAndMessages(null);
+      antiIntAutoBoxing.clear();
+    }
+  }
+
+  @Override
+  public boolean handleMessage(Message msg) {
+    boolean ret = false;
+    WXJSObject[] args;
+    if (msg != null) {
+      int what = msg.what;
+      if(WXEnvironment.isApkDebugable()) {
+        WXLogUtils.d(TAG, "Timer Module handleMessage : " + msg.what);
+      }
+      switch (what) {
+        case WXJSBridgeMsgType.MODULE_TIMEOUT:
+          if (msg.obj == null) {
+            break;
+          }
+          checkIfTimerInBack(msg.arg1);
+          args = createTimerArgs(msg.arg1, (Integer) msg.obj, false);
+          WXBridgeManager.getInstance().invokeExecJS(String.valueOf(msg.arg1), null, WXBridgeManager.METHOD_CALL_JS, args, true);
+          ret = true;
+          break;
+        case WXJSBridgeMsgType.MODULE_INTERVAL:
+          if (msg.obj == null) {
+            break;
+          }
+          checkIfTimerInBack(msg.arg1);
+          postMessage(WXJSBridgeMsgType.MODULE_INTERVAL, (Integer) msg.obj, msg.arg2, msg.arg1);
+          args = createTimerArgs(msg.arg1, (Integer) msg.obj, true);
+          WXBridgeManager.getInstance().invokeExecJS(String.valueOf(msg.arg1), null, WXBridgeManager.METHOD_CALL_JS, args, true);
+          ret = true;
+          break;
+        default:
+          break;
+      }
+    }
+    return ret;
+  }
+
+  private void checkIfTimerInBack(int instanceId){
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(String.valueOf(instanceId));
+    if (null == instance){
+      return;
+    }
+    if (instance.isViewDisAppear()){
+      instance.getApmForInstance().updateDiffStats(WXInstanceApm.KEY_PAGE_TIMER_BACK_NUM,1);
+    }
+  }
+
+  @VisibleForTesting
+  void setHandler(Handler handler) {
+    this.handler = handler;
+  }
+
+  private WXJSObject[] createTimerArgs(int instanceId, int funcId, boolean keepAlive) {
+    ArrayList<Object> argsList = new ArrayList<>();
+    argsList.add(funcId);
+    argsList.add(new HashMap<>());
+    argsList.add(keepAlive);
+    WXHashMap<String, Object> task = new WXHashMap<>();
+    task.put(WXBridgeManager.KEY_METHOD, WXBridgeManager.METHOD_CALLBACK);
+    task.put(WXBridgeManager.KEY_ARGS, argsList);
+    Object[] tasks = {task};
+    return new WXJSObject[]{
+            new WXJSObject(WXJSObject.String, String.valueOf(instanceId)),
+            new WXJSObject(WXJSObject.JSON,
+                    WXJsonUtils.fromObjectToJSONString(tasks))};
+  }
+
+  private void postOrHoldMessage(@MessageType final int what,final int funcId,final int interval,final int instanceId) {
+    if(mWXSDKInstance.isPreRenderMode()) {
+      postMessage(what,funcId,interval,instanceId);
+    } else {
+      postMessage(what,funcId,interval,instanceId);
+    }
+  }
+
+  private void removeOrHoldMessage(@MessageType final int what,final int funcId) {
+    if(mWXSDKInstance.isPreRenderMode()) {
+      handler.removeMessages(what, antiIntAutoBoxing.get(funcId, funcId));
+    } else {
+      handler.removeMessages(what, antiIntAutoBoxing.get(funcId, funcId));
+    }
+  }
+
+  private void postMessage(@MessageType int what,
+                           @IntRange(from = 1) int funcId,
+                           @IntRange(from = 0) int interval, int instanceId) {
+    if (interval < 0 || funcId <= 0) {
+      WXLogUtils.e(TAG, "interval < 0 or funcId <=0");
+    } else {
+      if(antiIntAutoBoxing.get(funcId) == null) {
+        antiIntAutoBoxing.put(funcId, funcId);
+      }
+      Message message = handler
+              .obtainMessage(what, instanceId, interval, antiIntAutoBoxing.get(funcId));
+      handler.sendMessageDelayed(message, interval);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/module/WXWebViewModule.java b/android/sdk/src/main/java/org/apache/weex/ui/module/WXWebViewModule.java
new file mode 100644
index 0000000..2513d36
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/module/WXWebViewModule.java
@@ -0,0 +1,70 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.module;
+
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.annotation.JSMethod;
+import org.apache.weex.common.WXModule;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXWeb;
+
+public class WXWebViewModule extends WXModule {
+
+    private enum Action {
+        reload,
+        goBack,
+        goForward,
+        postMessage
+    }
+
+    @JSMethod(uiThread = true)
+    public void goBack(String ref) {
+        action(Action.goBack, ref);
+    }
+
+    @JSMethod(uiThread = true)
+    public void goForward(String ref) {
+        action(Action.goForward, ref);
+    }
+
+    @JSMethod(uiThread = true)
+    public void reload(String ref) {
+        action(Action.reload, ref);
+    }
+
+    @JSMethod(uiThread = true)
+    public void postMessage(String ref, Object msg) {
+        action(Action.postMessage, ref, msg);
+    }
+
+    private void action(Action action, String ref, Object data) {
+        WXComponent webComponent =
+            WXSDKManager.getInstance()
+                .getWXRenderManager()
+                .getWXComponent(mWXSDKInstance.getInstanceId(), ref);
+        if(webComponent instanceof WXWeb) {
+            ((WXWeb) webComponent).setAction(action.name(), data);
+        }
+    }
+
+    private void action(Action action, String ref) {
+        action(action, ref, null);
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/BaseFrameLayout.java b/android/sdk/src/main/java/org/apache/weex/ui/view/BaseFrameLayout.java
new file mode 100644
index 0000000..8c008f7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/BaseFrameLayout.java
@@ -0,0 +1,79 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.drawable.Drawable;
+import android.support.annotation.NonNull;
+import android.widget.FrameLayout;
+import org.apache.weex.ui.flat.widget.Widget;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXViewUtils;
+import java.util.List;
+
+public class BaseFrameLayout extends FrameLayout{
+    private List<Widget> mWidgets;
+
+    public BaseFrameLayout(Context context){
+        super(context);
+    }
+
+    @Override
+    protected void dispatchDraw(Canvas canvas) {
+        try {
+            dispatchDrawInterval(canvas);
+        } catch (Throwable e) {
+            WXLogUtils.e(WXLogUtils.getStackTrace(e));
+        }
+    }
+
+    protected void dispatchDrawInterval(Canvas canvas) {
+        if (mWidgets != null) {
+            canvas.save();
+            canvas.translate(getPaddingLeft(), getPaddingTop());
+            for (Widget widget : mWidgets) {
+                widget.draw(canvas);
+            }
+            canvas.restore();
+        } else {
+            WXViewUtils.clipCanvasWithinBorderBox(this, canvas);
+            super.dispatchDraw(canvas);
+        }
+    }
+    public void mountFlatGUI(List<Widget> widgets){
+        this.mWidgets = widgets;
+        if (mWidgets != null) {
+            setWillNotDraw(true);
+        }
+        invalidate();
+    }
+
+    public void unmountFlatGUI(){
+        mWidgets = null;
+        setWillNotDraw(false);
+        invalidate();
+    }
+
+    @Override
+    protected boolean verifyDrawable(@NonNull Drawable who) {
+        return mWidgets != null || super.verifyDrawable(who);
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/IRenderResult.java b/android/sdk/src/main/java/org/apache/weex/ui/view/IRenderResult.java
new file mode 100644
index 0000000..fc46fe9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/IRenderResult.java
@@ -0,0 +1,26 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+
+import org.apache.weex.ui.component.WXComponent;
+
+public interface IRenderResult<T extends WXComponent> {
+    T getComponent();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/IRenderStatus.java b/android/sdk/src/main/java/org/apache/weex/ui/view/IRenderStatus.java
new file mode 100644
index 0000000..ae7effe
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/IRenderStatus.java
@@ -0,0 +1,28 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.ui.view;
+
+
+import org.apache.weex.ui.component.WXComponent;
+
+public interface IRenderStatus<T extends WXComponent> {
+
+  public void holdComponent(T component);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/IWXScroller.java b/android/sdk/src/main/java/org/apache/weex/ui/view/IWXScroller.java
new file mode 100644
index 0000000..a2c8314
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/IWXScroller.java
@@ -0,0 +1,24 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+public interface IWXScroller {
+
+  void destroy();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/IWXTextView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/IWXTextView.java
new file mode 100644
index 0000000..da71307
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/IWXTextView.java
@@ -0,0 +1,24 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+public interface IWXTextView {
+
+  CharSequence getText();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/IWebView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/IWebView.java
new file mode 100644
index 0000000..7a0f8a8
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/IWebView.java
@@ -0,0 +1,52 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.view.View;
+
+import java.util.Map;
+
+public interface IWebView {
+    public View getView();
+    public void destroy();
+    public void loadUrl(String url);
+    public void loadDataWithBaseURL(String source);
+    public void reload();
+    public void goBack();
+    public void goForward();
+    public void postMessage(Object msg);
+    public void setShowLoading(boolean shown);
+    public void setOnErrorListener(OnErrorListener listener);
+    public void setOnPageListener(OnPageListener listener);
+    public void setOnMessageListener(OnMessageListener listener);
+
+    public interface OnErrorListener {
+        public void onError(String type, Object message);
+    }
+
+    public interface OnPageListener {
+        public void onReceivedTitle(String title);
+        public void onPageStart(String url);
+        public void onPageFinish(String url, boolean canGoBack, boolean canGoForward);
+    }
+
+    public interface OnMessageListener {
+        public void onMessage(Map<String, Object> params);
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXBaseCircleIndicator.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXBaseCircleIndicator.java
new file mode 100644
index 0000000..070fda4
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXBaseCircleIndicator.java
@@ -0,0 +1,228 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.Paint;
+import android.graphics.Paint.Style;
+import android.support.v4.view.ViewPager;
+import android.support.v4.view.ViewPager.OnPageChangeListener;
+import android.util.AttributeSet;
+import android.view.MotionEvent;
+import android.widget.FrameLayout;
+
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import org.apache.weex.utils.WXViewUtils;
+
+
+public class WXBaseCircleIndicator extends FrameLayout implements WXGestureObservable {
+
+  private final Paint mPaintPage = new Paint();
+  private final Paint mPaintFill = new Paint();
+  private WXGesture wxGesture;
+  private WXCircleViewPager mCircleViewPager;
+
+  /**
+   * Radius of the circle
+   */
+  private float radius;
+  /**
+   * Padding of the circle
+   */
+  private float circlePadding;
+  /**
+   * Fill color of unselected circle
+   */
+  private int pageColor = Color.LTGRAY;
+  /**
+   * Fill color of the selected circle
+   */
+  private int fillColor = Color.DKGRAY;
+  private int realCurrentItem;
+
+  private OnPageChangeListener mListener;
+
+
+  public WXBaseCircleIndicator(Context context) {
+    super(context);
+    init();
+  }
+
+  private void init() {
+    radius = WXViewUtils.dip2px(5);
+    circlePadding = WXViewUtils.dip2px(5);
+    pageColor = Color.LTGRAY;
+    fillColor = Color.DKGRAY;
+
+    mPaintFill.setStyle(Style.FILL);
+    mPaintFill.setAntiAlias(true);
+    mPaintPage.setAntiAlias(true);
+    mPaintPage.setColor(pageColor);
+    mPaintFill.setStyle(Style.FILL);
+    mPaintFill.setColor(fillColor);
+    this.setWillNotDraw(false);
+
+  }
+
+  /**
+   * @param context
+   * @param attrs
+   */
+  public WXBaseCircleIndicator(Context context, AttributeSet attrs) {
+    super(context, attrs);
+    init();
+  }
+
+  /**
+   * @param viewPager the mCircleViewPager to set
+   */
+  public void setCircleViewPager(WXCircleViewPager viewPager) {
+    mCircleViewPager = viewPager;
+    if (mCircleViewPager != null) {
+      if (mListener == null) {
+        mListener = new ViewPager.SimpleOnPageChangeListener() {
+          @Override
+          public void onPageSelected(int position) {
+            realCurrentItem = mCircleViewPager.getRealCurrentItem();
+            invalidate();
+          }
+        };
+      }
+      this.mCircleViewPager.addOnPageChangeListener(mListener);
+      this.realCurrentItem = mCircleViewPager.getRealCurrentItem();
+      if (realCurrentItem < 0) {
+        realCurrentItem = 0;
+      }
+    }
+    requestLayout();
+  }
+
+  /**
+   * @param radius the radius to set
+   */
+  public void setRadius(float radius) {
+    this.radius = radius;
+  }
+
+  /**
+   * @param fillColor the fillColor to set
+   */
+  public void setFillColor(int fillColor) {
+    this.fillColor = fillColor;
+    mPaintFill.setColor(fillColor);
+  }
+
+  public void setPageColor(int pageColor) {
+    this.pageColor = pageColor;
+    mPaintPage.setColor(pageColor);
+  }
+
+  /**
+   * @return the realCurrentItem
+   */
+  public int getRealCurrentItem() {
+    return realCurrentItem;
+  }
+
+  /**
+   * @param realCurrentItem the realCurrentItem to set
+   */
+  public void setRealCurrentItem(int realCurrentItem) {
+    this.realCurrentItem = realCurrentItem;
+    invalidate();
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  @Override
+  public boolean dispatchTouchEvent(MotionEvent event) {
+    boolean result = super.dispatchTouchEvent(event);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, event);
+    }
+    return result;
+  }
+
+  @Override
+  protected void onDraw(Canvas canvas) {
+    super.onDraw(canvas);
+
+    float dotWidth = (circlePadding + radius) * 2;
+
+    float firstCenterX = getWidth() / 2 - (dotWidth * (getCount() - 1) / 2);
+    float firstCenterY = getHeight() / 2 + getPaddingTop();
+
+    for (int i = 0; i < getCount(); i++) {
+      float dx = firstCenterX + dotWidth * i;
+      float dy = firstCenterY;
+      if (i != realCurrentItem) {
+        canvas.drawCircle(dx, dy, radius, mPaintPage);
+      } else {
+        canvas.drawCircle(dx, dy, radius, mPaintFill);
+      }
+    }
+  }
+
+  @Override
+  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+
+    int viewWidth;
+    int viewHeight;
+
+    int widthMode = MeasureSpec.getMode(widthMeasureSpec);
+    int widthSize = MeasureSpec.getSize(widthMeasureSpec);
+    int heightMode = MeasureSpec.getMode(heightMeasureSpec);
+    int heightSize = MeasureSpec.getSize(heightMeasureSpec);
+
+    if (widthMode == MeasureSpec.EXACTLY) {
+      viewWidth = widthSize;
+    } else {
+      viewWidth = (int) (getPaddingLeft() + radius * 2 * getCount() + circlePadding * (getCount() - 1) + getPaddingRight()) + 1;
+    }
+
+    if (heightMode == MeasureSpec.EXACTLY) {
+      viewHeight = heightSize;
+    } else {
+      viewHeight = (int) (getPaddingTop() + radius * 2 + getPaddingBottom()) + 1;
+    }
+    setMeasuredDimension(viewWidth, viewHeight);
+  }
+
+  /**
+   * @return the count
+   */
+  public int getCount() {
+    if (mCircleViewPager == null || mCircleViewPager.getAdapter() == null) {
+      return 0;
+    }
+    return mCircleViewPager.getRealCount();
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXBaseRefreshLayout.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXBaseRefreshLayout.java
new file mode 100644
index 0000000..5599581
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXBaseRefreshLayout.java
@@ -0,0 +1,28 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.content.Context;
+
+public class WXBaseRefreshLayout extends WXFrameLayout {
+
+  public WXBaseRefreshLayout(Context context) {
+    super(context);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXCircleIndicator.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXCircleIndicator.java
new file mode 100644
index 0000000..4e73942
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXCircleIndicator.java
@@ -0,0 +1,29 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.content.Context;
+
+public class WXCircleIndicator extends WXBaseCircleIndicator {
+
+  public WXCircleIndicator(Context context) {
+    super(context);
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXCirclePageAdapter.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXCirclePageAdapter.java
new file mode 100644
index 0000000..83edc06
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXCirclePageAdapter.java
@@ -0,0 +1,203 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.support.v4.view.PagerAdapter;
+import android.view.View;
+import android.view.ViewGroup;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+public class WXCirclePageAdapter extends PagerAdapter {
+
+  /**
+   * Subviews
+   */
+  private List<View> views = new ArrayList<>();
+  private List<View> shadow = new ArrayList<>();
+  private boolean needLoop = true;
+
+  public boolean isRTL = false;
+  private List<View> originalViews = new ArrayList<>();
+
+  public WXCirclePageAdapter(List<View> views, boolean needLoop) {
+    super();
+    this.views = new ArrayList<>(views);
+    this.originalViews = new ArrayList<>(views);
+    this.needLoop = needLoop;
+  }
+
+  public void setLayoutDirectionRTL(boolean isRTL) {
+    if (isRTL == this.isRTL) return;
+    this.isRTL = isRTL;
+    this.views = new ArrayList<>(this.originalViews);
+    if (isRTL) {
+      Collections.reverse(this.views);
+    }
+    ensureShadow();
+  }
+
+  public WXCirclePageAdapter() {
+    this(true);
+  }
+
+  public WXCirclePageAdapter(boolean needLoop) {
+    super();
+    this.needLoop = needLoop;
+  }
+
+  public void addPageView(View view) {
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("onPageSelected >>>> addPageView");
+    }
+
+    originalViews.add(view);
+    if (this.isRTL) {
+      views.add(0, view);
+    } else {
+      views.add(view);
+    }
+    ensureShadow();
+  }
+
+  public void removePageView(View view) {
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("onPageSelected >>>> removePageView");
+    }
+    views.remove(view);
+    originalViews.remove(view);
+    ensureShadow();
+  }
+
+  public void replacePageView(View oldView, View newView) {
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("onPageSelected >>>> replacePageView");
+    }
+
+    int index = views.indexOf(oldView);
+    views.remove(index);
+    views.add(index, newView);
+    ensureShadow();
+
+    index = originalViews.indexOf(oldView);
+    originalViews.remove(index);
+    originalViews.add(index, newView);
+  }
+
+  @Override
+  public int getCount() {
+    return shadow.size();
+  }
+
+  public int getRealCount() {
+    return views.size();
+  }
+
+  @Override
+  public Object instantiateItem(ViewGroup container, int position) {
+    View pageView = null;
+    try {
+      pageView = shadow.get(position);
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.d("onPageSelected >>>> instantiateItem >>>>> position:" + position + ",position % getRealCount()" + position % getRealCount());
+      }
+      if (pageView.getParent() == null) {
+        container.addView(pageView);
+      } else {
+        ((ViewGroup) pageView.getParent()).removeView(pageView);
+        container.addView(pageView);
+      }
+    } catch (Exception e) {
+      WXLogUtils.e("[CirclePageAdapter] instantiateItem: ", e);
+    }
+    return pageView;
+  }
+
+  @Override
+  public void destroyItem(ViewGroup container, int position, Object object) {
+    if (WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("onPageSelected >>>> destroyItem >>>>> position:" + position);
+    }
+    // container.removeView((View) object);
+  }
+
+  @Override
+  public boolean isViewFromObject(View view, Object object) {
+    return view == object;
+  }
+
+  @Override
+  public int getItemPosition(Object object) {
+    return POSITION_NONE;
+  }
+
+  public int getPagePosition(View page) {
+    return views.indexOf(page);
+  }
+
+  public int getItemIndex(Object object) {
+    if (object instanceof View) {
+      return views.indexOf(object);
+    } else {
+      return -1;
+    }
+  }
+
+  public List<View> getViews(){
+    return views;
+  }
+
+  private void ensureShadow() {
+    List<View> temp = new ArrayList<>();
+    if (needLoop && views.size() > 2) {
+      temp.add(0, views.get(views.size() - 1));
+      for (View view : views) {
+        temp.add(view);
+      }
+      temp.add(views.get(0));
+    } else {
+      temp.addAll(views);
+    }
+    shadow.clear();
+    notifyDataSetChanged();
+    shadow.addAll(temp);
+    notifyDataSetChanged();
+  }
+
+  public int getRealPosition(int shadowPosition) {
+    if (shadowPosition < 0 || shadowPosition >= shadow.size()) {
+      return -1;
+    } else {
+      return getItemIndex(shadow.get(shadowPosition));
+    }
+  }
+
+  public int getFirst() {
+    if (needLoop && views.size() > 2) {
+      return 1;
+    } else {
+      return 0;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXCircleViewPager.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXCircleViewPager.java
new file mode 100644
index 0000000..65e8d8a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXCircleViewPager.java
@@ -0,0 +1,341 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.os.Handler;
+import android.os.Looper;
+import android.os.Message;
+import android.support.v4.view.PagerAdapter;
+import android.support.v4.view.ViewPager;
+import android.util.AttributeSet;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.animation.Interpolator;
+
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.lang.reflect.Field;
+
+/**
+ */
+@SuppressLint("HandlerLeak")
+public class WXCircleViewPager extends ViewPager implements WXGestureObservable {
+
+  private final int SCROLL_TO_NEXT = 1;
+  private WXGesture wxGesture;
+  private boolean isAutoScroll;
+  private long intervalTime = 3 * 1000;
+  private WXSmoothScroller mScroller;
+  private boolean needLoop = true;
+  private boolean scrollable = true;
+  private int mState = ViewPager.SCROLL_STATE_IDLE;
+  private Handler mAutoScrollHandler = new Handler(Looper.getMainLooper()) {
+    @Override
+    public void handleMessage(Message msg) {
+      if (msg.what == SCROLL_TO_NEXT) {
+        WXLogUtils.d("[CircleViewPager] trigger auto play action");
+        showNextItem();
+        this.sendEmptyMessageDelayed(SCROLL_TO_NEXT, intervalTime);
+        return;
+      }
+      super.handleMessage(msg);
+    }
+  };
+
+  @SuppressLint("NewApi")
+  public WXCircleViewPager(Context context) {
+    super(context);
+    init();
+  }
+
+  private void init() {
+    setOverScrollMode(View.OVER_SCROLL_NEVER);
+
+    addOnPageChangeListener(new OnPageChangeListener() {
+      @Override
+      public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
+
+      }
+
+      @Override
+      public void onPageSelected(int position) {
+
+      }
+
+      @Override
+      public void onPageScrollStateChanged(int state) {
+        mState = state;
+        WXCirclePageAdapter adapter = getCirclePageAdapter();
+        int currentItemInternal = WXCircleViewPager.super.getCurrentItem();
+        if (needLoop && state == ViewPager.SCROLL_STATE_IDLE && adapter.getCount() > 1) {
+          if (currentItemInternal == adapter.getCount() - 1) {
+            superSetCurrentItem(1, false);
+          } else if (currentItemInternal == 0) {
+            superSetCurrentItem(adapter.getCount() - 2, false);
+          }
+        }
+      }
+    });
+
+    postInitViewPager();
+  }
+
+  /**
+   * Override the Scroller instance with our own class so we can change the
+   * duration
+   */
+  private void postInitViewPager() {
+    if (isInEditMode()) {
+      return;
+    }
+    try {
+      Field scroller = ViewPager.class.getDeclaredField("mScroller");
+      scroller.setAccessible(true);
+      Field interpolator = ViewPager.class
+              .getDeclaredField("sInterpolator");
+      interpolator.setAccessible(true);
+
+      mScroller = new WXSmoothScroller(getContext(),
+              (Interpolator) interpolator.get(null));
+      scroller.set(this, mScroller);
+    } catch (Exception e) {
+      WXLogUtils.e("[CircleViewPager] postInitViewPager: ", e);
+    }
+  }
+
+  @SuppressLint("NewApi")
+  public WXCircleViewPager(Context context, AttributeSet attrs) {
+    super(context, attrs);
+    init();
+  }
+
+  @Override
+  public int getCurrentItem() {
+    return getRealCurrentItem();
+  }
+
+  public int superGetCurrentItem() {
+    return super.getCurrentItem();
+  }
+
+  @Override
+  public boolean onInterceptTouchEvent(MotionEvent ev) {
+    try {
+      return scrollable && super.onInterceptTouchEvent(ev);
+    } catch (IllegalArgumentException e) {
+      e.printStackTrace();
+    } catch (ArrayIndexOutOfBoundsException e) {
+      e.printStackTrace();
+    }
+    return false;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent ev) {
+    if(!scrollable) {
+      return true;
+    }
+    return super.onTouchEvent(ev);
+  }
+
+  @Override
+  public void scrollTo(int x, int y) {
+    if(scrollable || mState != ViewPager.SCROLL_STATE_DRAGGING) {
+      super.scrollTo(x, y);
+    }
+  }
+
+  /**
+   * Start auto scroll. Must be called after {@link #setAdapter(PagerAdapter)}
+   */
+  public void startAutoScroll() {
+    isAutoScroll = true;
+    mAutoScrollHandler.removeCallbacksAndMessages(null);
+    mAutoScrollHandler.sendEmptyMessageDelayed(SCROLL_TO_NEXT, intervalTime);
+  }
+
+  public void pauseAutoScroll(){
+    mAutoScrollHandler.removeCallbacksAndMessages(null);
+  }
+
+  /**
+   * Stop auto scroll.
+   */
+  public void stopAutoScroll() {
+    isAutoScroll = false;
+    mAutoScrollHandler.removeCallbacksAndMessages(null);
+  }
+
+  public boolean isAutoScroll() {
+    return isAutoScroll;
+  }
+
+  @Override
+  public void setCurrentItem(int item) {
+    setRealCurrentItem(item);
+  }
+
+  /**
+   * @return the circlePageAdapter
+   */
+  public WXCirclePageAdapter getCirclePageAdapter() {
+    return (WXCirclePageAdapter) getAdapter();
+  }
+
+  /**
+   * @param circlePageAdapter the circlePageAdapter to set
+   */
+  public void setCirclePageAdapter(WXCirclePageAdapter circlePageAdapter) {
+    this.setAdapter(circlePageAdapter);
+  }
+
+  /**
+   * Get auto scroll interval. The time unit is micro second.
+   * The default time interval is 3000 micro second
+   * @return the intervalTime
+   */
+  public long getIntervalTime() {
+    return intervalTime;
+  }
+
+  /**
+   * Set auto scroll interval. The time unit is micro second.
+   * The default time interval is 3000 micro second
+   * @param intervalTime the intervalTime to set
+   */
+  public void setIntervalTime(long intervalTime) {
+    this.intervalTime = intervalTime;
+  }
+
+  public void setCircle(boolean circle) {
+    needLoop = circle;
+  }
+
+  @Override
+  public boolean dispatchTouchEvent(MotionEvent ev) {
+    switch (ev.getAction()) {
+      case MotionEvent.ACTION_DOWN:
+      case MotionEvent.ACTION_MOVE:
+        mAutoScrollHandler.removeCallbacksAndMessages(null);
+        break;
+      case MotionEvent.ACTION_UP:
+      case MotionEvent.ACTION_CANCEL:
+        if (isAutoScroll()) {
+          mAutoScrollHandler.sendEmptyMessageDelayed(SCROLL_TO_NEXT, intervalTime);
+        }
+        break;
+    }
+    try{
+      boolean result = super.dispatchTouchEvent(ev);
+      if (wxGesture != null) {
+        result |= wxGesture.onTouch(this, ev);
+      }
+      return result;
+    }catch (Exception e){
+      return  false;
+    }
+  }
+
+  public void destory() {
+    mAutoScrollHandler.removeCallbacksAndMessages(null);
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  public int getRealCurrentItem() {
+    int i = super.getCurrentItem();
+    return ((WXCirclePageAdapter) getAdapter()).getRealPosition(i);
+  }
+
+  private void setRealCurrentItem(int item) {
+    superSetCurrentItem(((WXCirclePageAdapter) getAdapter()).getFirst() + item, false);
+  }
+
+  private void superSetCurrentItem(int item, boolean smooth) {
+    try {
+      super.setCurrentItem(item, smooth);
+    } catch (IllegalStateException e) {
+      WXLogUtils.e(e.toString());
+      if (getAdapter() != null) {
+        getAdapter().notifyDataSetChanged();
+        super.setCurrentItem(item, smooth);
+      }
+    }
+  }
+
+  public int getRealCount() {
+    return ((WXCirclePageAdapter) getAdapter()).getRealCount();
+  }
+
+  @Override
+  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+    try {
+      super.onMeasure(widthMeasureSpec, heightMeasureSpec);
+    } catch (IllegalStateException e) {
+      WXLogUtils.e(e.toString());
+      if (getAdapter() != null) {
+        getAdapter().notifyDataSetChanged();
+        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
+      }
+    }
+  }
+
+  public boolean isScrollable() {
+    return scrollable;
+  }
+
+  public void setScrollable(boolean scrollable) {
+    this.scrollable = scrollable;
+  }
+
+  private void showNextItem() {
+    if (this.getCirclePageAdapter() != null && this.getCirclePageAdapter().isRTL) {
+      if (!needLoop && superGetCurrentItem() == 0) {
+        return;
+      }
+      if (getRealCount() == 2 && superGetCurrentItem() == 0) {
+        superSetCurrentItem(1, true);
+      } else {
+        superSetCurrentItem(superGetCurrentItem() - 1, true);
+      }
+    } else {
+      if (!needLoop && superGetCurrentItem() == getRealCount() - 1) {
+        return;
+      }
+      if (getRealCount() == 2 && superGetCurrentItem() == 1) {
+        superSetCurrentItem(0, true);
+      } else {
+        superSetCurrentItem(superGetCurrentItem() + 1, true);
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXEditText.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXEditText.java
new file mode 100644
index 0000000..acadf8d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXEditText.java
@@ -0,0 +1,156 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.os.Build;
+import android.view.ActionMode;
+import android.view.Menu;
+import android.view.MenuItem;
+import android.view.MotionEvent;
+import android.view.ViewParent;
+import android.widget.EditText;
+
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+
+/**
+ * Wrapper class for editText
+ */
+@SuppressLint("AppCompatCustomView")
+public class WXEditText extends EditText implements WXGestureObservable {
+
+  private WXGesture wxGesture;
+  private int mLines = 1;
+  private boolean mAllowDisableMovement = true;
+  private boolean mAllowCopyPaste = true;
+
+  public WXEditText(Context context) {
+    super(context);
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+      setBackground(null);
+    } else {
+      setBackgroundDrawable(null);
+    }
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  @Override
+  public void setLines(int lines) {
+    super.setLines(lines);
+    mLines = lines;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent event) {
+    boolean result = super.onTouchEvent(event);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, event);
+    }
+
+    ViewParent parent = getParent();
+    if(parent != null){
+      switch (event.getAction() & MotionEvent.ACTION_MASK){
+        case MotionEvent.ACTION_DOWN:
+          if(mLines < getLineCount()) {
+            //scrollable
+            parent.requestDisallowInterceptTouchEvent(true);
+          }
+          break;
+        case MotionEvent.ACTION_UP:
+        case MotionEvent.ACTION_CANCEL:
+          parent.requestDisallowInterceptTouchEvent(false);
+          break;
+      }
+    }
+    return result;
+  }
+
+  @Override
+  protected void onSizeChanged(int w, int h, int oldw, int oldh) {
+    super.onSizeChanged(w, h, oldw, oldh);
+    if (getLayout() != null) {
+      int contentH = getLayout().getHeight();
+      //TODO: known issue,set movement to null will make cursor disappear.
+      if (mAllowDisableMovement && h < contentH) {
+        setMovementMethod(null);
+      } else {
+        setMovementMethod(getDefaultMovementMethod());
+      }
+    }
+  }
+
+  public void setAllowDisableMovement(boolean allow) {
+    mAllowDisableMovement = allow;
+  }
+
+  public void setAllowCopyPaste(boolean allow) {
+    mAllowCopyPaste = allow;
+    if (allow) {
+      setLongClickable(true);
+      setCustomSelectionActionModeCallback(null);
+      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
+        setCustomInsertionActionModeCallback(null);
+      }
+    } else {
+      setLongClickable(false);
+      ActionMode.Callback callback = new ActionMode.Callback() {
+        @Override
+        public boolean onCreateActionMode(ActionMode mode, Menu menu) {
+          return false;
+        }
+
+        @Override
+        public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
+          return false;
+        }
+
+        @Override
+        public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
+          return false;
+        }
+
+        @Override
+        public void onDestroyActionMode(ActionMode mode) {
+
+        }
+      };
+      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
+        setCustomInsertionActionModeCallback(callback);
+      }
+      setCustomSelectionActionModeCallback(callback);
+    }
+  }
+
+  @Override
+  public boolean onTextContextMenuItem(int id) {
+    return !mAllowCopyPaste || super.onTextContextMenuItem(id);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXFrameLayout.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXFrameLayout.java
new file mode 100644
index 0000000..199d0a0
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXFrameLayout.java
@@ -0,0 +1,140 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.content.Context;
+import android.graphics.Canvas;
+import android.support.annotation.Nullable;
+import android.view.MotionEvent;
+import android.view.View;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXDiv;
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import org.apache.weex.utils.WXExceptionUtils;
+import org.apache.weex.utils.WXLogUtils;
+import java.lang.ref.WeakReference;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * FrameLayout wrapper
+ *
+ */
+public class WXFrameLayout extends BaseFrameLayout implements WXGestureObservable,IRenderStatus<WXDiv>,IRenderResult<WXDiv>{
+
+  private WeakReference<WXDiv> mWeakReference;
+  private WXGesture wxGesture;
+
+
+  public WXFrameLayout(Context context) {
+    super(context);
+  }
+
+  @Nullable
+  @Override
+  public WXDiv getComponent() {
+    return null != mWeakReference ? mWeakReference.get() : null;
+  }
+
+  @Override
+  public void holdComponent(WXDiv component) {
+    mWeakReference = new WeakReference<WXDiv>(component);
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  @Override
+  public boolean dispatchTouchEvent(MotionEvent event) {
+    boolean result = super.dispatchTouchEvent(event);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, event);
+    }
+    return result;
+  }
+  @Override
+  protected void dispatchDraw(Canvas canvas) {
+    try {
+      super.dispatchDrawInterval(canvas);
+    } catch (Throwable e) {
+      if (getComponent() != null) {
+        notifyLayerOverFlow();
+        if (null != getComponent()){
+          WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(getComponent().getInstanceId());
+          if (null != instance && null != instance.getApmForInstance() &&!instance.getApmForInstance().hasReportLayerOverDraw){
+            instance.getApmForInstance().hasReportLayerOverDraw = true;
+            reportLayerOverFlowError();
+          }
+        }
+      }
+      WXLogUtils.e("Layer overflow limit error", WXLogUtils.getStackTrace(e));
+    }
+  }
+  private int reportLayerOverFlowError() {
+    int deep = calLayerDeep(this, 0);
+    if (getComponent() != null) {
+      WXExceptionUtils.commitCriticalExceptionRT(getComponent().getInstanceId(),
+              WXErrorCode.WX_RENDER_ERR_LAYER_OVERFLOW,
+              "draw android view",
+              WXErrorCode.WX_RENDER_ERR_LAYER_OVERFLOW.getErrorMsg() + "Layer overflow limit error: " + deep + " layers!",
+              null);
+    }
+    return deep;
+  }
+  private int calLayerDeep(View view, int deep) {
+    deep++;
+    if (view.getParent() != null && view.getParent() instanceof View) {
+      return calLayerDeep((View) view.getParent(), deep);
+    }
+    return deep;
+  }
+
+  public void notifyLayerOverFlow() {
+    if (getComponent() == null)
+      return;
+
+    WXSDKInstance instance = getComponent().getInstance();
+    if (instance == null)
+      return;
+
+    if (instance.getLayerOverFlowListeners() == null)
+      return;
+
+    for (String ref : instance.getLayerOverFlowListeners()) {
+      WXComponent component = WXSDKManager.getInstance().getWXRenderManager().getWXComponent(instance.getInstanceId(), ref);
+      Map<String, Object> params = new HashMap<>();
+      params.put(Constants.Weex.REF, ref);
+      params.put(Constants.Weex.INSTANCEID, component.getInstanceId());
+      component.fireEvent(Constants.Event.LAYEROVERFLOW, params);
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXHorizontalScrollView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXHorizontalScrollView.java
new file mode 100644
index 0000000..dd6771e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXHorizontalScrollView.java
@@ -0,0 +1,134 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.graphics.Rect;
+import android.util.AttributeSet;
+import android.view.MotionEvent;
+import android.view.View;
+import android.widget.HorizontalScrollView;
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import java.util.List;
+import java.util.concurrent.CopyOnWriteArrayList;
+
+public class WXHorizontalScrollView extends HorizontalScrollView implements IWXScroller, WXGestureObservable {
+
+  private WXGesture wxGesture;
+  private ScrollViewListener mScrollViewListener;
+  private List<ScrollViewListener> mScrollViewListeners;
+  private boolean scrollable = true;
+
+  public WXHorizontalScrollView(Context context) {
+    super(context);
+    init();
+  }
+
+  private void init() {
+    setWillNotDraw(false);
+    setOverScrollMode(View.OVER_SCROLL_NEVER);
+  }
+
+  public WXHorizontalScrollView(Context context, AttributeSet attrs) {
+    super(context, attrs);
+    init();
+  }
+
+  @Override
+  protected void onScrollChanged(int l, int t, int oldl, int oldt) {
+    super.onScrollChanged(l, t, oldl, oldt);
+    if (mScrollViewListener != null) {
+      mScrollViewListener.onScrollChanged(this, l, t, oldl, oldt);
+    }
+    if (mScrollViewListeners != null) {
+      for (ScrollViewListener listener : mScrollViewListeners) {
+        listener.onScrollChanged(this, l, t, oldl, oldt);
+      }
+    }
+  }
+
+  public void setScrollViewListener(ScrollViewListener scrollViewListener) {
+    this.mScrollViewListener = scrollViewListener;
+  }
+
+  @Override
+  public void destroy() {
+
+  }
+
+  public void addScrollViewListener(ScrollViewListener scrollViewListener) {
+    if (mScrollViewListeners == null) {
+      mScrollViewListeners = new CopyOnWriteArrayList<>();
+    }
+    if (!mScrollViewListeners.contains(scrollViewListener)) {
+      mScrollViewListeners.add(scrollViewListener);
+    }
+  }
+
+  public void removeScrollViewListener(ScrollViewListener scrollViewListener) {
+    mScrollViewListeners.remove(scrollViewListener);
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  @Override
+  public boolean dispatchTouchEvent(MotionEvent event) {
+    boolean result = super.dispatchTouchEvent(event);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, event);
+    }
+    return result;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent ev) {
+    if(!scrollable) {
+      return true; // when scrollable is set to false, then eat the touch event
+    }
+    return super.onTouchEvent(ev);
+  }
+
+  public interface ScrollViewListener {
+
+    void onScrollChanged(WXHorizontalScrollView scrollView, int x, int y, int oldx, int oldy);
+  }
+
+  public boolean isScrollable() {
+    return scrollable;
+  }
+
+  public void setScrollable(boolean scrollable) {
+    this.scrollable = scrollable;
+  }
+
+  public Rect getContentFrame() {
+    return new Rect(0, 0, computeHorizontalScrollRange(), computeVerticalScrollRange());
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXImageView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXImageView.java
new file mode 100644
index 0000000..96b3784
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXImageView.java
@@ -0,0 +1,262 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.graphics.Bitmap;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.ImageView;
+import org.apache.weex.ui.component.WXImage;
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import org.apache.weex.utils.ImageDrawable;
+import org.apache.weex.utils.WXLogUtils;
+import java.lang.ref.WeakReference;
+import java.util.Arrays;
+
+@SuppressLint("AppCompatCustomView")
+public class WXImageView extends ImageView implements WXGestureObservable,
+        IRenderStatus<WXImage>,
+        IRenderResult<WXImage>, WXImage.Measurable {
+
+  private WeakReference<WXImage> mWeakReference;
+  private WXGesture wxGesture;
+  private float[] borderRadius;
+  private boolean gif;
+  private boolean isBitmapReleased = false;
+  private boolean enableBitmapAutoManage = true;
+
+
+  public WXImageView(Context context) {
+    super(context);
+  }
+
+  @Override
+  public void setImageResource(int resId) {
+    Drawable drawable = getResources().getDrawable(resId);
+    setImageDrawable(drawable);
+  }
+
+  public void setImageDrawable(@Nullable Drawable drawable, boolean isGif) {
+    this.gif = isGif;
+    ViewGroup.LayoutParams layoutParams;
+    if ((layoutParams = getLayoutParams()) != null) {
+      Drawable wrapDrawable = ImageDrawable.createImageDrawable(drawable,
+              getScaleType(), borderRadius,
+              layoutParams.width - getPaddingLeft() - getPaddingRight(),
+              layoutParams.height - getPaddingTop() - getPaddingBottom(),
+              isGif);
+      if (wrapDrawable instanceof ImageDrawable) {
+        ImageDrawable imageDrawable = (ImageDrawable) wrapDrawable;
+        if (!Arrays.equals(imageDrawable.getCornerRadii(), borderRadius)) {
+          imageDrawable.setCornerRadii(borderRadius);
+        }
+      }
+      super.setImageDrawable(wrapDrawable);
+      if (mWeakReference != null) {
+        WXImage component = mWeakReference.get();
+        if (component != null) {
+          component.readyToRender();
+        }
+      }
+    }
+  }
+
+  @Override
+  public void setImageDrawable(@Nullable Drawable drawable) {
+    setImageDrawable(drawable, gif);
+  }
+
+  @Override
+  public void setImageBitmap(@Nullable Bitmap bm) {
+    setImageDrawable(bm == null ? null : new BitmapDrawable(getResources(), bm));
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent event) {
+    boolean result = super.onTouchEvent(event);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, event);
+    }
+    return result;
+  }
+
+  public void setBorderRadius(@NonNull float[] borderRadius) {
+    this.borderRadius = borderRadius;
+  }
+
+  @Override
+  protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+    super.onLayout(changed, left, top, right, bottom);
+    if (changed) {
+      setImageDrawable(getDrawable(), gif);
+    }
+  }
+
+  @Override
+  public void holdComponent(WXImage component) {
+    mWeakReference = new WeakReference<>(component);
+  }
+
+  @Nullable
+  @Override
+  public WXImage getComponent() {
+    return null != mWeakReference ? mWeakReference.get() : null;
+  }
+
+  @Override
+  public int getNaturalWidth() {
+    Drawable drawable = getDrawable();
+    if (drawable != null) {
+      if (drawable instanceof ImageDrawable) {
+        return ((ImageDrawable) drawable).getBitmapWidth();
+      } else if (drawable instanceof BitmapDrawable) {
+        Bitmap bitmap = ((BitmapDrawable) drawable).getBitmap();
+        if (bitmap != null) {
+          return bitmap.getWidth();
+        } else {
+          WXLogUtils.w("WXImageView", "Bitmap on " + drawable.toString() + " is null");
+        }
+      } else {
+        WXLogUtils.w("WXImageView", "Not supported drawable type: " + drawable.getClass().getSimpleName());
+      }
+    }
+    return -1;
+  }
+
+  @Override
+  public int getNaturalHeight() {
+    Drawable drawable = getDrawable();
+    if (drawable != null) {
+      if (drawable instanceof ImageDrawable) {
+        return ((ImageDrawable) drawable).getBitmapHeight();
+      } else if (drawable instanceof BitmapDrawable) {
+        Bitmap bitmap = ((BitmapDrawable) drawable).getBitmap();
+        if (bitmap != null) {
+          return bitmap.getHeight();
+        } else {
+          WXLogUtils.w("WXImageView", "Bitmap on " + drawable.toString() + " is null");
+        }
+      } else {
+        WXLogUtils.w("WXImageView", "Not supported drawable type: " + drawable.getClass().getSimpleName());
+      }
+    }
+    return -1;
+  }
+
+  private boolean mOutWindowVisibilityChangedReally;
+  @Override
+  public void dispatchWindowVisibilityChanged(int visibility) {
+    mOutWindowVisibilityChangedReally = true;
+    super.dispatchWindowVisibilityChanged(visibility);
+    mOutWindowVisibilityChangedReally = false;
+  }
+
+  @Override
+  protected void onWindowVisibilityChanged(int visibility) {
+    super.onWindowVisibilityChanged(visibility);
+    if(mOutWindowVisibilityChangedReally){
+      if(visibility == View.VISIBLE){
+        autoRecoverImage();
+      }else{
+        autoReleaseImage();
+      }
+    }
+  }
+
+
+  @Override
+  protected void onAttachedToWindow() {
+    super.onAttachedToWindow();
+    autoRecoverImage();
+  }
+
+  @Override
+  protected void onDetachedFromWindow() {
+    super.onDetachedFromWindow();
+    autoReleaseImage();
+
+  }
+
+
+  @Override
+  public void onStartTemporaryDetach () {
+    super.onStartTemporaryDetach();
+    autoReleaseImage();
+
+  }
+
+
+  @Override
+  public void onFinishTemporaryDetach () {
+    super.onFinishTemporaryDetach();
+    autoRecoverImage();
+  }
+
+
+  public void setEnableBitmapAutoManage(boolean enableBitmapAutoManage) {
+    this.enableBitmapAutoManage = enableBitmapAutoManage;
+  }
+
+  public void autoReleaseImage(){
+    if(enableBitmapAutoManage) {
+      if (!isBitmapReleased) {
+        isBitmapReleased = true;
+        WXImage image = getComponent();
+        if (image != null) {
+          image.autoReleaseImage();
+        }
+      }
+    }
+  }
+
+  public void autoRecoverImage(){
+    if(enableBitmapAutoManage){
+      if(isBitmapReleased){
+        WXImage image = getComponent();
+        if(image != null){
+          image.autoRecoverImage();
+        }
+        isBitmapReleased = false;
+      }
+    }
+  }
+
+
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXLoadingLayout.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXLoadingLayout.java
new file mode 100644
index 0000000..d728efd
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXLoadingLayout.java
@@ -0,0 +1,31 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.content.Context;
+
+/**
+ * Created by lixinke on 16/9/19.
+ */
+public class WXLoadingLayout extends WXBaseRefreshLayout {
+
+  public WXLoadingLayout(Context context) {
+    super(context);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXRefreshLayout.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXRefreshLayout.java
new file mode 100644
index 0000000..78bcf75
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXRefreshLayout.java
@@ -0,0 +1,31 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.content.Context;
+
+/**
+ * Created by lixinke on 16/9/19.
+ */
+public class WXRefreshLayout extends WXBaseRefreshLayout {
+
+  public WXRefreshLayout(Context context) {
+    super(context);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXScrollView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXScrollView.java
new file mode 100644
index 0000000..8932c02
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXScrollView.java
@@ -0,0 +1,467 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.Rect;
+import android.os.Handler;
+import android.os.Handler.Callback;
+import android.os.Message;
+import android.support.v4.view.NestedScrollingChild;
+import android.support.v4.view.NestedScrollingChildHelper;
+import android.support.v4.view.ViewCompat;
+import android.util.AttributeSet;
+import android.view.MotionEvent;
+import android.view.View;
+import android.widget.ScrollView;
+
+import org.apache.weex.common.WXThread;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXScroller;
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXReflectionUtils;
+
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Map.Entry;
+
+
+/**
+ * Custom-defined scrollView
+ */
+public class WXScrollView extends ScrollView implements Callback, IWXScroller,
+        WXGestureObservable,NestedScrollingChild {
+
+  private NestedScrollingChildHelper childHelper;
+  private float ox;
+  private float oy;
+  private int[] consumed = new int[2];
+  private int[] offsetInWindow = new int[2];
+
+  int mScrollX;
+  int mScrollY;
+  private WXGesture wxGesture;
+  private List<WXScrollViewListener> mScrollViewListeners;
+  private WXScroller mWAScroller;
+  //sticky
+  private View mCurrentStickyView;
+  private boolean mRedirectTouchToStickyView;
+  private int mStickyOffset;
+  private boolean mHasNotDoneActionDown = true;
+  @SuppressLint("HandlerLeak")
+  private Handler mScrollerTask;
+  private int mInitialPosition;
+  private int mCheckTime = 100;
+  /**
+   * The location of mCurrentStickyView
+   */
+  private int[] mStickyP = new int[2];
+  /**
+   * Location of the scrollView
+   */
+  private Rect mScrollRect;
+  private int[] stickyScrollerP = new int[2];
+  private int[] stickyViewP = new int[2];
+  private boolean scrollable = true;
+
+  public WXScrollView(Context context) {
+    super(context);
+    mScrollViewListeners = new ArrayList<>();
+    init();
+    try {
+      WXReflectionUtils.setValue(this, "mMinimumVelocity", 5);
+    } catch (Exception e) {
+      WXLogUtils.e("[WXScrollView] WXScrollView: ", e);
+    }
+  }
+
+  private void init() {
+    setWillNotDraw(false);
+    startScrollerTask();
+    setOverScrollMode(View.OVER_SCROLL_NEVER);
+    childHelper = new NestedScrollingChildHelper(this);
+    childHelper.setNestedScrollingEnabled(true);
+  }
+
+  public void startScrollerTask() {
+    if (mScrollerTask == null) {
+      mScrollerTask = new Handler(WXThread.secure(this));
+    }
+    mInitialPosition = getScrollY();
+    mScrollerTask.sendEmptyMessageDelayed(0, mCheckTime);
+  }
+
+  public WXScrollView(Context context, AttributeSet attrs) {
+    super(context, attrs);
+    init();
+  }
+
+  public WXScrollView(Context context, AttributeSet attrs, int defStyle) {
+    super(context, attrs, defStyle);
+    setOverScrollMode(View.OVER_SCROLL_NEVER);
+  }
+
+  /**
+   * Add listener for scrollView.
+   */
+  public void addScrollViewListener(WXScrollViewListener scrollViewListener) {
+    if (!mScrollViewListeners.contains(scrollViewListener)) {
+      mScrollViewListeners.add(scrollViewListener);
+    }
+  }
+
+  public void removeScrollViewListener(WXScrollViewListener scrollViewListener) {
+    mScrollViewListeners.remove(scrollViewListener);
+  }
+
+  @Override
+  public boolean dispatchTouchEvent(MotionEvent ev) {
+    if (ev.getAction() == MotionEvent.ACTION_DOWN) {
+      mRedirectTouchToStickyView = true;
+    }
+
+    if (mRedirectTouchToStickyView) {
+      mRedirectTouchToStickyView = mCurrentStickyView != null;
+
+      if (mRedirectTouchToStickyView) {
+        mRedirectTouchToStickyView = ev.getY() <= mCurrentStickyView.getHeight()
+                && ev.getX() >= mCurrentStickyView.getLeft()
+                && ev.getX() <= mCurrentStickyView.getRight();
+      }
+    }
+
+    if (mRedirectTouchToStickyView) {
+      if (mScrollRect == null) {
+        mScrollRect = new Rect();
+        getGlobalVisibleRect(mScrollRect);
+      }
+      mCurrentStickyView.getLocationOnScreen(stickyViewP);
+      ev.offsetLocation(0, stickyViewP[1] - mScrollRect.top);
+    }
+    boolean result = super.dispatchTouchEvent(ev);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, ev);
+    }
+    return result;
+  }
+
+  @Override
+  protected void dispatchDraw(Canvas canvas) {
+    super.dispatchDraw(canvas);
+    if (mCurrentStickyView != null) {
+      canvas.save();
+      mCurrentStickyView.getLocationOnScreen(mStickyP);
+      int realOffset = (mStickyOffset <= 0 ? mStickyOffset : 0);
+      canvas.translate(mStickyP[0], getScrollY() + realOffset);
+      canvas.clipRect(0, realOffset, mCurrentStickyView.getWidth(),
+              mCurrentStickyView.getHeight());
+      mCurrentStickyView.draw(canvas);
+      canvas.restore();
+    }
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent ev) {
+    if(!scrollable) {
+      return true; // when scrollable is set to false, then eat the touch event
+    }
+    if (mRedirectTouchToStickyView) {
+
+      if (mScrollRect == null) {
+        mScrollRect = new Rect();
+        getGlobalVisibleRect(mScrollRect);
+      }
+      mCurrentStickyView.getLocationOnScreen(stickyViewP);
+      ev.offsetLocation(0, -(stickyViewP[1] - mScrollRect.top));
+    }
+
+    if (ev.getAction() == MotionEvent.ACTION_DOWN) {
+      mHasNotDoneActionDown = false;
+    }
+
+    if (mHasNotDoneActionDown) {
+      MotionEvent down = MotionEvent.obtain(ev);
+      down.setAction(MotionEvent.ACTION_DOWN);
+      mHasNotDoneActionDown = false;
+      down.recycle();
+    }
+
+    if (ev.getAction() == MotionEvent.ACTION_DOWN) {
+      ox = ev.getX();
+      oy = ev.getY();
+      // Dispatch touch event to parent view
+      startNestedScroll(ViewCompat.SCROLL_AXIS_HORIZONTAL | ViewCompat.SCROLL_AXIS_VERTICAL);
+    }
+
+    if (ev.getAction() == MotionEvent.ACTION_UP || ev.getAction() == MotionEvent.ACTION_CANCEL) {
+      mHasNotDoneActionDown = true;
+      // stop nested scrolling dispatch
+      stopNestedScroll();
+    }
+
+    if (ev.getAction() == MotionEvent.ACTION_MOVE) {
+      float clampedX = ev.getX();
+      float clampedY = ev.getY();
+      int dx = (int) (ox - clampedX);
+      int dy = (int) (oy - clampedY);
+
+      if (dispatchNestedPreScroll(dx, dy, consumed, offsetInWindow)) {
+        // sub dx/dy was consumed by parent view!!!
+        ev.setLocation(clampedX+consumed[0],clampedY+consumed[1]);
+      }
+      ox = ev.getX();
+      oy = ev.getY();
+    }
+
+    return super.onTouchEvent(ev);
+  }
+
+  @Override
+  public void setNestedScrollingEnabled(boolean enabled) {
+    childHelper.setNestedScrollingEnabled(enabled);
+  }
+
+  @Override
+  public boolean isNestedScrollingEnabled() {
+    return childHelper.isNestedScrollingEnabled();
+  }
+
+  @Override
+  public boolean startNestedScroll(int axes) {
+    return childHelper.startNestedScroll(axes);
+  }
+
+  @Override
+  public void stopNestedScroll() {
+    childHelper.stopNestedScroll();
+  }
+
+  @Override
+  public boolean hasNestedScrollingParent() {
+    return childHelper.hasNestedScrollingParent();
+  }
+
+  public boolean isScrollable() {
+    return scrollable;
+  }
+
+  public void setScrollable(boolean scrollable) {
+    this.scrollable = scrollable;
+  }
+
+  @Override
+  public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed, int[] offsetInWindow) {
+    return childHelper.dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, offsetInWindow);
+  }
+
+  @Override
+  public boolean dispatchNestedPreScroll(int dx, int dy, int[] consumed, int[] offsetInWindow) {
+    return childHelper.dispatchNestedPreScroll(dx, dy, consumed, offsetInWindow);
+  }
+
+  @Override
+  public boolean dispatchNestedFling(float velocityX, float velocityY, boolean consumed) {
+    return childHelper.dispatchNestedFling(velocityX, velocityY, consumed);
+  }
+
+  @Override
+  public boolean dispatchNestedPreFling(float velocityX, float velocityY) {
+    return childHelper.dispatchNestedPreFling(velocityX, velocityY);
+  }
+
+  @Override
+  public boolean onNestedPreFling(View target, float velocityX,
+                                  float velocityY) {
+    return dispatchNestedPreFling(velocityX, velocityY);
+  }
+
+  @Override
+  public boolean onNestedFling(View target, float velocityX, float velocityY,
+                               boolean consumed) {
+    return dispatchNestedFling(velocityX, velocityY, consumed);
+  }
+
+  @Override
+  public void fling(int velocityY) {
+    super.fling(velocityY);
+    if (mScrollerTask != null) {
+      mScrollerTask.removeMessages(0);
+    }
+    startScrollerTask();
+  }
+
+  @Override
+  protected void onScrollChanged(int x, int y, int oldx, int oldy) {
+    mScrollX = getScrollX();
+    mScrollY = getScrollY();
+    onScroll(WXScrollView.this, mScrollX, mScrollY);
+    View view = getChildAt(getChildCount() - 1);
+    if (view == null) {
+      return;
+    }
+    int d = view.getBottom();
+    d -= (getHeight() + mScrollY);
+    if (d == 0) {
+      onScrollToBottom(mScrollX, mScrollY);
+    }
+    int count = mScrollViewListeners == null ? 0 : mScrollViewListeners.size();
+    for (int i = 0; i < count; ++i) {
+      mScrollViewListeners.get(i).onScrollChanged(this, x, y, oldx, oldy);
+    }
+
+    showStickyView();
+  }
+
+  protected void onScroll(WXScrollView scrollView, int x, int y) {
+    int count = mScrollViewListeners == null ? 0 : mScrollViewListeners.size();
+    for (int i = 0; i < count; ++i) {
+      mScrollViewListeners.get(i).onScroll(this, x, y);
+    }
+  }
+
+  protected void onScrollToBottom(int x, int y) {
+    int count = mScrollViewListeners == null ? 0 : mScrollViewListeners.size();
+    for (int i = 0; i < count; ++i) {
+      mScrollViewListeners.get(i).onScrollToBottom(this, x, y);
+    }
+  }
+
+  private void showStickyView() {
+    if(mWAScroller == null){
+      return;
+    }
+    View curStickyView = procSticky(mWAScroller.getStickMap());
+
+    if (curStickyView != null) {
+      mCurrentStickyView = curStickyView;
+    } else {
+      mCurrentStickyView = null;
+    }
+  }
+
+  private View procSticky(Map<String, Map<String, WXComponent>> mStickyMap) {
+    if (mStickyMap == null) {
+      return null;
+    }
+    Map<String, WXComponent> stickyMap = mStickyMap.get(mWAScroller.getRef());
+    if (stickyMap == null) {
+      return null;
+    }
+
+    Iterator<Entry<String, WXComponent>> iterator = stickyMap.entrySet().iterator();
+    Entry<String, WXComponent> entry = null;
+    WXComponent stickyData;
+    while (iterator.hasNext()) {
+      entry = iterator.next();
+      stickyData = entry.getValue();
+
+      getLocationOnScreen(stickyScrollerP);
+      stickyData.getHostView().getLocationOnScreen(stickyViewP);
+      int parentH = 0;
+      if(stickyData.getParent()!=null && stickyData.getParent().getRealView()!=null){
+        parentH=stickyData.getParent().getRealView().getHeight();
+      }
+      int stickyViewH = stickyData.getHostView().getHeight();
+      int stickyShowPos = stickyScrollerP[1];
+      int stickyStartHidePos = -parentH + stickyScrollerP[1] + stickyViewH;
+      if (stickyViewP[1] <= stickyShowPos && stickyViewP[1] >= (stickyStartHidePos - stickyViewH)) {
+        mStickyOffset = stickyViewP[1] - stickyStartHidePos;
+        stickyData.setStickyOffset(stickyViewP[1]-stickyScrollerP[1]);
+        return stickyData.getHostView();
+      }else{
+        stickyData.setStickyOffset(0);
+      }
+    }
+    return null;
+  }
+
+  @Override
+  public boolean handleMessage(Message msg) {
+    switch (msg.what) {
+      case 0:
+        if (mScrollerTask != null) {
+          mScrollerTask.removeMessages(0);
+        }
+        int newPosition = getScrollY();
+        if (mInitialPosition - newPosition == 0) {//has stopped
+          onScrollStopped(WXScrollView.this, getScrollX(), getScrollY());
+        } else {
+          onScroll(WXScrollView.this, getScrollX(), getScrollY());
+          mInitialPosition = getScrollY();
+          if (mScrollerTask != null) {
+            mScrollerTask.sendEmptyMessageDelayed(0, mCheckTime);
+          }
+        }
+        break;
+      default:
+        break;
+    }
+    return true;
+  }
+
+  protected void onScrollStopped(WXScrollView scrollView, int x, int y) {
+    int count = mScrollViewListeners == null ? 0 : mScrollViewListeners.size();
+    for (int i = 0; i < count; ++i) {
+      mScrollViewListeners.get(i).onScrollStopped(this, x, y);
+    }
+  }
+
+  @Override
+  public void destroy() {
+    if (mScrollerTask != null) {
+      mScrollerTask.removeCallbacksAndMessages(null);
+    }
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  public Rect getContentFrame() {
+    return new Rect(0, 0, computeHorizontalScrollRange(), computeVerticalScrollRange());
+  }
+
+  public interface WXScrollViewListener {
+
+    void onScrollChanged(WXScrollView scrollView, int x, int y, int oldx, int oldy);
+
+    void onScrollToBottom(WXScrollView scrollView, int x, int y);
+
+    void onScrollStopped(WXScrollView scrollView, int x, int y);
+
+    void onScroll(WXScrollView scrollView, int x, int y);
+  }
+
+  public void setWAScroller(WXScroller mWAScroller) {
+    this.mWAScroller = mWAScroller;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXSmoothScroller.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXSmoothScroller.java
new file mode 100644
index 0000000..e943ce8
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXSmoothScroller.java
@@ -0,0 +1,58 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.view.animation.Interpolator;
+import android.widget.Scroller;
+
+/**
+ * modify the scrollFactor
+ */
+public class WXSmoothScroller extends Scroller {
+
+  private double mScrollFactor = 1;
+
+  public WXSmoothScroller(Context context) {
+    super(context);
+  }
+
+  public WXSmoothScroller(Context context, Interpolator interpolator) {
+    super(context, interpolator);
+  }
+
+  @SuppressLint("NewApi")
+  public WXSmoothScroller(Context context, Interpolator interpolator, boolean flywheel) {
+    super(context, interpolator, flywheel);
+  }
+
+  /**
+   * Set the factor by which the duration will change
+   */
+  public void setScrollDurationFactor(double scrollFactor) {
+    mScrollFactor = scrollFactor;
+  }
+
+  @Override
+  public void startScroll(int startX, int startY, int dx, int dy, int duration) {
+    super.startScroll(startX, startY, dx, dy, (int) (duration * mScrollFactor));
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXSwitchView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXSwitchView.java
new file mode 100644
index 0000000..f02fe63
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXSwitchView.java
@@ -0,0 +1,59 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.support.v7.widget.SwitchCompat;
+import android.view.Gravity;
+import android.view.MotionEvent;
+
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+
+public class WXSwitchView extends SwitchCompat implements WXGestureObservable {
+
+  private WXGesture wxGesture;
+
+  public WXSwitchView(Context context) {
+    super(context);
+    setShowText(false);
+    setGravity(Gravity.CENTER_VERTICAL);
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent event) {
+    boolean result = super.onTouchEvent(event);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, event);
+    }
+    return result;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXTextView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXTextView.java
new file mode 100644
index 0000000..06073b3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXTextView.java
@@ -0,0 +1,185 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.ClipData;
+import android.content.ClipboardManager;
+import android.content.Context;
+import android.graphics.Canvas;
+import android.support.annotation.ColorInt;
+import android.support.annotation.Nullable;
+import android.support.v7.widget.PopupMenu;
+import android.text.Layout;
+import android.text.TextUtils;
+import android.view.MenuItem;
+import android.view.MotionEvent;
+import android.view.View;
+import org.apache.weex.ui.component.WXText;
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import java.lang.ref.WeakReference;
+
+/**
+ * TextView wrapper
+ */
+public class WXTextView extends View implements WXGestureObservable, IWXTextView,
+        IRenderStatus<WXText>, IRenderResult<WXText> {
+
+  private WeakReference<WXText> mWeakReference;
+  private WXGesture wxGesture;
+  private Layout textLayout;
+  private boolean mIsLabelSet = false;
+
+  public WXTextView(Context context) {
+    super(context);
+  }
+
+  @Override
+  protected void onDraw(Canvas canvas) {
+    super.onDraw(canvas);
+    canvas.save();
+    Layout layout= getTextLayout();
+    if(layout!=null){
+      canvas.translate(getPaddingLeft(),getPaddingTop());
+      layout.draw(canvas);
+    }
+    canvas.restore();
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent event) {
+    boolean result = super.onTouchEvent(event);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, event);
+    }
+    return result;
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  @Override
+  public CharSequence getText() {
+    return textLayout != null ? textLayout.getText() : null;
+  }
+
+  public Layout getTextLayout() {
+    return textLayout;
+  }
+
+  public void setTextLayout(Layout layout) {
+    this.textLayout = layout;
+    if(layout!=null && !mIsLabelSet){
+      setContentDescription(layout.getText());
+    }
+    if (mWeakReference != null) {
+      WXText wxText = mWeakReference.get();
+      if (wxText != null) {
+        wxText.readyToRender();
+      }
+    }
+  }
+
+  public void setAriaLabel(String label){
+    if(!TextUtils.isEmpty(label)){
+      mIsLabelSet = true;
+      setContentDescription(label);
+    }else{
+      mIsLabelSet = false;
+      if(textLayout != null){
+        setContentDescription(textLayout.getText());
+      }
+    }
+
+  }
+
+  /**
+   * Sets the text color for the text layout, it will be invalid
+   * when {@link #setTextLayout(Layout)} happens, and color has to be
+   * reset.
+   *
+   * @see #setTextLayout(Layout)
+   *
+   * @param color A color value in the form 0xAARRGGBB.
+   */
+  public void setTextColor(@ColorInt int color) {
+    Layout layout = getTextLayout();
+    if (layout != null) {
+      layout.getPaint().setColor(color);
+    }
+  }
+
+  @Override
+  public void holdComponent(WXText component) {
+    mWeakReference = new WeakReference<>(component);
+  }
+
+  @Nullable
+  @Override
+  public WXText getComponent() {
+    return null != mWeakReference ? mWeakReference.get() : null;
+  }
+
+  public void enableCopy(boolean enable) {
+    if (enable) {
+      setOnLongClickListener(new OnLongClickListener() {
+        @Override
+        public boolean onLongClick(View v) {
+          PopupMenu popupMenu = new PopupMenu(getContext(), WXTextView.this);
+          String s = "Copy";
+          try {
+            s = getContext().getResources().getString(android.R.string.copy);
+          } catch (Throwable t) {
+            //ignore
+          }
+          final String title = s;
+          popupMenu.getMenu().add(title);
+          popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
+            @Override
+            public boolean onMenuItemClick(MenuItem item) {
+              if (title.equals(item.getTitle())) {
+                String data = getText().toString();
+                ClipboardManager clipboardManager = (ClipboardManager) getContext().getSystemService(Context.CLIPBOARD_SERVICE);
+                if (clipboardManager != null) {
+                  ClipData clipData = ClipData.newPlainText(data, data);
+                  clipboardManager.setPrimaryClip(clipData);
+                }
+                return true;
+              }
+              return false;
+            }
+          });
+          popupMenu.show();
+          return true;
+        }
+      });
+    } else {
+      setOnLongClickListener(null);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXVideoView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXVideoView.java
new file mode 100644
index 0000000..4df2d4a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXVideoView.java
@@ -0,0 +1,304 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.graphics.Rect;
+import android.media.MediaPlayer;
+import android.net.Uri;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.util.AttributeSet;
+import android.view.Gravity;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.ViewTreeObserver;
+import android.widget.FrameLayout;
+import android.widget.MediaController;
+import android.widget.ProgressBar;
+import android.widget.VideoView;
+
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import org.apache.weex.utils.WXResourceUtils;
+
+
+public class WXVideoView extends VideoView implements WXGestureObservable {
+
+  private WXGesture wxGesture;
+  private VideoPlayListener mVideoPauseListener;
+
+  public WXVideoView(Context context) {
+    super(context);
+  }
+
+  @Override
+  public void registerGestureListener(WXGesture wxGesture) {
+    this.wxGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return wxGesture;
+  }
+
+  public void setOnVideoPauseListener(VideoPlayListener listener) {
+    mVideoPauseListener = listener;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent event) {
+    boolean result = super.onTouchEvent(event);
+    if (wxGesture != null) {
+      result |= wxGesture.onTouch(this, event);
+    }
+    return result;
+  }
+
+  @Override
+  public void start() {
+    super.start();
+    if (mVideoPauseListener != null) {
+      mVideoPauseListener.onStart();
+    }
+  }
+
+  @Override
+  public void pause() {
+    super.pause();
+    if (mVideoPauseListener != null) {
+      mVideoPauseListener.onPause();
+    }
+  }
+
+  public interface VideoPlayListener {
+
+    void onPause();
+
+    void onStart();
+  }
+
+
+  public static class Wrapper extends FrameLayout implements ViewTreeObserver.OnGlobalLayoutListener {
+
+    private WXVideoView mVideoView;
+    private ProgressBar mProgressBar;
+    private MediaController mMediaController;
+    private Uri mUri;
+    private MediaPlayer.OnPreparedListener mOnPreparedListener;
+    private MediaPlayer.OnErrorListener mOnErrorListener;
+    private MediaPlayer.OnCompletionListener mOnCompletionListener;
+    private WXVideoView.VideoPlayListener mVideoPlayListener;
+    private boolean mControls = true;
+
+    public Wrapper(Context context) {
+      super(context);
+      init(context);
+    }
+
+    public Wrapper(Context context, AttributeSet attrs) {
+      super(context, attrs);
+      init(context);
+    }
+
+    public Wrapper(Context context, AttributeSet attrs, int defStyleAttr) {
+      super(context, attrs, defStyleAttr);
+      init(context);
+    }
+
+    private void init(Context context) {
+      setBackgroundColor(WXResourceUtils.getColor("#ee000000"));
+      mProgressBar = new ProgressBar(context);
+      FrameLayout.LayoutParams pLayoutParams =
+              new FrameLayout.LayoutParams(FrameLayout.LayoutParams.WRAP_CONTENT,
+                      FrameLayout.LayoutParams.WRAP_CONTENT);
+      mProgressBar.setLayoutParams(pLayoutParams);
+      pLayoutParams.gravity = Gravity.CENTER;
+      addView(mProgressBar);
+
+      getViewTreeObserver().addOnGlobalLayoutListener(this);
+    }
+
+    public ProgressBar getProgressBar() {
+      return mProgressBar;
+    }
+
+    public
+    @Nullable
+    WXVideoView getVideoView() {
+      return mVideoView;
+    }
+
+    /**
+     * Create if not existed. Will cause request focus.
+     *
+     * @return
+     */
+    public
+    @NonNull
+    WXVideoView createIfNotExist() {
+      if (mVideoView == null) {
+        createVideoView();
+      }
+      return mVideoView;
+    }
+
+    public
+    @Nullable
+    MediaController getMediaController() {
+      return mMediaController;
+    }
+
+    public void setVideoURI(Uri uri) {
+      mUri = uri;
+      if (mVideoView != null) {
+        mVideoView.setVideoURI(uri);
+      }
+    }
+
+    public void start() {
+      if (mVideoView != null) {
+        mVideoView.start();
+      }
+    }
+
+    public void pause() {
+      if (mVideoView != null) {
+        mVideoView.pause();
+      }
+    }
+
+    public void stopPlayback() {
+      if (mVideoView != null) {
+        mVideoView.stopPlayback();
+      }
+    }
+
+    public void resume() {
+      if (mVideoView != null) {
+        mVideoView.resume();
+      }
+    }
+
+    public void setOnErrorListener(MediaPlayer.OnErrorListener l) {
+      mOnErrorListener = l;
+      if (mVideoView != null) {
+        mVideoView.setOnErrorListener(l);
+      }
+    }
+
+    public void setOnPreparedListener(MediaPlayer.OnPreparedListener l) {
+      mOnPreparedListener = l;
+      if (mVideoView != null) {
+        mVideoView.setOnPreparedListener(l);
+      }
+
+    }
+
+    public void setOnCompletionListener(MediaPlayer.OnCompletionListener l) {
+      mOnCompletionListener = l;
+      if (mVideoView != null) {
+        mVideoView.setOnCompletionListener(l);
+      }
+    }
+
+    public void setOnVideoPauseListener(VideoPlayListener listener) {
+      mVideoPlayListener = listener;
+      if (mVideoView != null) {
+        mVideoView.setOnVideoPauseListener(listener);
+      }
+    }
+
+    public void setControls(boolean controls) {
+      mControls = controls;
+      if (mVideoView != null && mMediaController != null) {
+        if (!mControls) {
+          mMediaController.setVisibility(View.GONE);
+        } else {
+          mMediaController.setVisibility(View.VISIBLE);
+        }
+      }
+    }
+
+    private synchronized void createVideoView() {
+      if(mVideoView != null){
+        return;
+      }
+      Context context = getContext();
+      WXVideoView video = new WXVideoView(context);
+      FrameLayout.LayoutParams videoLayoutParams =
+              new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT,
+                      FrameLayout.LayoutParams.MATCH_PARENT);
+      videoLayoutParams.gravity = Gravity.CENTER;
+      video.setLayoutParams(videoLayoutParams);
+      addView(video, 0);//first child
+      video.setOnErrorListener(mOnErrorListener);
+      video.setOnPreparedListener(mOnPreparedListener);
+      video.setOnCompletionListener(mOnCompletionListener);
+      video.setOnVideoPauseListener(mVideoPlayListener);
+      MediaController controller = new MediaController(context);
+      controller.setAnchorView(this);
+      video.setMediaController(controller);
+      controller.setMediaPlayer(video);
+      if (!mControls) {
+        controller.setVisibility(View.GONE);
+      } else {
+        controller.setVisibility(View.VISIBLE);
+      }
+      mMediaController = controller;
+      mVideoView = video;
+      mVideoView.setZOrderOnTop(true);
+
+      if(mUri != null) {
+        setVideoURI(mUri);
+      }
+    }
+
+    @SuppressLint("NewApi")
+    private void removeSelfFromViewTreeObserver() {
+      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
+        getViewTreeObserver().removeOnGlobalLayoutListener(this);
+      } else {
+        getViewTreeObserver().removeGlobalOnLayoutListener(this);
+      }
+    }
+
+
+    public boolean createVideoViewIfVisible(){
+      Rect visibleRect = new Rect();
+      if (mVideoView != null) {
+        return true;
+      } else if (getGlobalVisibleRect(visibleRect) && !visibleRect.isEmpty()) {
+        createVideoView();
+        return true;
+      }
+      return false;
+    }
+
+    @Override
+    public void onGlobalLayout() {
+      if(createVideoViewIfVisible()){
+        removeSelfFromViewTreeObserver();
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/WXWebView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/WXWebView.java
new file mode 100644
index 0000000..bca5350
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/WXWebView.java
@@ -0,0 +1,376 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.graphics.Bitmap;
+import android.graphics.Color;
+import android.net.Uri;
+import android.net.http.SslError;
+import android.os.Build;
+import android.os.Handler;
+import android.os.Message;
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+import android.view.Gravity;
+import android.view.View;
+import android.webkit.JavascriptInterface;
+import android.webkit.JsPromptResult;
+import android.webkit.SslErrorHandler;
+import android.webkit.WebChromeClient;
+import android.webkit.WebResourceError;
+import android.webkit.WebResourceRequest;
+import android.webkit.WebResourceResponse;
+import android.webkit.WebSettings;
+import android.webkit.WebView;
+import android.webkit.WebViewClient;
+import android.widget.FrameLayout;
+import android.widget.ProgressBar;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONException;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.lang.ref.WeakReference;
+import java.util.HashMap;
+import java.util.Map;
+
+public class WXWebView implements IWebView {
+
+    private Context mContext;
+    private String mOrigin;
+    private WebView mWebView;
+    private ProgressBar mProgressBar;
+    private boolean mShowLoading = true;
+    private Handler mMessageHandler;
+    private static final int POST_MESSAGE = 1;
+    private static final String BRIDGE_NAME = "__WEEX_WEB_VIEW_BRIDGE";
+    private static final int SDK_VERSION = Build.VERSION.SDK_INT;
+    // downgraded by CVE-2012-6636(https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2012-6636)
+    private static final boolean DOWNGRADE_JS_INTERFACE = SDK_VERSION < 17;
+
+    private OnErrorListener mOnErrorListener;
+    private OnPageListener mOnPageListener;
+    private OnMessageListener mOnMessageListener;
+
+    public WXWebView(Context context, String origin) {
+        mContext = context;
+        mOrigin = origin;
+    }
+
+    @Override
+    public View getView() {
+        FrameLayout root = new FrameLayout(mContext);
+        root.setBackgroundColor(Color.WHITE);
+
+        mWebView = new WebView(mContext);//mContext.getApplicationContext();
+        FrameLayout.LayoutParams wvLayoutParams =
+                new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT,
+                        FrameLayout.LayoutParams.MATCH_PARENT);
+        wvLayoutParams.gravity = Gravity.CENTER;
+        mWebView.setLayoutParams(wvLayoutParams);
+        root.addView(mWebView);
+        initWebView(mWebView);
+
+        mProgressBar = new ProgressBar(mContext);
+        showProgressBar(false);
+        FrameLayout.LayoutParams pLayoutParams =
+                new FrameLayout.LayoutParams(FrameLayout.LayoutParams.WRAP_CONTENT,
+                        FrameLayout.LayoutParams.WRAP_CONTENT);
+        mProgressBar.setLayoutParams(pLayoutParams);
+        pLayoutParams.gravity = Gravity.CENTER;
+        root.addView(mProgressBar);
+
+        mMessageHandler = new MessageHandler(this);
+
+        return root;
+    }
+
+    @Override
+    public void destroy() {
+        if (getWebView() != null) {
+            getWebView().removeAllViews();
+            getWebView().destroy();
+            mWebView = null;
+        }
+    }
+
+    @Override
+    public void loadUrl(String url) {
+        if(getWebView() == null)
+            return;
+        getWebView().loadUrl(url);
+    }
+
+    @Override
+    public void loadDataWithBaseURL(String source) {
+        if(getWebView() == null)
+            return;
+        getWebView().loadDataWithBaseURL(mOrigin, source, "text/html", "utf-8", null);
+    }
+
+    @Override
+    public void reload() {
+        if(getWebView() == null)
+            return;
+        getWebView().reload();
+    }
+
+    @Override
+    public void goBack() {
+        if(getWebView() == null)
+            return;
+        getWebView().goBack();
+    }
+
+    @Override
+    public void goForward() {
+        if(getWebView() == null)
+            return;
+        getWebView().goForward();
+    }
+
+    @Override
+    public void postMessage(Object msg) {
+        if (getWebView() == null) return;
+
+        try {
+            JSONObject initData = new JSONObject();
+            initData.put("type", "message");
+            initData.put("data", msg);
+            initData.put("origin", mOrigin);
+            evaluateJS("javascript:(function () {"
+                + "var initData = " + initData.toString() + ";"
+                + "try {"
+                + "var event = new MessageEvent('message', initData);"
+                + "window.dispatchEvent(event);"
+                + "} catch (e) {}"
+                + "})();");
+        } catch (JSONException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    /*@Override
+    public void setVisibility(int visibility) {
+        if (mRootView != null) {
+            mRootView.setVisibility(visibility);
+        }
+    }*/
+
+    @Override
+    public void setShowLoading(boolean shown) {
+        mShowLoading = shown;
+    }
+
+    @Override
+    public void setOnErrorListener(OnErrorListener listener) {
+        mOnErrorListener = listener;
+    }
+
+    @Override
+    public void setOnPageListener(OnPageListener listener) {
+        mOnPageListener = listener;
+    }
+
+    @Override
+    public void setOnMessageListener(OnMessageListener listener) {
+        mOnMessageListener = listener;
+    }
+
+    private void showProgressBar(boolean shown) {
+        if (mShowLoading) {
+            mProgressBar.setVisibility(shown ? View.VISIBLE : View.GONE);
+        }
+    }
+
+    private void showWebView(boolean shown) {
+        mWebView.setVisibility(shown ? View.VISIBLE : View.INVISIBLE);
+    }
+
+    private @Nullable WebView getWebView() {
+        //TODO: remove this, duplicate with getView semantically.
+        return mWebView;
+    }
+
+    @SuppressLint({"SetJavaScriptEnabled", "AddJavascriptInterface"})
+    private void initWebView(WebView wv) {
+        WebSettings settings = wv.getSettings();
+        settings.setJavaScriptEnabled(true);
+        settings.setAppCacheEnabled(true);
+        settings.setUseWideViewPort(true);
+        settings.setDomStorageEnabled(true);
+        settings.setSupportZoom(false);
+        settings.setBuiltInZoomControls(false);
+        settings.setAllowFileAccess(false);
+        wv.setWebViewClient(new WebViewClient() {
+
+            @Override
+            public boolean shouldOverrideUrlLoading(WebView view, String url) {
+                view.loadUrl(url);
+                WXLogUtils.v("tag", "onPageOverride " + url);
+                return true;
+            }
+
+            @Override
+            public void onPageStarted(WebView view, String url, Bitmap favicon) {
+                super.onPageStarted(view, url, favicon);
+                WXLogUtils.v("tag", "onPageStarted " + url);
+                if (mOnPageListener != null) {
+                    mOnPageListener.onPageStart(url);
+                }
+            }
+
+            @Override
+            public void onPageFinished(WebView view, String url) {
+                super.onPageFinished(view, url);
+                WXLogUtils.v("tag", "onPageFinished " + url);
+                if (mOnPageListener != null) {
+                    mOnPageListener.onPageFinish(url, view.canGoBack(), view.canGoForward());
+                }
+                if (mOnMessageListener != null) {
+                    evaluateJS("javascript:(window.postMessage = function(message, targetOrigin) {"
+                        + "if (message == null || !targetOrigin) return;"
+                        + (DOWNGRADE_JS_INTERFACE
+                        ? "prompt('" + BRIDGE_NAME + "://postMessage?message=' + JSON.stringify(message) + '&targetOrigin=' + targetOrigin)"
+                        : BRIDGE_NAME + ".postMessage(JSON.stringify(message), targetOrigin);")
+                        + "})");
+                }
+            }
+
+            @Override
+            public void onReceivedError(WebView view, WebResourceRequest request, WebResourceError error) {
+                super.onReceivedError(view, request, error);
+                if (mOnErrorListener != null) {
+                    //mOnErrorListener.onError("error", "page error code:" + error.getErrorCode() + ", desc:" + error.getDescription() + ", url:" + request.getUrl());
+                    mOnErrorListener.onError("error", "page error");
+                }
+            }
+
+            @Override
+            public void onReceivedHttpError(WebView view, WebResourceRequest request, WebResourceResponse errorResponse) {
+                super.onReceivedHttpError(view, request, errorResponse);
+                if (mOnErrorListener != null) {
+                    mOnErrorListener.onError("error", "http error");
+                }
+            }
+
+            @Override
+            public void onReceivedSslError(WebView view, SslErrorHandler handler, SslError error) {
+                super.onReceivedSslError(view, handler, error);
+                if (mOnErrorListener != null) {
+                    mOnErrorListener.onError("error", "ssl error");
+                }
+            }
+        });
+        wv.setWebChromeClient(new WebChromeClient() {
+            @Override
+            public void onProgressChanged(WebView view, int newProgress) {
+                super.onProgressChanged(view, newProgress);
+                showWebView(newProgress == 100);
+                showProgressBar(newProgress != 100);
+                WXLogUtils.v("tag", "onPageProgressChanged " + newProgress);
+            }
+
+            @Override
+            public void onReceivedTitle(WebView view, String title) {
+                super.onReceivedTitle(view, title);
+                if (mOnPageListener != null) {
+                    mOnPageListener.onReceivedTitle(view.getTitle());
+                }
+            }
+
+            @Override
+            public boolean onJsPrompt(WebView view, String url, String text, String defaultValue, JsPromptResult result) {
+                Uri uri = Uri.parse(text);
+                String scheme = uri.getScheme();
+                if (TextUtils.equals(scheme, BRIDGE_NAME)) {
+                    if (TextUtils.equals(uri.getAuthority(), "postMessage")) {
+                        String message = uri.getQueryParameter("message");
+                        String targetOrigin = uri.getQueryParameter("targetOrigin");
+                        onMessage(message, targetOrigin);
+                        result.confirm("success");
+                    } else {
+                        result.confirm("fail");
+                    }
+                    return true;
+                }
+                return super.onJsPrompt(view, url, text, defaultValue, result);
+            }
+        });
+        if (!DOWNGRADE_JS_INTERFACE) {
+            wv.addJavascriptInterface(new Object() {
+                @JavascriptInterface
+                public void postMessage(String message, String targetOrigin) {
+                    onMessage(message, targetOrigin);
+                }
+            }, BRIDGE_NAME);
+        }
+    }
+
+    private void onMessage(String message, String targetOrigin) {
+        if (message != null && targetOrigin != null && mOnMessageListener != null) {
+            try {
+                Map<String, Object> initData = new HashMap<>();
+                initData.put("data", JSON.parse(message));
+                initData.put("origin", targetOrigin);
+                initData.put("type", "message");
+                Message threadMessage = new Message();
+                threadMessage.what = POST_MESSAGE;
+                threadMessage.obj = initData;
+                mMessageHandler.sendMessage(threadMessage);
+            } catch (JSONException e) {
+                throw new RuntimeException(e);
+            }
+        }
+    }
+
+    private void evaluateJS(String jsStr) {
+        if (SDK_VERSION < 19) {
+            mWebView.loadUrl(jsStr);
+        } else {
+            mWebView.evaluateJavascript(jsStr, null);
+        }
+    }
+
+    private static class MessageHandler extends Handler {
+        private final WeakReference<WXWebView> mWv;
+
+        private MessageHandler(WXWebView wv) {
+            mWv = new WeakReference<>(wv);
+        }
+
+        @Override
+        @SuppressWarnings("unchecked")
+        public void handleMessage(Message msg) {
+            super.handleMessage(msg);
+            switch (msg.what) {
+                case POST_MESSAGE:
+                    if (mWv.get() != null && mWv.get().mOnMessageListener != null) {
+                        mWv.get().mOnMessageListener.onMessage((Map<String, Object>) msg.obj);
+                    }
+                    break;
+                default:
+                    break;
+            }
+        }
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderCorner.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderCorner.java
new file mode 100644
index 0000000..a997132
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderCorner.java
@@ -0,0 +1,201 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.border;
+
+import android.graphics.Canvas;
+import android.graphics.Paint;
+import android.graphics.RectF;
+import android.os.Build.VERSION;
+import android.os.Build.VERSION_CODES;
+import android.support.annotation.NonNull;
+import org.apache.weex.base.FloatUtil;
+
+abstract class BorderCorner {
+
+  final static float SWEEP_ANGLE = 45;
+  private float mCornerRadius = 0.0f;
+  private float mPreBorderWidth = 0.0f;
+  private float mPostBorderWidth = 0.0f;
+  private RectF mBorderBox;
+  protected float mAngleBisector;
+
+  /**
+   * Tell whether this corner has a rounded inner corner.
+   * If a corner has a rounded inner corner, it has an outer corner as well.
+   */
+  private boolean hasInnerCorner = false;
+
+  /**
+   * Tell whether this corner has a rounded outer corner.
+   */
+  private boolean hasOuterCorner = false;
+
+  private float mOvalLeft, mOvalTop, mOvalRight, mOvalBottom;
+
+  private float mRoundCornerStartX, mRoundCornerStartY;
+  private float mRoundCornerEndX, mRoundCornerEndY;
+
+  BorderCorner() {
+  }
+
+  final void set(float cornerRadius, float preBorderWidth, float postBorderWidth,
+                 @NonNull RectF borderBox, float angleBisector) {
+    boolean dirty = !FloatUtil.floatsEqual(mCornerRadius, cornerRadius)
+        || !FloatUtil.floatsEqual(mPreBorderWidth, preBorderWidth)
+        || !FloatUtil.floatsEqual(mPostBorderWidth, postBorderWidth)
+        || !FloatUtil.floatsEqual(mAngleBisector, angleBisector)
+        || (null != mBorderBox && mBorderBox.equals(borderBox));
+
+    if (dirty) {
+      mCornerRadius = cornerRadius;
+      mPreBorderWidth = preBorderWidth;
+      mPostBorderWidth = postBorderWidth;
+      mBorderBox = borderBox;
+      mAngleBisector = angleBisector;
+
+      hasOuterCorner = mCornerRadius > 0 && !FloatUtil.floatsEqual(0, mCornerRadius);
+
+      hasInnerCorner = (hasOuterCorner
+          && (getPreBorderWidth() >= 0)
+          && (getPostBorderWidth() >= 0)
+          && (getOuterCornerRadius() > getPreBorderWidth())
+          && (getOuterCornerRadius() > getPostBorderWidth()));
+
+      if (hasOuterCorner) {
+        prepareOval();
+      }
+      prepareRoundCorner();
+    }
+  }
+
+  /** Build oval data */
+  abstract protected void prepareOval();
+
+  /** Build corner data */
+  abstract protected void prepareRoundCorner();
+
+  public final void drawRoundedCorner(@NonNull Canvas canvas, @NonNull Paint paint, float startAngle) {
+    if (this.hasOuterCorner()) {
+      /*Due to the problem of hardware-acceleration, border-radius in some case will not
+       be rendered if Path.addArc used instead and the following condition met.
+       1. hardware-acceleration enabled
+       2. System version is Android 4.1
+       3. Screen width is 720px.
+       http://dotwe.org/weex/421b9ad09fde51c0b49bb56b37fcf955
+      */
+      if (VERSION.SDK_INT >= VERSION_CODES.LOLLIPOP) {
+        canvas.drawArc(mOvalLeft, mOvalTop, mOvalRight, mOvalBottom, startAngle, BorderCorner.SWEEP_ANGLE, false,
+            paint);
+      } else {
+        canvas.drawArc(new RectF(mOvalLeft, mOvalTop, mOvalRight, mOvalBottom), startAngle, BorderCorner.SWEEP_ANGLE,
+            false, paint);
+      }
+    } else {
+      canvas.drawLine(getRoundCornerStartX(), getRoundCornerStartY(), getRoundCornerEndX(), getRoundCornerEndY(),
+          paint);
+    }
+  }
+
+
+  public final float getRoundCornerStartX() {
+    return mRoundCornerStartX;
+  }
+
+  final void setRoundCornerStartX(float roundCornerStartX) {
+    this.mRoundCornerStartX = roundCornerStartX;
+  }
+
+  public final float getRoundCornerStartY() {
+    return mRoundCornerStartY;
+  }
+
+  final void setRoundCornerStartY(float roundCornerStartY) {
+    this.mRoundCornerStartY = roundCornerStartY;
+  }
+
+  public final float getRoundCornerEndX() {
+    return mRoundCornerEndX;
+  }
+
+  final void setRoundCornerEndX(float mRoundCornerEndX) {
+    this.mRoundCornerEndX = mRoundCornerEndX;
+  }
+
+  public final float getRoundCornerEndY() {
+    return mRoundCornerEndY;
+  }
+
+  final void setRoundCornerEndY(float mRoundCornerEndY) {
+    this.mRoundCornerEndY = mRoundCornerEndY;
+  }
+
+  final void setOvalLeft(float mOvalLeft) {
+    this.mOvalLeft = mOvalLeft;
+  }
+
+  final void setOvalTop(float mOvalTop) {
+    this.mOvalTop = mOvalTop;
+  }
+
+  final void setOvalRight(float mOvalRight) {
+    this.mOvalRight = mOvalRight;
+  }
+
+  final void setOvalBottom(float mOvalBottom) {
+    this.mOvalBottom = mOvalBottom;
+  }
+
+  /**
+   * Tell whether this corner has a rounded inner corner.
+   * If a corner has a rounded inner corner, it has an outer corner as well.
+   * @return true for a rounded inner corner, otherwise false.
+   */
+  boolean hasInnerCorner() {
+    return hasInnerCorner;
+  }
+
+  /**
+   * Tell whether this corner has a rounded outer corner.
+   * @return true for a rounded outer corner, otherwise false.
+   */
+  boolean hasOuterCorner() {
+    return hasOuterCorner;
+  }
+
+  protected final float getPreBorderWidth() {
+    return mPreBorderWidth;
+  }
+
+  protected final float getPostBorderWidth() {
+    return mPostBorderWidth;
+  }
+
+  protected final float getOuterCornerRadius() {
+    return mCornerRadius;
+  }
+
+  protected final float getAngleBisectorDegree(){
+    return mAngleBisector;
+  }
+
+  protected final RectF getBorderBox() {
+    return mBorderBox;
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderDrawable.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderDrawable.java
new file mode 100644
index 0000000..72b21e0
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderDrawable.java
@@ -0,0 +1,496 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.border;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+import java.util.Locale;
+
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.ColorFilter;
+import android.graphics.Outline;
+import android.graphics.Paint;
+import android.graphics.Path;
+import android.graphics.PixelFormat;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.graphics.Shader;
+import android.graphics.drawable.Drawable;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.util.SparseIntArray;
+import org.apache.weex.dom.CSSShorthand;
+import org.apache.weex.dom.CSSShorthand.CORNER;
+import org.apache.weex.dom.CSSShorthand.EDGE;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXViewUtils;
+import org.apache.weex.ui.component.WXComponent;
+
+import static org.apache.weex.dom.CSSShorthand.CORNER.ALL;
+import static org.apache.weex.dom.CSSShorthand.CORNER.BORDER_BOTTOM_LEFT;
+import static org.apache.weex.dom.CSSShorthand.CORNER.BORDER_BOTTOM_RIGHT;
+import static org.apache.weex.dom.CSSShorthand.CORNER.BORDER_TOP_LEFT;
+import static org.apache.weex.dom.CSSShorthand.CORNER.BORDER_TOP_RIGHT;
+
+/**
+ * A subclass of
+ * {@link Drawable} used for background of {@link WXComponent}.
+ * It supports drawing background color and borders (including rounded borders) by providing a react
+ * friendly API (setter for each of those properties). The implementation tries to allocate as few
+ * objects as possible depending on which properties are set. E.g. for views with rounded
+ * background/borders we allocate {@code mPathForBorderDrawn} and {@code mTempRectForBorderRadius}.
+ * In case when view have a rectangular borders we allocate {@code mBorderWidthResult} and similar.
+ * When only background color is set we won't allocate any extra/unnecessary objects.
+ */
+public class BorderDrawable extends Drawable {
+
+  public static final int BORDER_TOP_LEFT_RADIUS = 0;
+  public static final int BORDER_TOP_RIGHT_RADIUS = 1;
+  public static final int BORDER_BOTTOM_RIGHT_RADIUS = 2;
+  public static final int BORDER_BOTTOM_LEFT_RADIUS = 3;
+  public static final int BORDER_RADIUS_ALL = 5;
+  static final int DEFAULT_BORDER_COLOR = Color.BLACK;
+  static final float DEFAULT_BORDER_WIDTH = 0;
+  private static final BorderStyle DEFAULT_BORDER_STYLE = BorderStyle.SOLID;
+  private static final String TAG = "Border";
+  private final Paint mPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
+  private static BorderStyle[] sBorderStyle = BorderStyle.values();
+
+  private
+  @Nullable
+  CSSShorthand<EDGE> mBorderWidth;
+  private
+  @Nullable
+  CSSShorthand<CORNER> mBorderRadius;
+  private
+  @Nullable
+  CSSShorthand<CORNER> mOverlappingBorderRadius;
+  private
+  @Nullable
+  SparseIntArray mBorderColor;
+  private
+  @Nullable
+  SparseIntArray mBorderStyle;
+
+  private
+  @Nullable
+  Path mPathForBorderOutline;
+  private boolean mNeedUpdatePath = false;
+  private int mColor = Color.TRANSPARENT;
+  /**
+   * set background-image linear-gradient
+   */
+  private Shader mShader = null;
+  private int mAlpha = 255;
+
+  private TopLeftCorner mTopLeftCorner;
+  private TopRightCorner mTopRightCorner;
+  private BottomRightCorner mBottomRightCorner;
+  private BottomLeftCorner mBottomLeftCorner;
+
+  private final BorderEdge mBorderEdge = new BorderEdge();
+
+  private RectF mRectBounds;
+
+  public BorderDrawable() {
+  }
+
+  @Override
+  public void draw(@NonNull Canvas canvas) {
+    canvas.save();
+    updateBorderOutline();
+    //Shader uses alpha as well.
+    mPaint.setAlpha(255);
+    if (mPathForBorderOutline != null) {
+      int useColor = WXViewUtils.multiplyColorAlpha(mColor, mAlpha);
+      if (mShader != null) {
+        mPaint.setShader(mShader);
+        mPaint.setStyle(Paint.Style.FILL);
+        canvas.drawPath(mPathForBorderOutline, mPaint);
+        mPaint.setShader(null);
+      } else if ((useColor >>> 24) != 0) {
+        mPaint.setColor(useColor);
+        mPaint.setStyle(Paint.Style.FILL);
+        canvas.drawPath(mPathForBorderOutline, mPaint);
+        mPaint.setShader(null);
+      }
+    }
+    mPaint.setStyle(Paint.Style.STROKE);
+    mPaint.setStrokeJoin(Paint.Join.ROUND);
+    drawBorders(canvas);
+    mPaint.setShader(null);
+    canvas.restore();
+  }
+
+  @Override
+  protected void onBoundsChange(Rect bounds) {
+    super.onBoundsChange(bounds);
+    mNeedUpdatePath = true;
+  }
+
+  @Override
+  public void setAlpha(int alpha) {
+    if (alpha != mAlpha) {
+      mAlpha = alpha;
+      invalidateSelf();
+    }
+  }
+
+  @Override
+  public int getAlpha() {
+    return mAlpha;
+  }
+
+  /**
+   * Do not support Color Filter
+   */
+  @Override
+  public void setColorFilter(ColorFilter cf) {
+
+  }
+
+  @Override
+  public int getOpacity() {
+    return mShader != null ? PixelFormat.OPAQUE :
+            WXViewUtils.getOpacityFromColor(WXViewUtils.multiplyColorAlpha(mColor, mAlpha));
+  }
+
+  /* Android's elevation implementation requires this to be implemented to know where to draw the
+ shadow. */
+  @Override
+  public void getOutline(@NonNull Outline outline) {
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
+      if (mPathForBorderOutline == null) {
+        mNeedUpdatePath = true;
+      }
+      updateBorderOutline();
+      outline.setConvexPath(mPathForBorderOutline);
+    }
+  }
+
+  public void setBorderWidth(CSSShorthand.EDGE edge, float width) {
+    if (mBorderWidth == null) {
+      mBorderWidth = new CSSShorthand<>();
+    }
+    if (mBorderWidth.get(edge) != width) {
+      mBorderWidth.set(edge, width);
+      mNeedUpdatePath = true;
+      invalidateSelf();
+    }
+  }
+
+  float getBorderWidth(CSSShorthand.EDGE edge) {
+    return mBorderWidth.get(edge);
+  }
+
+  public void setBorderRadius(CORNER position, float radius) {
+    if (mBorderRadius == null) {
+      mBorderRadius = new CSSShorthand<>();
+    }
+    if (mBorderRadius.get(position) != radius ||
+        (position == ALL &&
+            (radius != mBorderRadius.get(BORDER_TOP_LEFT) ||
+            radius != mBorderRadius.get(BORDER_TOP_RIGHT) ||
+            radius != mBorderRadius.get(BORDER_BOTTOM_RIGHT) ||
+            radius != mBorderRadius.get(BORDER_BOTTOM_LEFT)))) {
+      mBorderRadius.set(position, radius);
+      mNeedUpdatePath = true;
+      invalidateSelf();
+    }
+  }
+
+  public
+  @NonNull
+  float[] getBorderRadius(RectF borderBox) {
+    prepareBorderRadius(borderBox);
+    if (mOverlappingBorderRadius == null) {
+      mOverlappingBorderRadius = new CSSShorthand<>();
+    }
+    float topLeftRadius = mOverlappingBorderRadius.get(BORDER_TOP_LEFT);
+    float topRightRadius = mOverlappingBorderRadius.get(BORDER_TOP_RIGHT);
+    float bottomRightRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_RIGHT);
+    float bottomLeftRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_LEFT);
+    return new float[]{topLeftRadius, topLeftRadius,
+            topRightRadius, topRightRadius,
+            bottomRightRadius, bottomRightRadius,
+            bottomLeftRadius, bottomLeftRadius};
+  }
+
+  public
+  @NonNull
+  float[] getBorderInnerRadius(RectF borderBox) {
+    prepareBorderRadius(borderBox);
+    if (mOverlappingBorderRadius == null) {
+      mOverlappingBorderRadius = new CSSShorthand<>();
+    }
+    float topLeftRadius = mOverlappingBorderRadius.get(BORDER_TOP_LEFT);
+    float topRightRadius = mOverlappingBorderRadius.get(BORDER_TOP_RIGHT);
+    float bottomRightRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_RIGHT);
+    float bottomLeftRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_LEFT);
+    if (null != mBorderWidth) {
+      topLeftRadius = Math.max(topLeftRadius - mBorderWidth.get(EDGE.TOP), 0);
+      topRightRadius = Math.max(topRightRadius - mBorderWidth.get(EDGE.TOP), 0);
+      bottomRightRadius = Math.max(bottomRightRadius - mBorderWidth.get(EDGE.BOTTOM), 0);
+      bottomLeftRadius = Math.max(bottomLeftRadius - mBorderWidth.get(EDGE.BOTTOM), 0);
+    }
+    return new float[] {topLeftRadius, topLeftRadius,
+        topRightRadius, topRightRadius,
+        bottomRightRadius, bottomRightRadius,
+        bottomLeftRadius, bottomLeftRadius};
+  }
+
+  public void setBorderColor(CSSShorthand.EDGE edge, int color) {
+    if (mBorderColor == null) {
+      mBorderColor = new SparseIntArray(5);
+      mBorderColor.put(CSSShorthand.EDGE.ALL.ordinal(), DEFAULT_BORDER_COLOR);
+    }
+    if (getBorderColor(edge) != color) {
+      BorderUtil.updateSparseArray(mBorderColor, edge.ordinal(), color);
+      invalidateSelf();
+    }
+  }
+
+  int getBorderColor(CSSShorthand.EDGE edge) {
+    return BorderUtil.fetchFromSparseArray(mBorderColor, edge.ordinal(), DEFAULT_BORDER_COLOR);
+  }
+
+  public void setBorderStyle(CSSShorthand.EDGE edge, @NonNull String style) {
+    if (mBorderStyle == null) {
+      mBorderStyle = new SparseIntArray(5);
+      mBorderStyle.put(CSSShorthand.EDGE.ALL.ordinal(), DEFAULT_BORDER_STYLE.ordinal());
+    }
+    try {
+      int borderStyle = BorderStyle.valueOf(style.toUpperCase(Locale.US)).ordinal();
+      if (getBorderStyle(edge) != borderStyle) {
+        BorderUtil.updateSparseArray(mBorderStyle, edge.ordinal(), borderStyle);
+        invalidateSelf();
+      }
+    } catch (IllegalArgumentException e) {
+      WXLogUtils.e(TAG, WXLogUtils.getStackTrace(e));
+    }
+  }
+
+  int getBorderStyle(CSSShorthand.EDGE edge) {
+    return BorderUtil.fetchFromSparseArray(mBorderStyle, edge.ordinal(), BorderStyle.SOLID.ordinal());
+  }
+
+  public int getColor() {
+    return mColor;
+  }
+
+  public void setColor(int color) {
+    mColor = color;
+    invalidateSelf();
+  }
+
+  public void setImage(Shader shader) {
+    mShader = shader;
+    invalidateSelf();
+  }
+
+  public boolean hasImage() {
+    return mShader != null;
+  }
+
+  public boolean isRounded() {
+    return mBorderRadius != null &&
+            (mBorderRadius.get(BORDER_TOP_LEFT) != 0 ||
+                mBorderRadius.get(BORDER_TOP_RIGHT) != 0 ||
+                mBorderRadius.get(BORDER_BOTTOM_RIGHT) != 0 ||
+                mBorderRadius.get(BORDER_BOTTOM_LEFT) != 0);
+  }
+
+  public
+  @NonNull
+  Path getContentPath(@NonNull RectF borderBox) {
+    Path contentClip = new Path();
+    prepareBorderPath(0, 0, 0, 0, borderBox, contentClip);
+    return contentClip;
+  }
+
+  private void updateBorderOutline() {
+    if (mNeedUpdatePath) {
+      mNeedUpdatePath = false;
+      if (mPathForBorderOutline == null) {
+        mPathForBorderOutline = new Path();
+      }
+      mPathForBorderOutline.reset();
+      prepareBorderPath(0, 0, 0, 0, new RectF(getBounds()), mPathForBorderOutline);
+    }
+  }
+
+  private void prepareBorderPath(int topPadding,
+                                 int rightPadding,
+                                 int bottomPadding,
+                                 int leftPadding,
+                                 @NonNull RectF rectF,
+                                 @NonNull Path path) {
+    if (mBorderRadius != null) {
+      prepareBorderRadius(rectF);
+      if (mOverlappingBorderRadius == null) {
+        mOverlappingBorderRadius = new CSSShorthand<>();
+      }
+      float topLeftRadius = mOverlappingBorderRadius.get(BORDER_TOP_LEFT);
+      float topRightRadius = mOverlappingBorderRadius.get(BORDER_TOP_RIGHT);
+      float bottomRightRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_RIGHT);
+      float bottomLeftRadius = mOverlappingBorderRadius.get(BORDER_BOTTOM_LEFT);
+      path.addRoundRect(
+              rectF,
+              new float[]{
+                      topLeftRadius - leftPadding,
+                      topLeftRadius - topPadding,
+                      topRightRadius - rightPadding,
+                      topRightRadius - topPadding,
+                      bottomRightRadius - rightPadding,
+                      bottomRightRadius - bottomPadding,
+                      bottomLeftRadius - leftPadding,
+                      bottomLeftRadius - bottomPadding
+              },
+              Path.Direction.CW);
+    } else {
+      path.addRect(rectF, Path.Direction.CW);
+    }
+  }
+
+  /**
+   * Process overlapping curve according to https://www.w3.org/TR/css3-background/#corner-overlap .
+   */
+  private void prepareBorderRadius(@NonNull RectF borderBox) {
+    if (mBorderRadius != null) {
+      float factor = getScaleFactor(borderBox);
+      if (mOverlappingBorderRadius == null) {
+        mOverlappingBorderRadius = new CSSShorthand<>();
+      }
+      if (!Float.isNaN(factor) && factor < 1) {
+        mOverlappingBorderRadius.set(BORDER_TOP_LEFT,
+            mBorderRadius.get(BORDER_TOP_LEFT) * factor);
+        mOverlappingBorderRadius.set(BORDER_TOP_RIGHT,
+            mBorderRadius.get(BORDER_TOP_RIGHT) * factor);
+        mOverlappingBorderRadius.set(BORDER_BOTTOM_RIGHT,
+            mBorderRadius.get(BORDER_BOTTOM_RIGHT) * factor);
+        mOverlappingBorderRadius.set(BORDER_BOTTOM_LEFT,
+            mBorderRadius.get(BORDER_BOTTOM_LEFT) * factor);
+      } else {
+        mOverlappingBorderRadius.set(BORDER_TOP_LEFT,
+            mBorderRadius.get(BORDER_TOP_LEFT));
+        mOverlappingBorderRadius.set(BORDER_TOP_RIGHT,
+            mBorderRadius.get(BORDER_TOP_RIGHT));
+        mOverlappingBorderRadius.set(BORDER_BOTTOM_RIGHT,
+            mBorderRadius.get(BORDER_BOTTOM_RIGHT));
+        mOverlappingBorderRadius.set(BORDER_BOTTOM_LEFT,
+            mBorderRadius.get(BORDER_BOTTOM_LEFT));
+      }
+    }
+  }
+
+  private float getScaleFactor(@NonNull RectF borderBox) {
+    final float topRadius = mBorderRadius.get(BORDER_TOP_LEFT)
+            + mBorderRadius.get(BORDER_TOP_RIGHT);
+    final float rightRadius = mBorderRadius.get(BORDER_TOP_RIGHT)
+            + mBorderRadius.get(BORDER_BOTTOM_RIGHT);
+    final float bottomRadius = mBorderRadius.get(BORDER_BOTTOM_RIGHT)
+            + mBorderRadius.get(BORDER_BOTTOM_LEFT);
+    final float leftRadius = mBorderRadius.get(BORDER_BOTTOM_LEFT)
+            + mBorderRadius.get(BORDER_TOP_LEFT);
+    List<Float> factors = new ArrayList<>(4);
+    updateFactor(factors, borderBox.width(), topRadius);
+    updateFactor(factors, borderBox.height(), rightRadius);
+    updateFactor(factors, borderBox.width(), bottomRadius);
+    updateFactor(factors, borderBox.height(), leftRadius);
+    float factor;
+    if (factors.isEmpty()) {
+      factor = Float.NaN;
+    } else {
+      factor = Collections.min(factors);
+    }
+    return factor;
+  }
+
+  private void updateFactor(@NonNull List<Float> list, float numerator, float denominator) {
+    if (denominator != 0) {
+      list.add(numerator / denominator);
+    }
+  }
+
+  private void drawBorders(Canvas canvas) {
+    if (mRectBounds == null) {
+      mRectBounds = new RectF(getBounds());
+    } else {
+      mRectBounds.set(getBounds());
+    }
+
+    if (mBorderWidth == null)
+      return;
+
+    final float leftBorderWidth = mBorderWidth.get(EDGE.LEFT);
+    final float topBorderWidth = mBorderWidth.get(EDGE.TOP);
+    final float bottomBorderWidth = mBorderWidth.get(EDGE.BOTTOM);
+    final float rightBorderWidth = mBorderWidth.get(EDGE.RIGHT);
+
+    if (mTopLeftCorner == null) {
+      mTopLeftCorner = new TopLeftCorner();
+    }
+    mTopLeftCorner.set(getBorderRadius(BORDER_TOP_LEFT), leftBorderWidth, topBorderWidth, mRectBounds);
+    if (mTopRightCorner == null) {
+      mTopRightCorner = new TopRightCorner();
+    }
+    mTopRightCorner.set(getBorderRadius(BORDER_TOP_RIGHT), topBorderWidth, rightBorderWidth, mRectBounds);
+    if (mBottomRightCorner == null) {
+      mBottomRightCorner = new BottomRightCorner();
+    }
+    mBottomRightCorner.set(getBorderRadius(BORDER_BOTTOM_RIGHT), rightBorderWidth, bottomBorderWidth, mRectBounds);
+    if (mBottomLeftCorner == null) {
+      mBottomLeftCorner = new BottomLeftCorner();
+    }
+    mBottomLeftCorner.set(getBorderRadius(BORDER_BOTTOM_LEFT), bottomBorderWidth, leftBorderWidth, mRectBounds);
+
+    drawOneSide(canvas, mBorderEdge.set(mTopLeftCorner, mTopRightCorner, topBorderWidth, EDGE.TOP));
+    drawOneSide(canvas, mBorderEdge.set(mTopRightCorner, mBottomRightCorner, rightBorderWidth, EDGE.RIGHT));
+    drawOneSide(canvas, mBorderEdge.set(mBottomRightCorner, mBottomLeftCorner, bottomBorderWidth, EDGE.BOTTOM));
+    drawOneSide(canvas, mBorderEdge.set(mBottomLeftCorner, mTopLeftCorner, leftBorderWidth, EDGE.LEFT));
+  }
+
+  private float getBorderRadius(CORNER position) {
+    if (null != mOverlappingBorderRadius) {
+      return mOverlappingBorderRadius.get(position);
+    } else {
+      return 0.0f;
+    }
+  }
+
+  private void drawOneSide(Canvas canvas, @NonNull BorderEdge borderEdge) {
+    if (0 != borderEdge.getBorderWidth()) {
+      preparePaint(borderEdge.getEdge());
+      borderEdge.drawEdge(canvas, mPaint);
+    }
+  }
+
+  private void preparePaint(CSSShorthand.EDGE edge) {
+    final float borderWidth = mBorderWidth.get(edge);
+    final int color = WXViewUtils.multiplyColorAlpha(getBorderColor(edge), mAlpha);
+    final BorderStyle borderStyle = sBorderStyle[getBorderStyle(edge)];
+    final Shader shader = borderStyle.getLineShader(borderWidth, color, edge);
+    mPaint.setShader(shader);
+    mPaint.setColor(color);
+    mPaint.setStrokeCap(Paint.Cap.ROUND);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderEdge.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderEdge.java
new file mode 100644
index 0000000..8d4d17e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderEdge.java
@@ -0,0 +1,88 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.border;
+
+import android.graphics.Canvas;
+import android.graphics.Paint;
+import android.support.annotation.NonNull;
+import org.apache.weex.dom.CSSShorthand;
+
+/**
+ * Edge for border. Every border has four edges, and each edge has a previous corner and a post
+ * corner.
+ */
+class BorderEdge {
+
+  private
+  @NonNull
+  BorderCorner mPreCorner;
+  private
+  @NonNull
+  BorderCorner mPostCorner;
+
+  private CSSShorthand.EDGE mEdge;
+  private float mBorderWidth;
+
+  BorderEdge() {
+  }
+
+  BorderEdge set(@NonNull BorderCorner preCorner, @NonNull BorderCorner postCorner,
+                 float borderWidth, CSSShorthand.EDGE edge) {
+    mPreCorner = preCorner;
+    mPostCorner = postCorner;
+    mBorderWidth = borderWidth;
+    mEdge = edge;
+    return this;
+  }
+
+  /**
+   * Draw the edge on the canvas with the specified paint.
+   * @param canvas the canvas where the edge will be drawn.
+   * @param paint the paint which is used to draw.
+   */
+  void drawEdge(@NonNull Canvas canvas, @NonNull Paint paint) {
+    paint.setStrokeWidth(mBorderWidth);
+
+    mPreCorner.drawRoundedCorner(canvas, paint, mPreCorner.getAngleBisectorDegree());
+
+    paint.setStrokeWidth(mBorderWidth);
+
+    final float lineStartX = mPreCorner.getRoundCornerEndX();
+    final float lineStartY = mPreCorner.getRoundCornerEndY();
+
+    final float lineEndX = mPostCorner.getRoundCornerStartX();
+    final float lineEndY = mPostCorner.getRoundCornerStartY();
+
+    canvas.drawLine(lineStartX, lineStartY, lineEndX, lineEndY, paint);
+
+    mPostCorner.drawRoundedCorner(canvas, paint, mPostCorner.getAngleBisectorDegree() - BorderCorner.SWEEP_ANGLE);
+  }
+
+  /**
+   * The index of the edge
+   * @return index of edge. May be one of
+   */
+  public CSSShorthand.EDGE getEdge() {
+    return mEdge;
+  }
+
+  public float getBorderWidth() {
+    return mBorderWidth;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderRadiusType.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderRadiusType.java
new file mode 100644
index 0000000..955991b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderRadiusType.java
@@ -0,0 +1,36 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.ui.view.border;
+
+import android.support.annotation.IntDef;
+
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+
+@Retention(RetentionPolicy.SOURCE)
+@IntDef({
+    BorderDrawable.BORDER_TOP_LEFT_RADIUS,
+    BorderDrawable.BORDER_TOP_RIGHT_RADIUS,
+    BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS,
+    BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS,
+    BorderDrawable.BORDER_RADIUS_ALL})
+public @interface BorderRadiusType {
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderStyle.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderStyle.java
new file mode 100644
index 0000000..c31d060
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderStyle.java
@@ -0,0 +1,65 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.border;
+
+import android.graphics.Color;
+import android.graphics.LinearGradient;
+import android.graphics.PathEffect;
+import android.graphics.Shader;
+import android.support.annotation.Nullable;
+import org.apache.weex.dom.CSSShorthand;
+
+enum BorderStyle {
+  SOLID,
+  DASHED,
+  DOTTED;
+
+  /**
+   * Use {@link LinearGradient} to replace {@link PathEffect}
+   * for implementing {@link #DASHED} or {@link #DASHED}
+   * @param borderWidth width of the edge
+   * @param borderColor color of the edge
+   * @param edge the index of the ede. See {@link CSSShorthand}
+   * @return An object of {@link LinearGradient} without color transitions for {@link #DOTTED}
+   * or {@link #DASHED}, null otherwise
+   */
+  @Nullable
+  Shader getLineShader(float borderWidth, int borderColor, CSSShorthand.EDGE edge) {
+    switch (this) {
+      case DOTTED:
+        if (edge == CSSShorthand.EDGE.LEFT || edge == CSSShorthand.EDGE.RIGHT) {
+          return new LinearGradient(0, 0, 0, borderWidth * 2, new int[]{borderColor, Color
+                  .TRANSPARENT}, new float[]{0.5f, 0.5f}, Shader.TileMode.REPEAT);
+        } else if (edge == CSSShorthand.EDGE.TOP || edge == CSSShorthand.EDGE.BOTTOM) {
+          return new LinearGradient(0, 0, borderWidth * 2, 0, new int[]{borderColor, Color
+                  .TRANSPARENT}, new float[]{0.5f, 0.5f}, Shader.TileMode.REPEAT);
+        }
+      case DASHED:
+        if (edge == CSSShorthand.EDGE.LEFT || edge == CSSShorthand.EDGE.RIGHT) {
+          return new LinearGradient(0, 0, 0, borderWidth * 6, new int[]{borderColor, Color
+                  .TRANSPARENT}, new float[]{0.5f, 0.5f}, Shader.TileMode.REPEAT);
+        } else if (edge == CSSShorthand.EDGE.TOP || edge == CSSShorthand.EDGE.BOTTOM) {
+          return new LinearGradient(0, 0, borderWidth * 6, 0, new int[]{borderColor, Color
+                  .TRANSPARENT}, new float[]{0.5f, 0.5f}, Shader.TileMode.REPEAT);
+        }
+      default:
+        return null;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderUtil.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderUtil.java
new file mode 100644
index 0000000..8aad832
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BorderUtil.java
@@ -0,0 +1,45 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.ui.view.border;
+
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.util.SparseIntArray;
+import org.apache.weex.dom.CSSShorthand;
+
+class BorderUtil {
+
+  static int fetchFromSparseArray(@Nullable SparseIntArray array, int position, int fallback) {
+    return array == null ? fallback :
+            array.get(position, array.get(CSSShorthand.EDGE.ALL.ordinal()));
+  }
+
+  static void updateSparseArray(@NonNull SparseIntArray array, int position, int value) {
+    if (position == CSSShorthand.EDGE.ALL.ordinal()) {
+      array.put(CSSShorthand.EDGE.ALL.ordinal(), value);
+      array.put(CSSShorthand.EDGE.TOP.ordinal(), value);
+      array.put(CSSShorthand.EDGE.LEFT.ordinal(), value);
+      array.put(CSSShorthand.EDGE.RIGHT.ordinal(), value);
+      array.put(CSSShorthand.EDGE.BOTTOM.ordinal(), value);
+    } else {
+      array.put(position, value);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/BottomLeftCorner.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BottomLeftCorner.java
new file mode 100644
index 0000000..79d964e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BottomLeftCorner.java
@@ -0,0 +1,64 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.border;
+
+import android.graphics.RectF;
+import android.support.annotation.NonNull;
+
+class BottomLeftCorner extends BorderCorner {
+
+  void set(float cornerRadius, float preBorderWidth, float postBorderWidth, @NonNull RectF borderBox) {
+    set(cornerRadius, preBorderWidth, postBorderWidth, borderBox, 135);
+  }
+
+  @Override
+  protected void prepareOval() {
+    if (hasInnerCorner()) {
+      setOvalLeft(getPostBorderWidth() / 2);
+      setOvalTop(getBorderBox().height() - (2 * getOuterCornerRadius() - getPreBorderWidth() / 2));
+      setOvalRight(2 * getOuterCornerRadius() - getPostBorderWidth() / 2);
+      setOvalBottom(getBorderBox().height() - getPreBorderWidth() / 2);
+    } else {
+      setOvalLeft(getOuterCornerRadius() / 2);
+      setOvalTop(getBorderBox().height() - 1.5f * getOuterCornerRadius());
+      setOvalRight(1.5f * getOuterCornerRadius());
+      setOvalBottom(getBorderBox().height() - getOuterCornerRadius() / 2);
+    }
+  }
+
+  @Override
+  protected void prepareRoundCorner() {
+    if (hasOuterCorner()) {
+      setRoundCornerStartX(getOuterCornerRadius());
+      setRoundCornerStartY(getBorderBox().height() - getPreBorderWidth() / 2);
+
+      setRoundCornerEndX(getPostBorderWidth() / 2);
+      setRoundCornerEndY(getBorderBox().height() - getOuterCornerRadius());
+    } else {
+      final float x = getPostBorderWidth() / 2;
+      final float y = getBorderBox().height() - getPreBorderWidth() / 2;
+
+      setRoundCornerStartX(x);
+      setRoundCornerStartY(y);
+
+      setRoundCornerEndX(x);
+      setRoundCornerEndY(y);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/BottomRightCorner.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BottomRightCorner.java
new file mode 100644
index 0000000..0d30912
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/BottomRightCorner.java
@@ -0,0 +1,64 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.ui.view.border;
+
+import android.graphics.RectF;
+import android.support.annotation.NonNull;
+
+class BottomRightCorner extends BorderCorner {
+
+  void set(float cornerRadius, float preBorderWidth, float postBorderWidth, @NonNull RectF borderBox) {
+    set(cornerRadius, preBorderWidth, postBorderWidth, borderBox, 45);
+  }
+
+  @Override
+  protected void prepareOval() {
+    if (hasInnerCorner()) {
+      setOvalLeft(getBorderBox().width() - (2 * getOuterCornerRadius() - getPreBorderWidth() / 2));
+      setOvalTop(getBorderBox().height() - (2 * getOuterCornerRadius() - getPostBorderWidth() / 2));
+      setOvalRight(getBorderBox().width() - (getPreBorderWidth() / 2));
+      setOvalBottom(getBorderBox().height() - (getPostBorderWidth() / 2));
+    } else {
+      setOvalLeft(getBorderBox().width() - 1.5f * getOuterCornerRadius());
+      setOvalTop(getBorderBox().height() - 1.5f * getOuterCornerRadius());
+      setOvalRight(getBorderBox().width() - getOuterCornerRadius() / 2);
+      setOvalBottom(getBorderBox().height() - getOuterCornerRadius() / 2);
+    }
+  }
+
+  @Override
+  protected void prepareRoundCorner() {
+    if (hasOuterCorner()) {
+      setRoundCornerStartX(getBorderBox().width() - getPreBorderWidth() / 2);
+      setRoundCornerStartY(getBorderBox().height() - getOuterCornerRadius());
+
+      setRoundCornerEndX(getBorderBox().width() - getOuterCornerRadius());
+      setRoundCornerEndY(getBorderBox().height() - getPostBorderWidth() / 2);
+    } else {
+      final float x = getBorderBox().width() - getPreBorderWidth() / 2;
+      final float y = getBorderBox().height() - getPostBorderWidth() / 2;
+
+      setRoundCornerStartX(x);
+      setRoundCornerStartY(y);
+
+      setRoundCornerEndX(x);
+      setRoundCornerEndY(y);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/TopLeftCorner.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/TopLeftCorner.java
new file mode 100644
index 0000000..5d9422d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/TopLeftCorner.java
@@ -0,0 +1,64 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.border;
+
+import android.graphics.RectF;
+import android.support.annotation.NonNull;
+
+class TopLeftCorner extends BorderCorner {
+
+  void set(float cornerRadius, float preBorderWidth, float postBorderWidth, @NonNull RectF borderBox) {
+    set(cornerRadius, preBorderWidth, postBorderWidth, borderBox, 225);
+  }
+
+  @Override
+  protected void prepareOval() {
+    if (hasInnerCorner()) {
+      setOvalLeft(getPreBorderWidth() / 2);
+      setOvalTop(getPostBorderWidth() / 2);
+      setOvalRight(2 * getOuterCornerRadius() - getPreBorderWidth() / 2);
+      setOvalBottom(2 * getOuterCornerRadius() - getPostBorderWidth() / 2);
+    } else {
+      setOvalLeft(getOuterCornerRadius() / 2);
+      setOvalTop(getOuterCornerRadius() / 2);
+      setOvalRight(getOuterCornerRadius() * 1.5f);
+      setOvalBottom(getOuterCornerRadius() * 1.5f);
+    }
+  }
+
+  @Override
+  protected void prepareRoundCorner() {
+    if (hasOuterCorner()) {
+      setRoundCornerStartX(getPreBorderWidth() / 2);
+      setRoundCornerStartY(getOuterCornerRadius());
+
+      setRoundCornerEndX(getOuterCornerRadius());
+      setRoundCornerEndY(getPostBorderWidth() / 2);
+    } else {
+      final float x = getPreBorderWidth() / 2;
+      final float y = getPostBorderWidth() / 2;
+
+      setRoundCornerStartX(x);
+      setRoundCornerStartY(y);
+
+      setRoundCornerEndX(x);
+      setRoundCornerEndY(y);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/border/TopRightCorner.java b/android/sdk/src/main/java/org/apache/weex/ui/view/border/TopRightCorner.java
new file mode 100644
index 0000000..58b8384
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/border/TopRightCorner.java
@@ -0,0 +1,64 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.border;
+
+import android.graphics.RectF;
+import android.support.annotation.NonNull;
+
+class TopRightCorner extends BorderCorner {
+
+  void set(float cornerRadius, float preBorderWidth, float postBorderWidth, @NonNull RectF borderBox) {
+    set(cornerRadius, preBorderWidth, postBorderWidth, borderBox, 315);
+  }
+
+  @Override
+  protected void prepareOval() {
+    if (hasInnerCorner()) {
+      setOvalLeft(getBorderBox().width() - (2 * getOuterCornerRadius() - getPostBorderWidth() / 2));
+      setOvalTop(getPreBorderWidth() / 2);
+      setOvalRight(getBorderBox().width() - getPostBorderWidth() / 2);
+      setOvalBottom(2 * getOuterCornerRadius() - getPreBorderWidth() / 2);
+    } else {
+      setOvalLeft(getBorderBox().width() - 1.5f * getOuterCornerRadius());
+      setOvalTop(getOuterCornerRadius() / 2);
+      setOvalRight(getBorderBox().width() - getOuterCornerRadius() / 2);
+      setOvalBottom(getOuterCornerRadius() * 1.5f);
+    }
+  }
+
+  @Override
+  protected void prepareRoundCorner() {
+    if (hasOuterCorner()) {
+      setRoundCornerStartX(getBorderBox().width() - getOuterCornerRadius());
+      setRoundCornerStartY(getPreBorderWidth() / 2);
+
+      setRoundCornerEndX(getBorderBox().width() - getPostBorderWidth() / 2);
+      setRoundCornerEndY(getOuterCornerRadius());
+    } else {
+      final float x = getBorderBox().width() - getPostBorderWidth() / 2;
+      final float y = getPreBorderWidth() / 2;
+
+      setRoundCornerStartX(x);
+      setRoundCornerStartY(y);
+
+      setRoundCornerEndX(x);
+      setRoundCornerEndY(y);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGesture.java b/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGesture.java
new file mode 100644
index 0000000..4b76bea
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGesture.java
@@ -0,0 +1,663 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.gesture;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.graphics.Point;
+import android.graphics.PointF;
+import android.graphics.Rect;
+import android.os.Looper;
+import android.support.annotation.NonNull;
+import android.view.GestureDetector;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.View.OnTouchListener;
+import android.view.ViewGroup;
+import android.view.ViewParent;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import org.apache.weex.bridge.EventResult;
+import org.apache.weex.common.Constants;
+import org.apache.weex.dom.WXEvent;
+import org.apache.weex.ui.component.Scrollable;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.view.gesture.WXGestureType.GestureInfo;
+import org.apache.weex.ui.view.gesture.WXGestureType.HighLevelGesture;
+import org.apache.weex.ui.view.gesture.WXGestureType.LowLevelGesture;
+import org.apache.weex.utils.WXLogUtils;
+import org.apache.weex.utils.WXUtils;
+import org.apache.weex.utils.WXViewUtils;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.common.Constants.Event;
+
+public class WXGesture extends GestureDetector.SimpleOnGestureListener implements OnTouchListener {
+
+  private final static String TAG = "Gesture";
+  private static final int CUR_EVENT = -1;
+  public static final String START = "start";
+  public static final String MOVE = "move";
+  public static final String END = "end";
+  public static final String UNKNOWN = "unknown";
+  public static final String LEFT = "left";
+  public static final String RIGHT = "right";
+  public static final String UP = "up";
+  public static final String DOWN = "down";
+  private WXComponent component;
+  private GestureDetector mGestureDetector;
+  private Rect globalRect;
+  private Point globalOffset;
+  private Point globalEventOffset;
+  private PointF locEventOffset;
+  private PointF locLeftTop;
+  private long swipeDownTime = -1;
+  private long panDownTime = -1;
+  private WXGestureType mPendingPan = null;//event type to notify when action_up or action_cancel
+  private int mParentOrientation =-1;
+  private boolean mIsPreventMoveEvent = false;
+  private boolean mIsTouchEventConsumed = false; //Reset to false when first touch event, set to true when gesture event fired.
+
+  private boolean requestDisallowInterceptTouchEvent = false;
+
+  private boolean shouldBubbleResult = true;
+  private int     shouldBubbleInterval = 0; //every times try
+  private int     shouldBubbleCallRemainTimes = 0;
+
+  private final List<OnTouchListener> mTouchListeners = new LinkedList<>();
+
+  public WXGesture(WXComponent wxComponent, Context context) {
+    this.component = wxComponent;
+    globalRect = new Rect();
+    globalOffset = new Point();
+    globalEventOffset = new Point();
+    locEventOffset = new PointF();
+    locLeftTop = new PointF();
+    mGestureDetector = new GestureDetector(context, this, new GestureHandler());
+    Scrollable parentScrollable = wxComponent.getParentScroller();
+    if(parentScrollable != null) {
+      mParentOrientation = parentScrollable.getOrientation();
+    }
+    shouldBubbleResult =  WXUtils.getBoolean(wxComponent.getAttrs().get(Constants.Name.SHOULD_STOP_PROPAGATION_INIT_RESULT), true);
+    shouldBubbleInterval = WXUtils.getNumberInt(wxComponent.getAttrs().get(Constants.Name.SHOULD_STOP_PROPAGATION_INTERVAL), 0);
+  }
+
+  private boolean isParentScrollable() {
+    if(component == null) {
+      return true;
+    }
+    Scrollable parentScrollable = component.getParentScroller();
+    return parentScrollable == null || parentScrollable.isScrollable();
+  }
+
+  private boolean hasSameOrientationWithParent(){
+    return (mParentOrientation == Constants.Orientation.HORIZONTAL && component.containsGesture(
+        HighLevelGesture.HORIZONTALPAN))
+            || (mParentOrientation == Constants.Orientation.VERTICAL && component.containsGesture(HighLevelGesture.VERTICALPAN));
+  }
+
+  public void setPreventMoveEvent(boolean preventMoveEvent) {
+    mIsPreventMoveEvent = preventMoveEvent;
+  }
+
+  /**
+   *
+   * @return true if current touch event is already consumed by gesture.
+   * Reset to false when next first touch event, set to true when gesture event fired.
+   */
+  public boolean isTouchEventConsumedByAdvancedGesture(){
+    return mIsTouchEventConsumed;
+  }
+
+
+  /**
+   * stoppropagation
+   * */
+  public static boolean isStopPropagation(String type){
+    return  Constants.Event.STOP_PROPAGATION.equals(type) || Constants.Event.STOP_PROPAGATION_RAX.equals(type);
+  }
+
+  public static boolean hasStopPropagation(WXComponent component){
+    WXEvent event = component.getEvents();
+    if(event == null){
+      return false;
+    }
+    int size = event.size();
+    for (int i=0; i<size; i++) {
+      if(i >= event.size()){
+        break;
+      }
+      String type = event.get(i);
+      if(isStopPropagation(type)){
+        return true;
+      }
+    }
+    return false;
+  }
+
+  /**
+   * shouldBubbleEvent default true
+   * */
+  private boolean shouldBubbleTouchEvent(MotionEvent event){
+    if(hasStopPropagation(component)){
+      if(shouldBubbleInterval > 0 && shouldBubbleCallRemainTimes > 0){
+        shouldBubbleCallRemainTimes--;
+        return  shouldBubbleResult;
+      }
+      Map<String, Object> eventMap = createFireEventParam(event, CUR_EVENT, null);
+      eventMap.put("type", "touch");
+      if(event.getAction() == MotionEvent.ACTION_DOWN){
+        eventMap.put("action", START);
+      }else if(event.getAction() == MotionEvent.ACTION_CANCEL
+              ||  event.getAction() == MotionEvent.ACTION_UP){
+        eventMap.put("action", END);
+      }else{
+        eventMap.put("action", MOVE);
+      }
+
+      String name = Event.STOP_PROPAGATION;
+      if(!component.getEvents().contains(Event.STOP_PROPAGATION)){
+         name = Event.STOP_PROPAGATION_RAX;
+      }
+      EventResult result = component.fireEventWait(name, eventMap);
+      if(result.isSuccess() && result.getResult() != null){
+        boolean stopPropagation = WXUtils.getBoolean(result.getResult(), !shouldBubbleResult);
+        shouldBubbleResult = !stopPropagation;
+      }
+      shouldBubbleCallRemainTimes = shouldBubbleInterval;
+      return shouldBubbleResult;
+
+    }
+    return  true;
+  }
+
+  @SuppressWarnings("unused")
+  public void addOnTouchListener(OnTouchListener listener) {
+    if(listener != null) {
+      mTouchListeners.add(listener);
+    }
+  }
+
+  @SuppressWarnings("unused")
+  public boolean removeTouchListener(OnTouchListener listener) {
+    if(listener != null) {
+      return mTouchListeners.remove(listener);
+    }
+    return false;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouch(View v, MotionEvent event) {
+    if(requestDisallowInterceptTouchEvent){
+      requestDisallowInterceptTouchEvent = false;
+      return false;
+    }
+    try {
+      boolean result = mGestureDetector.onTouchEvent(event);
+
+      if(mTouchListeners != null && !mTouchListeners.isEmpty()) {
+        for(OnTouchListener listener : mTouchListeners) {
+          result |= listener.onTouch(v, event);
+        }
+      }
+
+      switch (event.getActionMasked()) {
+        case MotionEvent.ACTION_POINTER_DOWN:
+        case MotionEvent.ACTION_DOWN:
+          mIsTouchEventConsumed = false;
+          /**
+           * If component has same scroll orientation with it's parent and it's parent not scrollable
+           * , we should disallow parent in DOWN.
+           */
+          if(hasSameOrientationWithParent() && !isParentScrollable()){
+            ViewParent p;
+            if ((p = component.getRealView().getParent()) != null) {
+              p.requestDisallowInterceptTouchEvent(true);
+            }
+          }
+          result |= handleMotionEvent(LowLevelGesture.ACTION_DOWN, event);
+          break;
+        case MotionEvent.ACTION_MOVE:
+          result |= handleMotionEvent(LowLevelGesture.ACTION_MOVE, event);
+          break;
+        case MotionEvent.ACTION_UP:
+        case MotionEvent.ACTION_POINTER_UP:
+          finishDisallowInterceptTouchEvent(v);
+          result |= handleMotionEvent(LowLevelGesture.ACTION_UP, event);
+          result |= handlePanMotionEvent(event);
+          break;
+        case MotionEvent.ACTION_CANCEL:
+          finishDisallowInterceptTouchEvent(v);
+          result |= handleMotionEvent(LowLevelGesture.ACTION_CANCEL, event);
+          result |= handlePanMotionEvent(event);
+          break;
+      }
+      if(hasStopPropagation(component)){
+        ViewGroup parent = (ViewGroup) v.getParent();
+        boolean requestDisallowInterceptTouchEvent = false;
+        if(parent != null){
+          if(!shouldBubbleTouchEvent(event)){
+            requestDisallowInterceptTouchEvent = true;
+          }
+          parent.requestDisallowInterceptTouchEvent(requestDisallowInterceptTouchEvent);
+        }
+        if(component.getParent() != null){
+          component.getParent().requestDisallowInterceptTouchEvent(requestDisallowInterceptTouchEvent);
+        }
+        if(mIsTouchEventConsumed && WXUtils.getBoolean(component.getAttrs().get("cancelTouchOnConsume"), false)){//when touch event consumed by one gesture, other component should not consumed
+          event.setAction(MotionEvent.ACTION_CANCEL);
+        }
+      }
+      return result;
+    } catch (Exception e) {
+      WXLogUtils.e("Gesture RunTime Error ", e);
+      return false;
+    }
+  }
+
+  private String getPanEventAction(MotionEvent event) {
+    switch (event.getAction()) {
+      case MotionEvent.ACTION_DOWN:
+        return START;
+      case MotionEvent.ACTION_MOVE:
+        return MOVE;
+      case MotionEvent.ACTION_UP:
+        return END;
+      case MotionEvent.ACTION_CANCEL:
+        return END;
+      default:
+        return UNKNOWN;
+    }
+  }
+
+  private void finishDisallowInterceptTouchEvent(View v){
+    if(v.getParent() != null){
+      v.getParent().requestDisallowInterceptTouchEvent(false);
+    }
+  }
+
+  private boolean handlePanMotionEvent(MotionEvent motionEvent) {
+    if (mPendingPan == null) {
+      return false;
+    }
+    String state = null;
+    if (mPendingPan == HighLevelGesture.HORIZONTALPAN || mPendingPan == HighLevelGesture.VERTICALPAN) {
+      state = getPanEventAction(motionEvent);
+
+    }
+
+    if (component.containsGesture(mPendingPan)) {
+      if(mIsPreventMoveEvent && MOVE.equals(state)){
+        return true;
+      }
+      List<Map<String, Object>> list = createMultipleFireEventParam(motionEvent, state);
+      for (Map<String, Object> map : list) {
+        component.fireEvent(mPendingPan.toString(), map);
+      }
+      //action is finish, clean pending pan
+      if (motionEvent.getAction() == MotionEvent.ACTION_UP || motionEvent.getAction() == MotionEvent.ACTION_CANCEL) {
+        mPendingPan = null;
+      }
+      return true;
+    } else {
+      return false;
+    }
+  }
+
+  /**
+   *
+   * @param WXGestureType possible low-level gesture, defined in {@link Event}
+   * @param motionEvent motionEvent, which contains all pointers event in a period of time
+   * @return true if this event is handled, otherwise false.
+   */
+  private boolean handleMotionEvent(WXGestureType WXGestureType, MotionEvent motionEvent) {
+    if (component.containsGesture(WXGestureType)) {
+      List<Map<String, Object>> list = createMultipleFireEventParam(motionEvent, null);
+      for (Map<String, Object> map : list) {
+        component.fireEvent(WXGestureType.toString(), map);
+      }
+      return true;
+    } else {
+      return false;
+    }
+  }
+
+  /**
+   * Create a list of event for {@link WXSDKInstance#fireEvent(String, String, Map, Map)}.
+   * As there is a batch mechanism in MotionEvent, so this method returns a list.
+   * @param motionEvent motionEvent, which contains all pointers event in a period of time
+   * @return List of Map, which contains touch object.
+   */
+  private List<Map<String, Object>> createMultipleFireEventParam(MotionEvent motionEvent,String state) {
+    List<Map<String, Object>> list = new ArrayList<>(motionEvent.getHistorySize() + 1);
+    //list.addAll(getHistoricalEvents(motionEvent));
+    list.add(createFireEventParam(motionEvent, CUR_EVENT, state));
+    return list;
+  }
+
+  /**
+   * Get historical event. This is only applied to {@link MotionEvent#ACTION_MOVE}.
+   * For other types of motionEvent, historical event is meaningless.
+   * @param motionEvent motionEvent, which contains all pointers event in a period of time
+   * @return If motionEvent.getActionMasked()!=MotionEvent.ACTION_MOVE,
+   * this method will return an empty list.
+   * Otherwise this method will return the historical motionEvent, which may also be empty.
+   */
+  private List<Map<String, Object>> getHistoricalEvents(MotionEvent motionEvent) {
+    List<Map<String, Object>> list = new ArrayList<>(motionEvent.getHistorySize());
+    if (motionEvent.getActionMasked() == MotionEvent.ACTION_MOVE) {
+      Map<String, Object> param;
+      for (int i = 0; i < motionEvent.getHistorySize(); i++) {
+        param = createFireEventParam(motionEvent, i,null);
+        list.add(param);
+      }
+    }
+    return list;
+  }
+
+  /**
+   * Create a map represented touch event at a certain moment.
+   * @param motionEvent motionEvent, which contains all pointers event in a period of time
+   * @param pos index used to retrieve a certain moment in a period of time.
+   * @return touchEvent
+   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/TouchEvent">touchEvent</a>
+   */
+  private Map<String, Object> createFireEventParam(MotionEvent motionEvent, int pos, String state) {
+    JSONArray jsonArray = new JSONArray(motionEvent.getPointerCount());
+    if (motionEvent.getActionMasked() == MotionEvent.ACTION_MOVE) {
+      for (int i = 0; i < motionEvent.getPointerCount(); i++) {
+        jsonArray.add(createJSONObject(motionEvent, pos, i));
+      }
+    } else if (isPointerNumChanged(motionEvent)) {
+      int pointerIndex = motionEvent.getActionIndex();
+      jsonArray.add(createJSONObject(motionEvent, CUR_EVENT, pointerIndex));
+    }
+    Map<String, Object> map = new HashMap<>();
+    map.put(GestureInfo.HISTORICAL_XY, jsonArray);
+    if (state != null) {
+      map.put(GestureInfo.STATE, state);
+    }
+    return map;
+  }
+
+  /**
+   * Tell whether the number of motion event's pointer changed.
+   * @param event the current motion event
+   * @return true for number of motion event's pointer changed, otherwise false.
+   */
+  private boolean isPointerNumChanged(MotionEvent event) {
+    return event.getActionMasked() == MotionEvent.ACTION_DOWN ||
+            event.getActionMasked() == MotionEvent.ACTION_POINTER_DOWN ||
+            event.getActionMasked() == MotionEvent.ACTION_UP ||
+            event.getActionMasked() == MotionEvent.ACTION_POINTER_UP ||
+            event.getActionMasked() == MotionEvent.ACTION_CANCEL;
+  }
+
+  /**
+   * Tell whether component contains pan gesture
+   * @return true for contains pan gesture, otherwise false.
+   */
+  private boolean containsSimplePan() {
+    return component.containsGesture(HighLevelGesture.PAN_START) ||
+            component.containsGesture(HighLevelGesture.PAN_MOVE) ||
+            component.containsGesture(HighLevelGesture.PAN_END);
+  }
+
+  /**
+   * Create a touchObject for a pointer at a certain moment.
+   * @param motionEvent motionEvent, which contains all pointers event in a period of time
+   * @param pos index used to retrieve a certain moment in a period of time.
+   * @param pointerIndex pointerIndex
+   * @return JSONObject represent a touch event
+   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch">touch</a>
+   */
+  private JSONObject createJSONObject(MotionEvent motionEvent, int pos, int pointerIndex) {
+    PointF screenXY, pageXY;
+    if (pos == CUR_EVENT) {
+      pageXY = getEventLocInPageCoordinate(motionEvent, pointerIndex);
+      screenXY = getEventLocInScreenCoordinate(motionEvent, pointerIndex);
+    } else {
+      pageXY = getEventLocInPageCoordinate(motionEvent, pointerIndex, pos);
+      screenXY = getEventLocInScreenCoordinate(motionEvent, pointerIndex, pos);
+    }
+    JSONObject map = createJSONObject(screenXY, pageXY, (float) motionEvent.getPointerId(pointerIndex));
+    float force = motionEvent.getPressure();
+    if(force > 0 && force < 1) {
+      map.put("force", motionEvent.getPressure());
+    }
+    return map;
+  }
+
+  /**
+   * Create a touchObject for a pointer at a certain moment.
+   * @param screenXY the point of event happened in screen coordinate
+   * @param pageXY the point of event happened in page coorindate
+   * @param pointerId pointerIndex pointerIndex
+   * @return JSONObject represent a touch event
+   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch">touch</a>
+   */
+  @NonNull
+  private JSONObject createJSONObject(PointF screenXY, PointF pageXY, float pointerId) {
+    JSONObject jsonObject = new JSONObject();
+    jsonObject.put(GestureInfo.PAGE_X, pageXY.x);
+    jsonObject.put(GestureInfo.PAGE_Y, pageXY.y);
+    jsonObject.put(GestureInfo.SCREEN_X, screenXY.x);
+    jsonObject.put(GestureInfo.SCREEN_Y, screenXY.y);
+    jsonObject.put(GestureInfo.POINTER_ID, pointerId);
+    return jsonObject;
+  }
+
+  /**
+   * @see {@link #getEventLocInScreenCoordinate(MotionEvent, int, int)}
+   */
+  private PointF getEventLocInScreenCoordinate(MotionEvent motionEvent, int pointerIndex) {
+    return getEventLocInScreenCoordinate(motionEvent, pointerIndex, CUR_EVENT);
+  }
+
+  /**
+   * Get event location in Screen's coordinate, e.g. root(global) coordinate.
+   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/screenX">screenX</a>
+   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/screenY">screenY</a>
+   * @param motionEvent the original motionEvent
+   * @param pointerIndex pointerIndex
+   * @param position if motionEvent.getHistoricalSize()!=0, the is the index of historical event,
+   *                 otherwise this is {@link #CUR_EVENT} which indicates historicalSize is zero
+   * @return the eventLocation in screen's coordinate
+   */
+  private PointF getEventLocInScreenCoordinate(MotionEvent motionEvent, int pointerIndex, int position) {
+    float eventX, eventY;
+    if (position == CUR_EVENT) {
+      eventX = motionEvent.getX(pointerIndex);
+      eventY = motionEvent.getY(pointerIndex);
+    } else {
+      eventX = motionEvent.getHistoricalX(pointerIndex, position);
+      eventY = motionEvent.getHistoricalY(pointerIndex, position);
+    }
+    return getEventLocInScreenCoordinate(eventX, eventY);
+  }
+
+  /**
+   * Get event location in Screen's coordinate, e.g. root(global) coordinate.
+   * @param eventX {@link MotionEvent#getX()} or {@link MotionEvent#getHistoricalX(int, int)}
+   * @param eventY {@link MotionEvent#getX()} or {@link MotionEvent#getHistoricalX(int, int)}
+   * @return the eventLocation in screen's coordinate
+   * @see {@link #getEventLocInScreenCoordinate(MotionEvent, int, int)}
+   */
+  @NonNull
+  private PointF getEventLocInScreenCoordinate(float eventX, float eventY) {
+    globalRect.set(0, 0, 0, 0);
+    globalOffset.set(0, 0);
+    globalEventOffset.set((int) eventX, (int) eventY);
+    component.getRealView().getGlobalVisibleRect(globalRect, globalOffset);
+    globalEventOffset.offset(globalOffset.x, globalOffset.y);
+    return new PointF(WXViewUtils.getWebPxByWidth(globalEventOffset.x,component.getInstance().getInstanceViewPortWidth()),
+            WXViewUtils.getWebPxByWidth(globalEventOffset.y,component.getInstance().getInstanceViewPortWidth()));
+  }
+
+  /**
+   * @see {@link #getEventLocInPageCoordinate(MotionEvent, int, int)}
+   */
+  private PointF getEventLocInPageCoordinate(MotionEvent motionEvent, int pointerIndex) {
+    return getEventLocInPageCoordinate(motionEvent, pointerIndex, CUR_EVENT);
+  }
+
+  /**
+   * Get event's location in Document's (Page) coordinate.
+   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/pageX">pageX</a>
+   * @see <a href="https://developer.mozilla.org/en-US/docs/Web/API/Touch/pageY">pageY</a>
+   * @param motionEvent the original motionEvent
+   * @param pointerIndex pointerIndex
+   * @param position if motionEvent.getHistoricalSize()!=0, the is the index of historical event,
+   *                 otherwise this is {@link #CUR_EVENT} which indicates historicalSize is zero
+   * @return the event location in page's coordinate.
+   */
+  private PointF getEventLocInPageCoordinate(MotionEvent motionEvent, int pointerIndex, int position) {
+    float eventX, eventY;
+    if (position == CUR_EVENT) {
+      eventX = motionEvent.getX(pointerIndex);
+      eventY = motionEvent.getY(pointerIndex);
+    } else {
+      eventX = motionEvent.getHistoricalX(pointerIndex, position);
+      eventY = motionEvent.getHistoricalY(pointerIndex, position);
+    }
+    return getEventLocInPageCoordinate(eventX, eventY);
+  }
+
+  /**
+   * Get event's location in Document's (Page) coordinate.
+   * @param eventX {@link MotionEvent#getX()} or {@link MotionEvent#getHistoricalX(int, int)}
+   * @param eventY {@link MotionEvent#getX()} or {@link MotionEvent#getHistoricalX(int, int)}
+   * @return the event location in page's coordinate.
+   * @see {@link #getEventLocInPageCoordinate(MotionEvent, int, int)}
+   */
+  @NonNull
+  private PointF getEventLocInPageCoordinate(float eventX, float eventY) {
+    locEventOffset.set(eventX, eventY);
+    locLeftTop.set(0, 0);
+    component.computeVisiblePointInViewCoordinate(locLeftTop);
+    locEventOffset.offset(locLeftTop.x, locLeftTop.y);
+    return new PointF(WXViewUtils.getWebPxByWidth(locEventOffset.x,component.getInstance().getInstanceViewPortWidth()),
+            WXViewUtils.getWebPxByWidth(locEventOffset.y,component.getInstance().getInstanceViewPortWidth()));
+  }
+
+  private static class GestureHandler extends android.os.Handler {
+
+    public GestureHandler() {
+      super(Looper.getMainLooper());
+    }
+  }
+
+
+  /***************** OnGestureListener ****************/
+
+  @Override
+  public void onLongPress(MotionEvent e) {
+    if (component.containsGesture(HighLevelGesture.LONG_PRESS)) {
+      List<Map<String, Object>> list = createMultipleFireEventParam(e,null);
+      component.getInstance().fireEvent(
+              component.getRef(),
+              HighLevelGesture.LONG_PRESS.toString(),
+              list.get(list.size() - 1));
+      mIsTouchEventConsumed = true;
+    }
+  }
+
+  /**
+   * Gesture priority：horizontalPan & verticalPan > pan > swipe
+   */
+  @Override
+  public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
+    boolean result = false;
+    if (e1 == null || e2 == null) {
+      return false;
+    }
+    float dx = Math.abs(e2.getX() - e1.getX());
+    float dy = Math.abs(e2.getY() - e1.getY());
+    WXGestureType possiblePan;
+    if (dx > dy) {
+      possiblePan = HighLevelGesture.HORIZONTALPAN;
+    } else {
+      possiblePan = HighLevelGesture.VERTICALPAN;
+    }
+    if (mPendingPan == HighLevelGesture.HORIZONTALPAN || mPendingPan == HighLevelGesture.VERTICALPAN) {
+      //already during directional-pan
+      result = handlePanMotionEvent(e2);
+    } else if (component.containsGesture(possiblePan)) {
+      ViewParent p;
+      if ((p = component.getRealView().getParent()) != null) {
+        p.requestDisallowInterceptTouchEvent(true);
+      }
+      if (mPendingPan != null) {
+        handleMotionEvent(mPendingPan, e2);//finish pan if exist
+      }
+      mPendingPan = possiblePan;
+      component.fireEvent(possiblePan.toString(), createFireEventParam(e2, CUR_EVENT, START));
+
+      result = true;
+    } else if (containsSimplePan()) {
+      if (panDownTime != e1.getEventTime()) {
+        panDownTime = e1.getEventTime();
+        mPendingPan = HighLevelGesture.PAN_END;
+        component.fireEvent(HighLevelGesture.PAN_START.toString(),
+                createFireEventParam(e1, CUR_EVENT, null));
+      } else {
+        component.fireEvent(HighLevelGesture.PAN_MOVE.toString(),
+                createFireEventParam(e2, CUR_EVENT, null));
+      }
+      result = true;
+    } else if (component.containsGesture(HighLevelGesture.SWIPE)) {
+      if (swipeDownTime != e1.getEventTime()) {
+        swipeDownTime = e1.getEventTime();
+        List<Map<String, Object>> list = createMultipleFireEventParam(e2, null);
+        Map<String, Object> param = list.get(list.size() - 1);
+        if (Math.abs(distanceX) > Math.abs(distanceY)) {
+          param.put(GestureInfo.DIRECTION, distanceX > 0 ? LEFT : RIGHT);
+        } else {
+          param.put(GestureInfo.DIRECTION, distanceY > 0 ? UP : DOWN);
+        }
+        component.getInstance().fireEvent(component.getRef(),
+                HighLevelGesture.SWIPE.toString(), param);
+        result = true;
+      }
+    }
+    mIsTouchEventConsumed = mIsTouchEventConsumed || result;
+    return result;
+  }
+
+  @Override
+  public boolean onDown(MotionEvent e) {
+    return true;
+  }
+
+  public boolean isRequestDisallowInterceptTouchEvent() {
+    return requestDisallowInterceptTouchEvent;
+  }
+
+  public void setRequestDisallowInterceptTouchEvent(boolean requestDisallowInterceptTouchEvent) {
+    this.requestDisallowInterceptTouchEvent = requestDisallowInterceptTouchEvent;
+  }
+
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGestureObservable.java b/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGestureObservable.java
new file mode 100644
index 0000000..9cab499
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGestureObservable.java
@@ -0,0 +1,49 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.gesture;
+
+import android.support.annotation.Nullable;
+import android.view.MotionEvent;
+import android.view.View;
+
+import org.apache.weex.ui.view.WXFrameLayout;
+
+/**
+ * Views that want to receive Gesture Event must implement this interface. Besides,
+ * those view must override their {@link android.view.View#onTouchEvent(MotionEvent)}
+ * and add method invocation to {@link WXGesture#onTouch(View, MotionEvent)}.
+ * Refer to {@link WXFrameLayout#onTouchEvent(MotionEvent)} for more info.
+ *
+ */
+public interface WXGestureObservable {
+
+  /**
+   * Register a {@link WXGesture} for corresponding view.
+   * @param wxGesture The Gesture to register, null for unregister.
+   */
+  void registerGestureListener(@Nullable WXGesture wxGesture);
+
+  /**
+   * Get gesture listener for corresponding view.
+   *
+   * @return the gesture listener has register before
+   *
+   * */
+  WXGesture getGestureListener();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGestureType.java b/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGestureType.java
new file mode 100644
index 0000000..f6620fe
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/gesture/WXGestureType.java
@@ -0,0 +1,71 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.gesture;
+
+public interface WXGestureType {
+
+  enum LowLevelGesture implements WXGestureType {
+    ACTION_DOWN("touchstart"),
+    ACTION_MOVE("touchmove"),
+    ACTION_UP("touchend"),
+    ACTION_CANCEL("touchcancel");
+    private String description;
+
+    LowLevelGesture(String description) {
+      this.description = description;
+    }
+
+    @Override
+    public String toString() {
+      return description;
+    }
+  }
+
+  enum HighLevelGesture implements WXGestureType {
+    SWIPE("swipe"),
+    LONG_PRESS("longpress"),
+    PAN_START("panstart"),
+    PAN_MOVE("panmove"),
+    PAN_END("panend"),
+    HORIZONTALPAN("horizontalpan"),
+    VERTICALPAN("verticalpan");
+    private String description;
+
+    HighLevelGesture(String description) {
+      this.description = description;
+    }
+
+    @Override
+    public String toString() {
+      return description;
+    }
+  }
+
+  class GestureInfo {
+
+    public static final String HISTORICAL_XY = "changedTouches";
+    public static final String PAGE_X = "pageX";
+    public static final String PAGE_Y = "pageY";
+    public static final String SCREEN_X = "screenX";
+    public static final String SCREEN_Y = "screenY";
+    public static final String POINTER_ID = "identifier";
+    public static final String DIRECTION = "direction";
+    public static final String STATE = "state";
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/ExtendedLinearLayoutManager.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/ExtendedLinearLayoutManager.java
new file mode 100644
index 0000000..c4dd32a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/ExtendedLinearLayoutManager.java
@@ -0,0 +1,115 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview;
+
+import android.content.Context;
+import android.graphics.PointF;
+import android.support.v7.widget.LinearLayoutManager;
+import android.support.v7.widget.LinearSmoothScroller;
+import android.support.v7.widget.RecyclerView;
+
+/**
+ * Created by moxun on 17/2/16.
+ */
+
+public class ExtendedLinearLayoutManager extends LinearLayoutManager{
+
+    private RecyclerView.SmoothScroller smoothScroller;
+
+
+    private OnSmoothScrollEndListener onScrollEndListener;
+
+    public ExtendedLinearLayoutManager(Context context) {
+        super(context, VERTICAL, false);
+    }
+
+    public ExtendedLinearLayoutManager(Context context, int orientation, boolean reverseLayout) {
+        super(context, orientation, reverseLayout);
+    }
+
+    @Override
+    public boolean supportsPredictiveItemAnimations() {
+        return false;
+    }
+
+    public void onLayoutChildren(RecyclerView.Recycler recycler, RecyclerView.State state) {
+        try {
+            super.onLayoutChildren(recycler, state);
+        } catch (IndexOutOfBoundsException e) {
+            e.printStackTrace();
+
+        }
+    }
+
+    @Override
+    public int scrollVerticallyBy(int dy, RecyclerView.Recycler recycler, RecyclerView.State state) {
+        try {
+            return super.scrollVerticallyBy(dy, recycler, state);
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+        return 0;
+    }
+
+
+    @Override
+    public void smoothScrollToPosition(RecyclerView recyclerView, RecyclerView.State state,
+                                       int position) {
+        if (smoothScroller == null) {
+            smoothScroller = new ExtendedLinearLayoutManager.TopSnappedSmoothScroller(recyclerView.getContext());
+        }
+        smoothScroller.setTargetPosition(position);
+        startSmoothScroll(smoothScroller);
+    }
+
+    private class TopSnappedSmoothScroller extends LinearSmoothScroller {
+        public TopSnappedSmoothScroller(Context context) {
+            super(context);
+
+        }
+
+        @Override
+        public PointF computeScrollVectorForPosition(int targetPosition) {
+            return ExtendedLinearLayoutManager.this
+                    .computeScrollVectorForPosition(targetPosition);
+        }
+
+        @Override
+        protected int getVerticalSnapPreference() {
+            return SNAP_TO_START;
+        }
+
+        @Override
+        protected void onStop() {
+            super.onStop();
+            if(onScrollEndListener != null){
+                onScrollEndListener.onStop();
+                onScrollEndListener = null;
+            }
+        }
+    }
+
+    public void setOnScrollEndListener(OnSmoothScrollEndListener onScrollEndListener) {
+        this.onScrollEndListener = onScrollEndListener;
+    }
+
+    public interface OnSmoothScrollEndListener {
+        void  onStop();
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/ExtendedStaggeredGridLayoutManager.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/ExtendedStaggeredGridLayoutManager.java
new file mode 100644
index 0000000..a49d110
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/ExtendedStaggeredGridLayoutManager.java
@@ -0,0 +1,49 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview;
+
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.utils.WXLogUtils;
+
+/**
+ * Created by zhengshihan on 2017/5/5.
+ */
+
+public class ExtendedStaggeredGridLayoutManager extends StaggeredGridLayoutManager{
+
+  public ExtendedStaggeredGridLayoutManager(int spanCount, int orientation) {
+    super(spanCount, orientation);
+  }
+
+  @Override
+  public void onItemsRemoved(RecyclerView recyclerView, int positionStart, int itemCount) {
+    if(positionStart ==-1){
+      WXLogUtils.e("ExtendedStaggeredGridLayoutManager: onItemsRemoved  Error Invalid Index : positionStart :"+positionStart +"  itemCount:"+ itemCount);
+      return ;
+    }else {
+      if(WXEnvironment.isApkDebugable()){
+        WXLogUtils.e("ExtendedStaggeredGridLayoutManager: onItemsRemoved  positionStart :"+positionStart+"  itemCount:"+ itemCount);
+      }
+    }
+    super.onItemsRemoved(recyclerView, positionStart, itemCount);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/WXRecyclerView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/WXRecyclerView.java
new file mode 100644
index 0000000..0bc6b96
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/WXRecyclerView.java
@@ -0,0 +1,157 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview;
+
+import android.annotation.SuppressLint;
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.os.Build;
+import android.support.annotation.Nullable;
+import android.support.v7.widget.GridLayoutManager;
+import android.support.v7.widget.LinearLayoutManager;
+import android.support.v7.widget.OrientationHelper;
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+import android.view.MotionEvent;
+
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXThread;
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+
+public class WXRecyclerView extends RecyclerView implements WXGestureObservable {
+
+  public static final int TYPE_LINEAR_LAYOUT = 1;
+  public static final int TYPE_GRID_LAYOUT = 2;
+  public static final int TYPE_STAGGERED_GRID_LAYOUT = 3;
+  private WXGesture mGesture;
+  private boolean scrollable = true;
+  private boolean hasTouch = false;
+
+
+  public WXRecyclerView(Context context) {
+    super(context);
+  }
+
+  public boolean isScrollable() {
+    return scrollable;
+  }
+
+  public void setScrollable(boolean scrollable) {
+    this.scrollable = scrollable;
+  }
+
+  public void initView(Context context, int type,int orientation) {
+    initView(context,type, Constants.Value.COLUMN_COUNT_NORMAL,Constants.Value.COLUMN_GAP_NORMAL,orientation);
+  }
+
+
+  /**
+   *
+   * @param context
+   * @param type
+   * @param orientation should be {@link OrientationHelper#HORIZONTAL} or {@link OrientationHelper#VERTICAL}
+   */
+  @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
+  public void initView(Context context, int type, int columnCount, float columnGap, int orientation) {
+    if (type == TYPE_GRID_LAYOUT) {
+      setLayoutManager(new GridLayoutManager(context, columnCount,orientation,false));
+    } else if (type == TYPE_STAGGERED_GRID_LAYOUT) {
+      setLayoutManager(new ExtendedStaggeredGridLayoutManager(columnCount, orientation));
+    } else if (type == TYPE_LINEAR_LAYOUT) {
+      setLayoutManager(new ExtendedLinearLayoutManager(context,orientation,false));
+    }
+  }
+
+  @Override
+  public void registerGestureListener(@Nullable WXGesture wxGesture) {
+    mGesture = wxGesture;
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return mGesture;
+  }
+
+  @SuppressLint("ClickableViewAccessibility")
+  @Override
+  public boolean onTouchEvent(MotionEvent event) {
+    if(!scrollable) {
+      return true;
+    }
+    return super.onTouchEvent(event);
+  }
+
+  @Override
+  public boolean dispatchTouchEvent(MotionEvent event) {
+    hasTouch = true;
+    boolean result = super.dispatchTouchEvent(event);
+    if (mGesture != null) {
+      result |= mGesture.onTouch(this, event);
+    }
+    return result;
+  }
+
+  public void scrollTo(boolean smooth, int position, final  int offset, final int orientation){
+    if (!smooth) {
+      RecyclerView.LayoutManager layoutManager = getLayoutManager();
+      if (layoutManager instanceof LinearLayoutManager) {
+        //GridLayoutManager is also instance of LinearLayoutManager
+        ((LinearLayoutManager) layoutManager).scrollToPositionWithOffset(position, -offset);
+      } else if (layoutManager instanceof StaggeredGridLayoutManager) {
+        ((StaggeredGridLayoutManager) layoutManager).scrollToPositionWithOffset(position, -offset);
+      }
+      //Any else?
+    } else {
+      smoothScrollToPosition(position);
+      if (offset != 0) {
+        setOnSmoothScrollEndListener(new ExtendedLinearLayoutManager.OnSmoothScrollEndListener() {
+          @Override
+          public void onStop() {
+            post(WXThread.secure(new Runnable() {
+              @Override
+              public void run() {
+                if (orientation == Constants.Orientation.VERTICAL) {
+                  smoothScrollBy(0, offset);
+                } else {
+                  smoothScrollBy(offset, 0);
+                }
+              }
+            }));
+          }
+        });
+      }
+    }
+  }
+
+  public void setOnSmoothScrollEndListener(final ExtendedLinearLayoutManager.OnSmoothScrollEndListener onSmoothScrollEndListener){
+    addOnScrollListener(new RecyclerView.OnScrollListener() {
+      @Override
+      public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
+        if (newState == RecyclerView.SCROLL_STATE_IDLE) {
+          recyclerView.removeOnScrollListener(this);
+          if(onSmoothScrollEndListener != null){
+            onSmoothScrollEndListener.onStop();
+          }
+        }
+      }
+    });
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/IOnLoadMoreListener.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/IOnLoadMoreListener.java
new file mode 100644
index 0000000..79632b2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/IOnLoadMoreListener.java
@@ -0,0 +1,27 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview.adapter;
+
+
+public interface IOnLoadMoreListener {
+
+  void onLoadMore(int offScreenY);
+  void notifyAppearStateChange(int firstVisible, int lastVisible, int directionX, int directionY);
+  void onBeforeScroll(int dx, int dy);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/IRecyclerAdapterListener.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/IRecyclerAdapterListener.java
new file mode 100644
index 0000000..934cd5d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/IRecyclerAdapterListener.java
@@ -0,0 +1,42 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview.adapter;
+
+import android.support.v7.widget.RecyclerView;
+import android.view.ViewGroup;
+
+/**
+ * Listener for recyclerView event
+ */
+public interface IRecyclerAdapterListener<T extends RecyclerView.ViewHolder> {
+
+  void onViewRecycled(T holder);
+
+  void onBindViewHolder(T holder, int position);
+
+  T onCreateViewHolder(ViewGroup parent, int viewType);
+
+  int getItemViewType(int position);
+
+  int getItemCount();
+
+  boolean onFailedToRecycleView(T holder);
+
+  long getItemId(int position);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/ListBaseViewHolder.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/ListBaseViewHolder.java
new file mode 100644
index 0000000..ce959ae
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/ListBaseViewHolder.java
@@ -0,0 +1,106 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview.adapter;
+
+import android.support.v7.widget.RecyclerView;
+import android.view.View;
+
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.component.WXHeader;
+
+import java.lang.ref.WeakReference;
+
+
+/**
+ * There are bi-directional association between ViewHolder and View.
+ * This is accomplished by weak-reference and final field from ViewHolder to View.
+ * From View to ViewHolder, this is done by set {@link android.view.ViewGroup.LayoutParams} to View.
+ */
+public class ListBaseViewHolder extends RecyclerView.ViewHolder {
+  private int mViewType;
+  private boolean isRecycled;
+  private WeakReference<WXComponent> mComponent;
+
+  public ListBaseViewHolder(WXComponent component, int viewType) {
+    super(component.getHostView());
+    mViewType = viewType;
+    mComponent = new WeakReference(component);
+    // This tag is used to determine whether bind / rebind data is needed.
+    // It should be false When component can not be recycled Which means
+    // no need to bind / rebind data.
+    isRecycled = component.canRecycled();
+  }
+
+  public ListBaseViewHolder(WXComponent component, int viewType, boolean forceBindData) {
+    this(component, viewType);
+    isRecycled = isRecycled || forceBindData;
+  }
+
+  public ListBaseViewHolder(View view, int viewType) {
+    super(view);
+    mViewType = viewType;
+  }
+
+  public boolean isRecycled() {
+    return isRecycled;
+  }
+
+  public void recycled() {
+    if (mComponent != null && mComponent.get() != null) {
+      mComponent.get().recycled();
+      isRecycled = true;
+
+    }
+  }
+
+  public void bindData(WXComponent component) {
+    if (mComponent != null && mComponent.get() != null) {
+      mComponent.get().bindData(component);
+      isRecycled = false;
+    }
+  }
+    
+  public boolean isFullSpan() {
+    return mComponent != null && mComponent.get() instanceof WXHeader;
+  }
+
+  public boolean canRecycled() {
+    if (mComponent != null && mComponent.get() != null) {
+      return mComponent.get().canRecycled();
+    }
+    return true;
+  }
+
+  public View getView() {
+    return itemView;
+  }
+
+  public int getViewType() {
+    return mViewType;
+  }
+
+  public void setComponentUsing(boolean using) {
+    if (mComponent != null && mComponent.get() != null)
+      mComponent.get().setUsing(using);
+  }
+
+  public WXComponent getComponent() {
+    return mComponent != null ? mComponent.get() : null;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/RecyclerViewBaseAdapter.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/RecyclerViewBaseAdapter.java
new file mode 100644
index 0000000..38ce0a2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/RecyclerViewBaseAdapter.java
@@ -0,0 +1,110 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview.adapter;
+
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+import android.view.ViewGroup;
+
+
+/**
+ * Adapter for recyclerView
+ */
+public class RecyclerViewBaseAdapter<T extends ListBaseViewHolder> extends RecyclerView.Adapter<T> {
+
+  private IRecyclerAdapterListener iRecyclerAdapterListener;
+
+  public RecyclerViewBaseAdapter(IRecyclerAdapterListener Listener) {
+    this.iRecyclerAdapterListener = Listener;
+  }
+
+  @Override
+  public T onCreateViewHolder(ViewGroup parent, int viewType) {
+    if (iRecyclerAdapterListener != null) {
+      return (T) iRecyclerAdapterListener.onCreateViewHolder(parent, viewType);
+    }
+
+    return null;
+  }
+
+  @Override
+  public void onViewAttachedToWindow(T holder) {
+    super.onViewAttachedToWindow(holder);
+    if( holder !=null && holder.isFullSpan()){
+      ViewGroup.LayoutParams lp = holder.itemView.getLayoutParams();
+      if(lp != null
+              && lp instanceof StaggeredGridLayoutManager.LayoutParams
+              ) {
+        StaggeredGridLayoutManager.LayoutParams p = (StaggeredGridLayoutManager.LayoutParams) lp;
+        p.setFullSpan(true);
+      }
+    }
+  }
+
+  @Override
+  public void onViewDetachedFromWindow(T holder) {
+    super.onViewDetachedFromWindow(holder);
+    if (holder != null)
+      holder.setComponentUsing(false);
+  }
+
+  @Override
+  public void onBindViewHolder(T viewHolder, int i) {
+    if (iRecyclerAdapterListener != null) {
+      iRecyclerAdapterListener.onBindViewHolder(viewHolder, i);
+    }
+  }
+
+  @Override
+  public int getItemViewType(int position) {
+    if (iRecyclerAdapterListener != null) {
+      return iRecyclerAdapterListener.getItemViewType(position);
+    }
+    return position;
+  }
+
+  @Override
+  public long getItemId(int position) {
+    return iRecyclerAdapterListener.getItemId(position);
+  }
+
+  @Override
+  public int getItemCount() {
+    if (iRecyclerAdapterListener != null) {
+      return iRecyclerAdapterListener.getItemCount();
+    }
+    return 0;
+  }
+
+  @Override
+  public void onViewRecycled(T holder) {
+    if (iRecyclerAdapterListener != null) {
+      iRecyclerAdapterListener.onViewRecycled(holder);
+    }
+    super.onViewRecycled(holder);
+  }
+
+  @Override
+  public boolean onFailedToRecycleView(T holder) {
+    if (iRecyclerAdapterListener != null) {
+      return iRecyclerAdapterListener.onFailedToRecycleView(holder);
+    }
+    return super.onFailedToRecycleView(holder);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/TransformItemDecoration.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/TransformItemDecoration.java
new file mode 100644
index 0000000..2dae5c3
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/TransformItemDecoration.java
@@ -0,0 +1,93 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview.adapter;
+
+import android.graphics.Canvas;
+import android.support.v7.widget.RecyclerView;
+import android.view.View;
+
+public class TransformItemDecoration extends RecyclerView.ItemDecoration{
+  boolean mIsVertical = true;
+  float mAlpha = -1f;
+  int mXTranslate = 0;
+  int mYTranslate = 0;
+  int mRotation = 0;
+  float mScaleX = 0;
+  float mScaleY  = 0;
+
+  public TransformItemDecoration(boolean isVertical,float alpha,int translateX,int translateY,int rotation,float scaleX,float scaleY){
+    this.mIsVertical = isVertical;
+    this.mAlpha = alpha;
+    this.mXTranslate = translateX;
+    this.mYTranslate = translateY;
+    this.mRotation = rotation;
+    this.mScaleX = scaleX;
+    this.mScaleY = scaleY;
+  }
+
+
+  @Override
+  public void onDrawOver(Canvas c, RecyclerView parent, RecyclerView.State state) {
+    super.onDrawOver(c, parent, state);
+    int width = parent.getWidth();
+    int height = parent.getHeight();
+    for (int i = 0,count=parent.getChildCount(); i < count; i++) {
+      updateItem(parent.getChildAt(i),width,height);
+    }
+  }
+
+  private void updateItem(View child, int width, int height) {
+    int size,childCenter,containerSize;
+    if (mIsVertical) {
+      containerSize = height;
+      size = child.getHeight();
+      childCenter = child.getTop() + size / 2;
+    } else {
+      containerSize = width;
+      size = child.getWidth();
+      childCenter = child.getLeft() + size / 2;
+    }
+
+    final int actionDistance = (containerSize + size) / 2;
+    final float effectsAmount = Math.min(1.0f, Math.max(-1.0f, (1.0f / actionDistance) * (childCenter - containerSize/2)));
+
+
+    if(mAlpha>0){
+      child.setAlpha(1-mAlpha*Math.abs(effectsAmount));
+    }
+
+    if(mScaleX>0||mScaleY>0){
+      child.setScaleX(1-mScaleX*Math.abs(effectsAmount));
+      child.setScaleY(1-mScaleY*Math.abs(effectsAmount));
+    }
+
+    if(mRotation!=0){
+      child.setRotation(mRotation * effectsAmount);
+    }
+
+    if(mXTranslate!=0){
+      child.setTranslationX(mXTranslate * Math.abs( effectsAmount));
+    }
+
+    if(mYTranslate!=0){
+      child.setTranslationY(mYTranslate * Math.abs( effectsAmount));
+    }
+
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/WXRecyclerViewOnScrollListener.java b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/WXRecyclerViewOnScrollListener.java
new file mode 100644
index 0000000..fd14e1b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/listview/adapter/WXRecyclerViewOnScrollListener.java
@@ -0,0 +1,180 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.listview.adapter;
+
+import android.support.v7.widget.GridLayoutManager;
+import android.support.v7.widget.LinearLayoutManager;
+import android.support.v7.widget.RecyclerView;
+import android.support.v7.widget.StaggeredGridLayoutManager;
+
+import org.apache.weex.utils.WXLogUtils;
+
+import java.lang.ref.WeakReference;
+
+
+/**
+ * Listener for scroll event of recyclerView
+ */
+public class WXRecyclerViewOnScrollListener extends RecyclerView.OnScrollListener {
+
+  /**
+   * type of layoutManager
+   */
+  protected LAYOUT_MANAGER_TYPE layoutManagerType;
+
+  /**
+   * The last position
+   */
+  private int[] mLastPositions;
+  /**
+   * The first position
+   */
+  private int[] mFirstPositions;
+
+
+  /**
+   * The location of last visible item
+   */
+  private int mLastVisibleItemPosition;
+
+  /**
+   * The location of last visible item
+   */
+  private int mFirstVisibleItemPosition;
+
+  /**
+   * The state of scroll status
+   */
+  private int mCurrentScrollState = 0;
+
+  private WeakReference<IOnLoadMoreListener> listener;
+
+  public WXRecyclerViewOnScrollListener(IOnLoadMoreListener listener) {
+    this.listener = new WeakReference<>(listener);
+  }
+
+  @Override
+  public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
+    super.onScrollStateChanged(recyclerView, newState);
+    mCurrentScrollState = newState;
+    RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
+    int visibleItemCount = layoutManager.getChildCount();
+    int totalItemCount = layoutManager.getItemCount();
+
+    if (visibleItemCount != 0) {
+      int bottomOffset = (totalItemCount - mLastVisibleItemPosition - 1) * (recyclerView.getHeight()) / visibleItemCount;
+      if (visibleItemCount > 0 && mCurrentScrollState == RecyclerView.SCROLL_STATE_IDLE) {
+        if (listener != null && listener.get() != null) {
+          listener.get().onLoadMore(bottomOffset);
+        }
+      }
+    }
+  }
+
+  @Override
+  public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
+    super.onScrolled(recyclerView, dx, dy);
+    RecyclerView.LayoutManager layoutManager = recyclerView.getLayoutManager();
+    if(listener == null){
+      return;
+    }
+    IOnLoadMoreListener iOnLoadMoreListener = listener.get();
+
+    if(iOnLoadMoreListener!=null) {
+
+      iOnLoadMoreListener.onBeforeScroll(dx, dy);
+
+      if (layoutManager instanceof LinearLayoutManager) {
+        layoutManagerType = LAYOUT_MANAGER_TYPE.LINEAR;
+        LinearLayoutManager linearLayoutManager = (LinearLayoutManager) layoutManager;
+        mLastVisibleItemPosition = linearLayoutManager.findLastVisibleItemPosition();
+        int firstVisible = linearLayoutManager.findFirstVisibleItemPosition();
+        iOnLoadMoreListener.notifyAppearStateChange(firstVisible
+            , mLastVisibleItemPosition
+            , dx
+            , dy);
+      } else if (layoutManager instanceof GridLayoutManager) {
+        layoutManagerType = LAYOUT_MANAGER_TYPE.GRID;
+        GridLayoutManager gridLayoutManager = (GridLayoutManager) layoutManager;
+        mLastVisibleItemPosition = gridLayoutManager.findLastVisibleItemPosition();
+        iOnLoadMoreListener.notifyAppearStateChange(gridLayoutManager.findFirstVisibleItemPosition()
+            , mLastVisibleItemPosition
+            , dx
+            , dy);
+
+      } else if (layoutManager instanceof StaggeredGridLayoutManager) {
+        layoutManagerType = LAYOUT_MANAGER_TYPE.STAGGERED_GRID;
+        StaggeredGridLayoutManager staggeredGridLayoutManager = (StaggeredGridLayoutManager) layoutManager;
+        int newSpanCount = staggeredGridLayoutManager.getSpanCount();
+        if (mLastPositions == null || newSpanCount != mLastPositions.length) {
+          mLastPositions = new int[newSpanCount];
+        }
+        if (mFirstPositions == null || newSpanCount != mFirstPositions.length) {
+          mFirstPositions = new int[newSpanCount];
+        }
+        //avoid crash of support-v7 original bug
+        try{
+          staggeredGridLayoutManager.findFirstVisibleItemPositions(mFirstPositions);
+          mFirstVisibleItemPosition = findMin(mFirstPositions);
+          staggeredGridLayoutManager.findLastVisibleItemPositions(mLastPositions);
+          mLastVisibleItemPosition = findMax(mLastPositions);
+          iOnLoadMoreListener.notifyAppearStateChange(
+              mFirstVisibleItemPosition
+              , mLastVisibleItemPosition
+              , dx
+              , dy);
+
+        }catch(Exception e){
+          e.printStackTrace();
+          WXLogUtils.e(e.toString());
+        }
+
+      } else {
+        throw new RuntimeException(
+            "Unsupported LayoutManager used. Valid ones are LinearLayoutManager, GridLayoutManager and StaggeredGridLayoutManager");
+      }
+    }
+  }
+
+  private int findMax(int[] lastPositions) {
+    int max = lastPositions[0];
+    for (int value : lastPositions) {
+      if (value > max) {
+        max = value;
+      }
+    }
+    return max;
+  }
+
+  private int findMin(int[] firstPositions) {
+    int min = firstPositions[0];
+    for (int value : firstPositions) {
+      if (value < min) {
+        min = value;
+      }
+    }
+    return min;
+  }
+
+  public enum LAYOUT_MANAGER_TYPE {
+    LINEAR,
+    GRID,
+    STAGGERED_GRID
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/circlebar/CircleProgressBar.java b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/circlebar/CircleProgressBar.java
new file mode 100644
index 0000000..cbb581f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/circlebar/CircleProgressBar.java
@@ -0,0 +1,329 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.refresh.circlebar;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.Paint;
+import android.graphics.RadialGradient;
+import android.graphics.Shader;
+import android.graphics.drawable.ShapeDrawable;
+import android.graphics.drawable.shapes.OvalShape;
+import android.support.v4.view.ViewCompat;
+import android.util.AttributeSet;
+import android.view.animation.Animation;
+import android.widget.ImageView;
+
+/**
+ * Modify of android.support.v4
+ */
+@SuppressLint("AppCompatCustomView")
+public class CircleProgressBar extends ImageView {
+
+  private static final int KEY_SHADOW_COLOR = 0x1E000000;
+  private static final int FILL_SHADOW_COLOR = 0x3D000000;
+  private static final float X_OFFSET = 0f;
+  private static final float Y_OFFSET = 1.75f;
+  private static final float SHADOW_RADIUS = 3.5f;
+  private static final int SHADOW_ELEVATION = 4;
+
+  public static final int DEFAULT_CIRCLE_BG_LIGHT = 0xFFFAFAFA;
+  public static final int DEFAULT_CIRCLE_COLOR = 0xFFF00000;
+  private static final int DEFAULT_CIRCLE_DIAMETER = 40;
+  private static final int STROKE_WIDTH_LARGE = 3;
+
+  private Animation.AnimationListener mListener;
+  private int mShadowRadius;
+  private int mBackGroundColor;
+  private int mProgressColor;
+  private int mProgressStokeWidth;
+  private int mArrowWidth;
+  private int mArrowHeight;
+  private int mProgress;
+  private int mMax;
+  private int mDiameter;
+  private int mInnerRadius;
+  private boolean mShowArrow;
+  public MaterialProgressDrawable mProgressDrawable;
+  private ShapeDrawable mBgCircle;
+  private boolean mCircleBackgroundEnabled;
+  private int[] mColors = new int[]{Color.BLACK};
+
+  public CircleProgressBar(Context context) {
+    super(context);
+    init(context, null, 0);
+
+  }
+
+  public CircleProgressBar(Context context, AttributeSet attrs) {
+    super(context, attrs);
+    init(context, attrs, 0);
+
+  }
+
+  public CircleProgressBar(Context context, AttributeSet attrs, int defStyleAttr) {
+    super(context, attrs, defStyleAttr);
+    init(context, attrs, defStyleAttr);
+  }
+
+  private void init(Context context, AttributeSet attrs, int defStyleAttr) {
+
+    final float density = getContext().getResources().getDisplayMetrics().density;
+    mBackGroundColor = DEFAULT_CIRCLE_BG_LIGHT;
+    mProgressColor = DEFAULT_CIRCLE_COLOR;
+    mColors = new int[]{mProgressColor};
+    mInnerRadius = -1;
+    mProgressStokeWidth = (int) (STROKE_WIDTH_LARGE * density);
+    mArrowWidth =  -1;
+    mArrowHeight = -1;
+    mShowArrow = true;
+    mCircleBackgroundEnabled = true;
+    mProgress = 0;
+    mMax = 100;
+    mProgressDrawable = new MaterialProgressDrawable(getContext(), this);
+    super.setImageDrawable(mProgressDrawable);
+  }
+
+  public void setProgressBackGroundColor(int color) {
+    this.mBackGroundColor = color;
+  }
+
+  private boolean elevationSupported() {
+    return android.os.Build.VERSION.SDK_INT >= 21;
+  }
+
+  @Override
+  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+    super.onMeasure(widthMeasureSpec, heightMeasureSpec);
+    if (!elevationSupported()) {
+      setMeasuredDimension(getMeasuredWidth() + mShadowRadius * 2, getMeasuredHeight()
+                                                                   + mShadowRadius * 2);
+    }
+  }
+
+  public int getProgressStokeWidth() {
+    return mProgressStokeWidth;
+  }
+
+  public void setProgressStokeWidth(int mProgressStokeWidth) {
+    final float density = getContext().getResources().getDisplayMetrics().density;
+    this.mProgressStokeWidth = (int) (mProgressStokeWidth * density);
+  }
+
+  @Override
+  protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+    super.onLayout(changed, left, top, right, bottom);
+    final float density = getContext().getResources().getDisplayMetrics().density;
+    mDiameter = Math.min(getMeasuredWidth(), getMeasuredHeight());
+    if (mDiameter <= 0) {
+      mDiameter = (int) density * DEFAULT_CIRCLE_DIAMETER;
+    }
+    if (getBackground() == null && mCircleBackgroundEnabled) {
+      final int shadowYOffset = (int) (density * Y_OFFSET);
+      final int shadowXOffset = (int) (density * X_OFFSET);
+      mShadowRadius = (int) (density * SHADOW_RADIUS);
+
+      if (elevationSupported()) {
+        if(mBgCircle == null) {
+          mBgCircle = new ShapeDrawable(new OvalShape());
+        }
+        ViewCompat.setElevation(this, SHADOW_ELEVATION * density);
+      } else {
+        if(!(mBgCircle != null &&
+            mBgCircle.getShape() instanceof  OvalShadow &&
+            ((OvalShadow) mBgCircle.getShape()).mCircleDiameter == (mDiameter - mShadowRadius * 2) &&
+            ((OvalShadow) mBgCircle.getShape()).mShadowRadius == mShadowRadius)) {
+          OvalShape oval = new OvalShadow(mShadowRadius, mDiameter - mShadowRadius * 2);
+          mBgCircle = new ShapeDrawable(oval);
+        }
+        ViewCompat.setLayerType(this, ViewCompat.LAYER_TYPE_SOFTWARE, mBgCircle.getPaint());
+        mBgCircle.getPaint().setShadowLayer(mShadowRadius, shadowXOffset, shadowYOffset,
+                                            KEY_SHADOW_COLOR);
+        final int padding = (int) mShadowRadius;
+        // set padding so the inner image sits correctly within the shadow.
+        setPadding(padding, padding, padding, padding);
+      }
+      mBgCircle.getPaint().setColor(mBackGroundColor);
+      setBackgroundDrawable(mBgCircle);
+    }
+    mProgressDrawable.setBackgroundColor(mBackGroundColor);
+    mProgressDrawable.setColorSchemeColors(mColors);
+    if (isShowArrow()) {
+      mProgressDrawable.setArrowScale(1f);
+      mProgressDrawable.showArrow(true);
+    }
+    super.setImageDrawable(null);
+    super.setImageDrawable(mProgressDrawable);
+    mProgressDrawable.setAlpha(255);
+    if (getVisibility() == VISIBLE) {
+      mProgressDrawable.setStartEndTrim(0, (float) 0.8);
+    }
+  }
+
+  public boolean isShowArrow() {
+    return mShowArrow;
+  }
+
+  public void setShowArrow(boolean showArrow) {
+    this.mShowArrow = showArrow;
+  }
+
+  public void setAnimationListener(Animation.AnimationListener listener) {
+    mListener = listener;
+  }
+
+  @Override
+  public void onAnimationStart() {
+    super.onAnimationStart();
+    if (mListener != null) {
+      mListener.onAnimationStart(getAnimation());
+    }
+  }
+
+  @Override
+  public void onAnimationEnd() {
+    super.onAnimationEnd();
+    if (mListener != null) {
+      mListener.onAnimationEnd(getAnimation());
+    }
+  }
+
+  /**
+   * Set the colors used in the progress animation. The first
+   * color will also be the color of the bar that grows in response to a user
+   * swipe gesture.
+   *
+   * @param colors
+   */
+  public void setColorSchemeColors(int... colors) {
+    mColors = colors;
+    if (mProgressDrawable != null) {
+      mProgressDrawable.setColorSchemeColors(colors);
+    }
+  }
+
+  /**
+   * Update the background color of the mBgCircle image view.
+   */
+  public void setBackgroundColorResource(int colorRes) {
+    if (getBackground() instanceof ShapeDrawable) {
+      final Resources res = getResources();
+      ((ShapeDrawable) getBackground()).getPaint().setColor(res.getColor(colorRes));
+    }
+  }
+
+  public void setBackgroundColor(int color) {
+    if (getBackground() instanceof ShapeDrawable) {
+      ((ShapeDrawable) getBackground()).getPaint().setColor(color);
+    }
+  }
+
+  public int getMax() {
+    return mMax;
+  }
+
+  public void setMax(int max) {
+    mMax = max;
+  }
+
+  public int getProgress() {
+    return mProgress;
+  }
+
+  public void setProgress(int progress) {
+    if (getMax() > 0) {
+      mProgress = progress;
+    }
+    invalidate();
+  }
+
+  public boolean circleBackgroundEnabled() {
+    return mCircleBackgroundEnabled;
+  }
+
+  public void setCircleBackgroundEnabled(boolean enableCircleBackground) {
+    this.mCircleBackgroundEnabled = enableCircleBackground;
+  }
+
+  @Override
+  protected void onAttachedToWindow() {
+    super.onAttachedToWindow();
+    if (mProgressDrawable != null) {
+      mProgressDrawable.stop();
+      mProgressDrawable.setVisible(getVisibility() == VISIBLE, false);
+    }
+  }
+
+  @Override
+  protected void onDetachedFromWindow() {
+    super.onDetachedFromWindow();
+    if (mProgressDrawable != null) {
+      mProgressDrawable.stop();
+      mProgressDrawable.setVisible(false, false);
+    }
+  }
+
+  private class OvalShadow extends OvalShape {
+
+    private RadialGradient mRadialGradient;
+    private int mShadowRadius;
+    private Paint mShadowPaint;
+    private int mCircleDiameter;
+
+    public OvalShadow(int shadowRadius, int circleDiameter) {
+      super();
+      mShadowPaint = new Paint();
+      mShadowRadius = shadowRadius;
+      mCircleDiameter = circleDiameter;
+      mRadialGradient = new RadialGradient(mCircleDiameter / 2, mCircleDiameter / 2,
+                                           mShadowRadius, new int[]{
+          FILL_SHADOW_COLOR, Color.TRANSPARENT
+      }, null, Shader.TileMode.CLAMP);
+      mShadowPaint.setShader(mRadialGradient);
+    }
+
+    @Override
+    public void draw(Canvas canvas, Paint paint) {
+      final int viewWidth = CircleProgressBar.this.getWidth();
+      final int viewHeight = CircleProgressBar.this.getHeight();
+      canvas.drawCircle(viewWidth / 2, viewHeight / 2, (mCircleDiameter / 2 + mShadowRadius),
+                        mShadowPaint);
+      canvas.drawCircle(viewWidth / 2, viewHeight / 2, (mCircleDiameter / 2), paint);
+    }
+  }
+
+  public void start() {
+    mProgressDrawable.start();
+  }
+
+  public void setStartEndTrim(float startAngle, float endAngle) {
+    mProgressDrawable.setStartEndTrim(startAngle, endAngle);
+  }
+
+  public void stop() {
+    mProgressDrawable.stop();
+  }
+
+  public void setProgressRotation(float rotation) {
+    mProgressDrawable.setProgressRotation(rotation);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/circlebar/MaterialProgressDrawable.java b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/circlebar/MaterialProgressDrawable.java
new file mode 100644
index 0000000..86716ba
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/circlebar/MaterialProgressDrawable.java
@@ -0,0 +1,797 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.refresh.circlebar;
+
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.ColorFilter;
+import android.graphics.Paint;
+import android.graphics.Paint.Style;
+import android.graphics.Path;
+import android.graphics.PixelFormat;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.graphics.drawable.Animatable;
+import android.graphics.drawable.Drawable;
+import android.support.annotation.IntDef;
+import android.support.annotation.NonNull;
+import android.support.v4.view.animation.FastOutSlowInInterpolator;
+import android.util.DisplayMetrics;
+import android.view.View;
+import android.view.animation.Animation;
+import android.view.animation.Interpolator;
+import android.view.animation.LinearInterpolator;
+import android.view.animation.Transformation;
+
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.util.ArrayList;
+
+/**
+ * Copy of android.support.v4
+ */
+class MaterialProgressDrawable extends Drawable implements Animatable {
+
+  private static final Interpolator LINEAR_INTERPOLATOR = new LinearInterpolator();
+  private static final Interpolator MATERIAL_INTERPOLATOR = new FastOutSlowInInterpolator();
+
+  private static final float FULL_ROTATION = 1080.0f;
+
+  @Retention(RetentionPolicy.CLASS)
+  @IntDef({LARGE, DEFAULT})
+  public @interface ProgressDrawableSize {
+
+  }
+
+  // Maps to ProgressBar.Large style
+  static final int LARGE = 0;
+  // Maps to ProgressBar default style
+  static final int DEFAULT = 1;
+
+  // Maps to ProgressBar default style
+  private static final int CIRCLE_DIAMETER = 40;
+  private static final float CENTER_RADIUS = 8.75f; //should add up to 10 when + stroke_width
+  private static final float STROKE_WIDTH = 2.5f;
+
+  // Maps to ProgressBar.Large style
+  private static final int CIRCLE_DIAMETER_LARGE = 56;
+  private static final float CENTER_RADIUS_LARGE = 12.5f;
+  private static final float STROKE_WIDTH_LARGE = 3f;
+
+  private final int[] COLORS = new int[]{
+      Color.BLACK
+  };
+
+  /**
+   * The value in the linear interpolator for animating the drawable at which
+   * the color transition should start
+   */
+  private static final float COLOR_START_DELAY_OFFSET = 0.75f;
+  private static final float END_TRIM_START_DELAY_OFFSET = 0.5f;
+  private static final float START_TRIM_DURATION_OFFSET = 0.5f;
+
+  /** The duration of a single progress spin in milliseconds. */
+  private static final int ANIMATION_DURATION = 1332;
+
+  /** The number of points in the progress "star". */
+  private static final float NUM_POINTS = 5f;
+  /** The list of animators operating on this drawable. */
+  private final ArrayList<Animation> mAnimators = new ArrayList<Animation>();
+
+  /** The indicator ring, used to manage animation state. */
+  private final Ring mRing;
+
+  /** Canvas rotation in degrees. */
+  private float mRotation;
+
+  /** Layout info for the arrowhead in dp */
+  private static final int ARROW_WIDTH = 10;
+  private static final int ARROW_HEIGHT = 5;
+  private static final float ARROW_OFFSET_ANGLE = 5;
+
+  /** Layout info for the arrowhead for the large spinner in dp */
+  private static final int ARROW_WIDTH_LARGE = 12;
+  private static final int ARROW_HEIGHT_LARGE = 6;
+  private static final float MAX_PROGRESS_ARC = .8f;
+
+  private Resources mResources;
+  private View mParent;
+  private Animation mAnimation;
+  private float mRotationCount;
+  private double mWidth;
+  private double mHeight;
+  boolean mFinishing;
+
+  public MaterialProgressDrawable(Context context, View parent) {
+    mParent = parent;
+    mResources = context.getResources();
+
+    mRing = new Ring(mCallback);
+    mRing.setColors(COLORS);
+
+    updateSizes(DEFAULT);
+    setupAnimators();
+  }
+
+  private void setSizeParameters(double progressCircleWidth, double progressCircleHeight,
+                                 double centerRadius, double strokeWidth, float arrowWidth, float arrowHeight) {
+    final Ring ring = mRing;
+    final DisplayMetrics metrics = mResources.getDisplayMetrics();
+    final float screenDensity = metrics.density;
+
+    mWidth = progressCircleWidth * screenDensity;
+    mHeight = progressCircleHeight * screenDensity;
+    ring.setStrokeWidth((float) strokeWidth * screenDensity);
+    ring.setCenterRadius(centerRadius * screenDensity);
+    ring.setColorIndex(0);
+    ring.setArrowDimensions(arrowWidth * screenDensity, arrowHeight * screenDensity);
+    ring.setInsets((int) mWidth, (int) mHeight);
+  }
+
+  /**
+   * Set the overall size for the progress spinner. This updates the radius
+   * and stroke width of the ring.
+   *
+   * @param size One of {@link MaterialProgressDrawable.LARGE} or
+   *            {@link MaterialProgressDrawable.DEFAULT}
+   */
+  public void updateSizes(@ProgressDrawableSize int size) {
+    if (size == LARGE) {
+      setSizeParameters(CIRCLE_DIAMETER_LARGE, CIRCLE_DIAMETER_LARGE, CENTER_RADIUS_LARGE,
+                        STROKE_WIDTH_LARGE, ARROW_WIDTH_LARGE, ARROW_HEIGHT_LARGE);
+    } else {
+      setSizeParameters(CIRCLE_DIAMETER, CIRCLE_DIAMETER, CENTER_RADIUS, STROKE_WIDTH,
+                        ARROW_WIDTH, ARROW_HEIGHT);
+    }
+  }
+
+  /**
+   * @param show Set to true to display the arrowhead on the progress spinner.
+   */
+  public void showArrow(boolean show) {
+    mRing.setShowArrow(show);
+  }
+
+  /**
+   * @param scale Set the scale of the arrowhead for the spinner.
+   */
+  public void setArrowScale(float scale) {
+    mRing.setArrowScale(scale);
+  }
+
+  /**
+   * Set the start and end trim for the progress spinner arc.
+   *
+   * @param startAngle start angle
+   * @param endAngle end angle
+   */
+  public void setStartEndTrim(float startAngle, float endAngle) {
+    mRing.setStartTrim(startAngle);
+    mRing.setEndTrim(endAngle);
+  }
+
+  /**
+   * Set the amount of rotation to apply to the progress spinner.
+   *
+   * @param rotation Rotation is from [0..1]
+   */
+  public void setProgressRotation(float rotation) {
+    mRing.setRotation(rotation);
+  }
+
+  /**
+   * Update the background color of the circle image view.
+   */
+  public void setBackgroundColor(int color) {
+    mRing.setBackgroundColor(color);
+  }
+
+  /**
+   * Set the colors used in the progress animation from color resources.
+   * The first color will also be the color of the bar that grows in response
+   * to a user swipe gesture.
+   *
+   * @param colors
+   */
+  public void setColorSchemeColors(int... colors) {
+    mRing.setColors(colors);
+    mRing.setColorIndex(0);
+  }
+
+  @Override
+  public int getIntrinsicHeight() {
+    return (int) mHeight;
+  }
+
+  @Override
+  public int getIntrinsicWidth() {
+    return (int) mWidth;
+  }
+
+  @Override
+  public void draw(Canvas c) {
+    final Rect bounds = getBounds();
+    final int saveCount = c.save();
+    c.rotate(mRotation, bounds.exactCenterX(), bounds.exactCenterY());
+    mRing.draw(c, bounds);
+    c.restoreToCount(saveCount);
+  }
+
+  @Override
+  public void setAlpha(int alpha) {
+    mRing.setAlpha(alpha);
+  }
+
+  public int getAlpha() {
+    return mRing.getAlpha();
+  }
+
+  @Override
+  public void setColorFilter(ColorFilter colorFilter) {
+    mRing.setColorFilter(colorFilter);
+  }
+
+  @SuppressWarnings("unused")
+  void setRotation(float rotation) {
+    mRotation = rotation;
+    invalidateSelf();
+  }
+
+  @SuppressWarnings("unused")
+  private float getRotation() {
+    return mRotation;
+  }
+
+  @Override
+  public int getOpacity() {
+    return PixelFormat.TRANSLUCENT;
+  }
+
+  @Override
+  public boolean isRunning() {
+    final ArrayList<Animation> animators = mAnimators;
+    final int N = animators.size();
+    for (int i = 0; i < N; i++) {
+      final Animation animator = animators.get(i);
+      if (animator.hasStarted() && !animator.hasEnded()) {
+        return true;
+      }
+    }
+    return false;
+  }
+
+  @Override
+  public void start() {
+    mAnimation.reset();
+    mRing.storeOriginals();
+    // Already showing some part of the ring
+    if (mRing.getEndTrim() != mRing.getStartTrim()) {
+      mFinishing = true;
+      mAnimation.setDuration(ANIMATION_DURATION / 2);
+      mParent.startAnimation(mAnimation);
+    } else {
+      mRing.setColorIndex(0);
+      mRing.resetOriginals();
+      mAnimation.setDuration(ANIMATION_DURATION);
+      mParent.startAnimation(mAnimation);
+    }
+  }
+
+  @Override
+  public void stop() {
+    mParent.clearAnimation();
+    setRotation(0);
+    mRing.setShowArrow(false);
+    mRing.setColorIndex(0);
+    mRing.resetOriginals();
+  }
+
+  private float getMinProgressArc(Ring ring) {
+    return (float) Math.toRadians(
+        ring.getStrokeWidth() / (2 * Math.PI * ring.getCenterRadius()));
+  }
+
+  // Adapted from ArgbEvaluator.java
+  private int evaluateColorChange(float fraction, int startValue, int endValue) {
+    int startInt = (Integer) startValue;
+    int startA = (startInt >> 24) & 0xff;
+    int startR = (startInt >> 16) & 0xff;
+    int startG = (startInt >> 8) & 0xff;
+    int startB = startInt & 0xff;
+
+    int endInt = (Integer) endValue;
+    int endA = (endInt >> 24) & 0xff;
+    int endR = (endInt >> 16) & 0xff;
+    int endG = (endInt >> 8) & 0xff;
+    int endB = endInt & 0xff;
+
+    return (int) ((startA + (int) (fraction * (endA - startA))) << 24) |
+           (int) ((startR + (int) (fraction * (endR - startR))) << 16) |
+           (int) ((startG + (int) (fraction * (endG - startG))) << 8) |
+           (int) ((startB + (int) (fraction * (endB - startB))));
+  }
+
+  /**
+   * Update the ring color if this is within the last 25% of the animation.
+   * The new ring color will be a translation from the starting ring color to
+   * the next color.
+   */
+  private void updateRingColor(float interpolatedTime, Ring ring) {
+    if (interpolatedTime > COLOR_START_DELAY_OFFSET) {
+      // scale the interpolatedTime so that the full
+      // transformation from 0 - 1 takes place in the
+      // remaining time
+      ring.setColor(evaluateColorChange((interpolatedTime - COLOR_START_DELAY_OFFSET)
+                                        / (1.0f - COLOR_START_DELAY_OFFSET), ring.getStartingColor(),
+                                        ring.getNextColor()));
+    }
+  }
+
+  private void applyFinishTranslation(float interpolatedTime, Ring ring) {
+    // shrink back down and complete a full rotation before
+    // starting other circles
+    // Rotation goes between [0..1].
+    updateRingColor(interpolatedTime, ring);
+    float targetRotation = (float) (Math.floor(ring.getStartingRotation() / MAX_PROGRESS_ARC)
+                                    + 1f);
+    final float minProgressArc = getMinProgressArc(ring);
+    final float startTrim = ring.getStartingStartTrim()
+                            + (ring.getStartingEndTrim() - minProgressArc - ring.getStartingStartTrim())
+                              * interpolatedTime;
+    ring.setStartTrim(startTrim);
+    ring.setEndTrim(ring.getStartingEndTrim());
+    final float rotation = ring.getStartingRotation()
+                           + ((targetRotation - ring.getStartingRotation()) * interpolatedTime);
+    ring.setRotation(rotation);
+  }
+
+  private void setupAnimators() {
+    final Ring ring = mRing;
+    final Animation animation = new Animation() {
+      @Override
+      public void applyTransformation(float interpolatedTime, Transformation t) {
+        if (mFinishing) {
+          applyFinishTranslation(interpolatedTime, ring);
+        } else {
+          // The minProgressArc is calculated from 0 to create an
+          // angle that matches the stroke width.
+          final float minProgressArc = getMinProgressArc(ring);
+          final float startingEndTrim = ring.getStartingEndTrim();
+          final float startingTrim = ring.getStartingStartTrim();
+          final float startingRotation = ring.getStartingRotation();
+
+          updateRingColor(interpolatedTime, ring);
+
+          // Moving the start trim only occurs in the first 50% of a
+          // single ring animation
+          if (interpolatedTime <= START_TRIM_DURATION_OFFSET) {
+            // scale the interpolatedTime so that the full
+            // transformation from 0 - 1 takes place in the
+            // remaining time
+            final float scaledTime = (interpolatedTime)
+                                     / (1.0f - START_TRIM_DURATION_OFFSET);
+            final float startTrim = startingTrim
+                                    + ((MAX_PROGRESS_ARC - minProgressArc) * MATERIAL_INTERPOLATOR
+                .getInterpolation(scaledTime));
+            ring.setStartTrim(startTrim);
+          }
+
+          // Moving the end trim starts after 50% of a single ring
+          // animation completes
+          if (interpolatedTime > END_TRIM_START_DELAY_OFFSET) {
+            // scale the interpolatedTime so that the full
+            // transformation from 0 - 1 takes place in the
+            // remaining time
+            final float minArc = MAX_PROGRESS_ARC - minProgressArc;
+            float scaledTime = (interpolatedTime - START_TRIM_DURATION_OFFSET)
+                               / (1.0f - START_TRIM_DURATION_OFFSET);
+            final float endTrim = startingEndTrim
+                                  + (minArc * MATERIAL_INTERPOLATOR.getInterpolation(scaledTime));
+            ring.setEndTrim(endTrim);
+          }
+
+          final float rotation = startingRotation + (0.25f * interpolatedTime);
+          ring.setRotation(rotation);
+
+          float groupRotation = ((FULL_ROTATION / NUM_POINTS) * interpolatedTime)
+                                + (FULL_ROTATION * (mRotationCount / NUM_POINTS));
+          setRotation(groupRotation);
+        }
+      }
+    };
+    animation.setRepeatCount(Animation.INFINITE);
+    animation.setRepeatMode(Animation.RESTART);
+    animation.setInterpolator(LINEAR_INTERPOLATOR);
+    animation.setAnimationListener(new Animation.AnimationListener() {
+
+      @Override
+      public void onAnimationStart(Animation animation) {
+        mRotationCount = 0;
+      }
+
+      @Override
+      public void onAnimationEnd(Animation animation) {
+        // do nothing
+      }
+
+      @Override
+      public void onAnimationRepeat(Animation animation) {
+        ring.storeOriginals();
+        ring.goToNextColor();
+        ring.setStartTrim(ring.getEndTrim());
+        if (mFinishing) {
+          // finished closing the last ring from the swipe gesture; go
+          // into progress mode
+          mFinishing = false;
+          animation.setDuration(ANIMATION_DURATION);
+          ring.setShowArrow(false);
+        } else {
+          mRotationCount = (mRotationCount + 1) % (NUM_POINTS);
+        }
+      }
+    });
+    mAnimation = animation;
+  }
+
+  private final Callback mCallback = new Callback() {
+    @Override
+    public void invalidateDrawable(Drawable d) {
+      invalidateSelf();
+    }
+
+    @Override
+    public void scheduleDrawable(Drawable d, Runnable what, long when) {
+      scheduleSelf(what, when);
+    }
+
+    @Override
+    public void unscheduleDrawable(Drawable d, Runnable what) {
+      unscheduleSelf(what);
+    }
+  };
+
+  private static class Ring {
+
+    private final RectF mTempBounds = new RectF();
+    private final Paint mPaint = new Paint();
+    private final Paint mArrowPaint = new Paint();
+
+    private final Callback mCallback;
+
+    private float mStartTrim = 0.0f;
+    private float mEndTrim = 0.0f;
+    private float mRotation = 0.0f;
+    private float mStrokeWidth = 5.0f;
+    private float mStrokeInset = 2.5f;
+
+    private int[] mColors;
+    // mColorIndex represents the offset into the available mColors that the
+    // progress circle should currently display. As the progress circle is
+    // animating, the mColorIndex moves by one to the next available color.
+    private int mColorIndex;
+    private float mStartingStartTrim;
+    private float mStartingEndTrim;
+    private float mStartingRotation;
+    private boolean mShowArrow;
+    private Path mArrow;
+    private float mArrowScale;
+    private double mRingCenterRadius;
+    private int mArrowWidth;
+    private int mArrowHeight;
+    private int mAlpha;
+    private final Paint mCirclePaint = new Paint(Paint.ANTI_ALIAS_FLAG);
+    private int mBackgroundColor;
+    private int mCurrentColor;
+
+    public Ring(Callback callback) {
+      mCallback = callback;
+
+      mPaint.setStrokeCap(Paint.Cap.SQUARE);
+      mPaint.setAntiAlias(true);
+      mPaint.setStyle(Style.STROKE);
+
+      mArrowPaint.setStyle(Style.FILL);
+      mArrowPaint.setAntiAlias(true);
+    }
+
+    public void setBackgroundColor(int color) {
+      mBackgroundColor = color;
+    }
+
+    /**
+     * Set the dimensions of the arrowhead.
+     *
+     * @param width Width of the hypotenuse of the arrow head
+     * @param height Height of the arrow point
+     */
+    public void setArrowDimensions(float width, float height) {
+      mArrowWidth = (int) width;
+      mArrowHeight = (int) height;
+    }
+
+    /**
+     * Draw the progress spinner
+     */
+    public void draw(Canvas c, Rect bounds) {
+      final RectF arcBounds = mTempBounds;
+      arcBounds.set(bounds);
+      arcBounds.inset(mStrokeInset, mStrokeInset);
+
+      final float startAngle = (mStartTrim + mRotation) * 360;
+      final float endAngle = (mEndTrim + mRotation) * 360;
+      float sweepAngle = endAngle - startAngle;
+
+      mPaint.setColor(mCurrentColor);
+      c.drawArc(arcBounds, startAngle, sweepAngle, false, mPaint);
+
+      drawTriangle(c, startAngle, sweepAngle, bounds);
+
+      if (mAlpha < 255) {
+        mCirclePaint.setColor(mBackgroundColor);
+        mCirclePaint.setAlpha(255 - mAlpha);
+        c.drawCircle(bounds.exactCenterX(), bounds.exactCenterY(), bounds.width() / 2,
+                     mCirclePaint);
+      }
+    }
+
+    private void drawTriangle(Canvas c, float startAngle, float sweepAngle, Rect bounds) {
+      if (mShowArrow) {
+        if (mArrow == null) {
+          mArrow = new Path();
+          mArrow.setFillType(Path.FillType.EVEN_ODD);
+        } else {
+          mArrow.reset();
+        }
+
+        // Adjust the position of the triangle so that it is inset as
+        // much as the arc, but also centered on the arc.
+        float inset = (int) mStrokeInset / 2 * mArrowScale;
+        float x = (float) (mRingCenterRadius * Math.cos(0) + bounds.exactCenterX());
+        float y = (float) (mRingCenterRadius * Math.sin(0) + bounds.exactCenterY());
+
+        // Update the path each time. This works around an issue in SKIA
+        // where concatenating a rotation matrix to a scale matrix
+        // ignored a starting negative rotation. This appears to have
+        // been fixed as of API 21.
+        mArrow.moveTo(0, 0);
+        mArrow.lineTo(mArrowWidth * mArrowScale, 0);
+        mArrow.lineTo((mArrowWidth * mArrowScale / 2), (mArrowHeight
+                                                        * mArrowScale));
+        mArrow.offset(x - inset, y);
+        mArrow.close();
+        // draw a triangle
+        mArrowPaint.setColor(mCurrentColor);
+        c.rotate(startAngle + sweepAngle - ARROW_OFFSET_ANGLE, bounds.exactCenterX(),
+                 bounds.exactCenterY());
+        c.drawPath(mArrow, mArrowPaint);
+      }
+    }
+
+    /**
+     * Set the colors the progress spinner alternates between.
+     *
+     * @param colors Array of integers describing the colors. Must be non-<code>null</code>.
+     */
+    public void setColors(@NonNull int[] colors) {
+      mColors = colors;
+      // if colors are reset, make sure to reset the color index as well
+      setColorIndex(0);
+    }
+
+    /**
+     * Set the absolute color of the progress spinner. This is should only
+     * be used when animating between current and next color when the
+     * spinner is rotating.
+     *
+     * @param color int describing the color.
+     */
+    public void setColor(int color) {
+      mCurrentColor = color;
+    }
+
+    /**
+     * @param index Index into the color array of the color to display in
+     *            the progress spinner.
+     */
+    public void setColorIndex(int index) {
+      mColorIndex = index;
+      mCurrentColor = mColors[mColorIndex];
+    }
+
+    /**
+     * @return int describing the next color the progress spinner should use when drawing.
+     */
+    public int getNextColor() {
+      return mColors[getNextColorIndex()];
+    }
+
+    private int getNextColorIndex() {
+      return (mColorIndex + 1) % (mColors.length);
+    }
+
+    /**
+     * Proceed to the next available ring color. This will automatically
+     * wrap back to the beginning of colors.
+     */
+    public void goToNextColor() {
+      setColorIndex(getNextColorIndex());
+    }
+
+    public void setColorFilter(ColorFilter filter) {
+      mPaint.setColorFilter(filter);
+      invalidateSelf();
+    }
+
+    /**
+     * @param alpha Set the alpha of the progress spinner and associated arrowhead.
+     */
+    public void setAlpha(int alpha) {
+      mAlpha = alpha;
+    }
+
+    /**
+     * @return Current alpha of the progress spinner and arrowhead.
+     */
+    public int getAlpha() {
+      return mAlpha;
+    }
+
+    /**
+     * @param strokeWidth Set the stroke width of the progress spinner in pixels.
+     */
+    public void setStrokeWidth(float strokeWidth) {
+      mStrokeWidth = strokeWidth;
+      mPaint.setStrokeWidth(strokeWidth);
+      invalidateSelf();
+    }
+
+    @SuppressWarnings("unused")
+    public float getStrokeWidth() {
+      return mStrokeWidth;
+    }
+
+    @SuppressWarnings("unused")
+    public void setStartTrim(float startTrim) {
+      mStartTrim = startTrim;
+      invalidateSelf();
+    }
+
+    @SuppressWarnings("unused")
+    public float getStartTrim() {
+      return mStartTrim;
+    }
+
+    public float getStartingStartTrim() {
+      return mStartingStartTrim;
+    }
+
+    public float getStartingEndTrim() {
+      return mStartingEndTrim;
+    }
+
+    public int getStartingColor() {
+      return mColors[mColorIndex];
+    }
+
+    @SuppressWarnings("unused")
+    public void setEndTrim(float endTrim) {
+      mEndTrim = endTrim;
+      invalidateSelf();
+    }
+
+    @SuppressWarnings("unused")
+    public float getEndTrim() {
+      return mEndTrim;
+    }
+
+    @SuppressWarnings("unused")
+    public void setRotation(float rotation) {
+      mRotation = rotation;
+      invalidateSelf();
+    }
+
+    @SuppressWarnings("unused")
+    public float getRotation() {
+      return mRotation;
+    }
+
+    public void setInsets(int width, int height) {
+      final float minEdge = (float) Math.min(width, height);
+      float insets;
+      if (mRingCenterRadius <= 0 || minEdge < 0) {
+        insets = (float) Math.ceil(mStrokeWidth / 2.0f);
+      } else {
+        insets = (float) (minEdge / 2.0f - mRingCenterRadius);
+      }
+      mStrokeInset = insets;
+    }
+
+    @SuppressWarnings("unused")
+    public float getInsets() {
+      return mStrokeInset;
+    }
+
+    /**
+     * @param centerRadius Inner radius in px of the circle the progress
+     *            spinner arc traces.
+     */
+    public void setCenterRadius(double centerRadius) {
+      mRingCenterRadius = centerRadius;
+    }
+
+    public double getCenterRadius() {
+      return mRingCenterRadius;
+    }
+
+    /**
+     * @param show Set to true to show the arrow head on the progress spinner.
+     */
+    public void setShowArrow(boolean show) {
+      if (mShowArrow != show) {
+        mShowArrow = show;
+        invalidateSelf();
+      }
+    }
+
+    /**
+     * @param scale Set the scale of the arrowhead for the spinner.
+     */
+    public void setArrowScale(float scale) {
+      if (scale != mArrowScale) {
+        mArrowScale = scale;
+        invalidateSelf();
+      }
+    }
+
+    /**
+     * @return The amount the progress spinner is currently rotated, between [0..1].
+     */
+    public float getStartingRotation() {
+      return mStartingRotation;
+    }
+
+    /**
+     * If the start / end trim are offset to begin with, store them so that
+     * animation starts from that offset.
+     */
+    public void storeOriginals() {
+      mStartingStartTrim = mStartTrim;
+      mStartingEndTrim = mEndTrim;
+      mStartingRotation = mRotation;
+    }
+
+    /**
+     * Reset the progress spinner to default rotation, start and end angles.
+     */
+    public void resetOriginals() {
+      mStartingStartTrim = 0;
+      mStartingEndTrim = 0;
+      mStartingRotation = 0;
+      setStartTrim(0);
+      setEndTrim(0);
+      setRotation(0);
+    }
+
+    private void invalidateSelf() {
+      mCallback.invalidateDrawable(null);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/core/WXRefreshView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/core/WXRefreshView.java
new file mode 100644
index 0000000..1edc5b7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/core/WXRefreshView.java
@@ -0,0 +1,149 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.refresh.core;
+
+import android.content.Context;
+import android.util.AttributeSet;
+import android.view.Gravity;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.FrameLayout;
+import android.widget.LinearLayout;
+
+import org.apache.weex.common.WXThread;
+import org.apache.weex.ui.view.refresh.circlebar.CircleProgressBar;
+
+public class WXRefreshView extends FrameLayout {
+
+  private CircleProgressBar circleProgressBar;
+  private LinearLayout linearLayout;
+
+  public WXRefreshView(Context context) {
+    super(context);
+    setupViews();
+  }
+
+  public WXRefreshView(Context context, AttributeSet attrs) {
+    super(context, attrs);
+    setupViews();
+  }
+
+  public WXRefreshView(Context context, AttributeSet attrs, int defStyleAttr) {
+    super(context, attrs, defStyleAttr);
+    setupViews();
+  }
+
+  private void setupViews() {
+    linearLayout = new LinearLayout(getContext());
+    FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(FrameLayout.LayoutParams
+            .MATCH_PARENT,FrameLayout
+            .LayoutParams.MATCH_PARENT);
+    linearLayout.setOrientation(LinearLayout.VERTICAL);
+    linearLayout.setGravity(Gravity.CENTER);
+    addView(linearLayout,lp);
+  }
+
+  public void setContentGravity(int gravity) {
+    if (linearLayout != null) {
+      linearLayout.setGravity(gravity);
+    }
+  }
+
+  /**
+   * Setting refresh view or loading view
+   *
+   * @param view refresh or loading
+   */
+  public void setRefreshView(final View view) {
+    if (view == null)
+      return;
+    post(WXThread.secure(new Runnable() {
+      @Override
+      public void run() {
+        View child = null;
+        View temp = view;
+        if (view.getParent() != null) {
+          ((ViewGroup) view.getParent()).removeView(view);
+        }
+        for (int i = 0;i<((ViewGroup)temp).getChildCount(); i++) {
+          child = ((ViewGroup) temp).getChildAt(i);
+          if (child instanceof CircleProgressBar)
+            circleProgressBar = (CircleProgressBar) child;
+        }
+        linearLayout.addView(temp);
+      }
+    }));
+  }
+
+  /**
+   * Set loading_indicator bgColor
+   *
+   * @param color
+   */
+  public void setProgressBgColor(int color) {
+    if (circleProgressBar != null) {
+      circleProgressBar.setBackgroundColor(color);
+    }
+  }
+
+  /**
+   * Set loading_indicator color
+   *
+   * @param color
+   */
+  public void setProgressColor(int color) {
+    if (circleProgressBar != null) {
+      circleProgressBar.setColorSchemeColors(color);
+    }
+  }
+
+  protected void startAnimation() {
+    if (circleProgressBar != null) {
+      circleProgressBar.start();
+    }
+  }
+
+  /**
+   * Set the start and end trim for the progress spinner arc.
+   *
+   * @param startAngle start angle
+   * @param endAngle end angle
+   */
+  public void setStartEndTrim(float startAngle, float endAngle) {
+    if (circleProgressBar != null) {
+      circleProgressBar.setStartEndTrim(startAngle, endAngle);
+    }
+  }
+
+  protected void stopAnimation() {
+    if (circleProgressBar != null) {
+      circleProgressBar.stop();
+    }
+  }
+
+  /**
+   * Set the amount of rotation to apply to the progress spinner.
+   *
+   * @param rotation Rotation is from [0..1]
+   */
+  public void setProgressRotation(float rotation) {
+    if (circleProgressBar != null)
+      circleProgressBar.setProgressRotation(rotation);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/core/WXSwipeLayout.java b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/core/WXSwipeLayout.java
new file mode 100644
index 0000000..67f9333
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/core/WXSwipeLayout.java
@@ -0,0 +1,854 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.refresh.core;
+
+import android.animation.Animator;
+import android.animation.ValueAnimator;
+import android.annotation.SuppressLint;
+import android.annotation.TargetApi;
+import android.content.Context;
+import android.graphics.Color;
+import android.os.Build;
+import android.support.annotation.Nullable;
+import android.support.v4.view.NestedScrollingChild;
+import android.support.v4.view.NestedScrollingChildHelper;
+import android.support.v4.view.NestedScrollingParent;
+import android.support.v4.view.NestedScrollingParentHelper;
+import android.support.v4.view.ViewCompat;
+import android.support.v4.view.ViewParentCompat;
+import android.util.AttributeSet;
+import android.util.DisplayMetrics;
+import android.util.TypedValue;
+import android.view.Gravity;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewParent;
+import android.widget.AbsListView;
+import android.widget.FrameLayout;
+
+import java.util.LinkedList;
+import java.util.List;
+
+public class WXSwipeLayout extends FrameLayout implements NestedScrollingParent, NestedScrollingChild {
+
+  private NestedScrollingParentHelper mNestedScrollingParentHelper;
+  private NestedScrollingChildHelper mNestedScrollingChildHelper;
+  private final int[] mParentScrollConsumed = new int[2];
+  private final int[] mParentOffsetInWindow = new int[2];
+  private boolean mNestedScrollInProgress;
+  private WXOnRefreshListener onRefreshListener;
+  private WXOnLoadingListener onLoadingListener;
+
+  private ViewParent mNestedScrollAcceptedParent;
+
+  private final List<OnRefreshOffsetChangedListener> mRefreshOffsetChangedListeners = new LinkedList<>();
+
+  public interface OnRefreshOffsetChangedListener {
+    void onOffsetChanged(int verticalOffset);
+  }
+
+  /**
+   * On refresh Callback, call on start refresh
+   */
+  public interface WXOnRefreshListener {
+
+    void onRefresh();
+
+    void onPullingDown(float dy, int pullOutDistance, float viewHeight);
+  }
+
+  /**
+   * On loadmore Callback, call on start loadmore
+   */
+  public interface WXOnLoadingListener {
+
+    void onLoading();
+    void onPullingUp(float dy, int pullOutDistance, float viewHeight);
+  }
+
+  static class WXRefreshAnimatorListener implements Animator.AnimatorListener {
+
+    @Override
+    public void onAnimationStart(Animator animation) {
+    }
+
+    @Override
+    public void onAnimationEnd(Animator animation) {
+    }
+
+    @Override
+    public void onAnimationCancel(Animator animation) {
+    }
+
+    @Override
+    public void onAnimationRepeat(Animator animation) {
+    }
+  }
+
+  private WXRefreshView headerView;
+  private WXRefreshView footerView;
+  private View mTargetView;
+
+  private static final int INVALID = -1;
+  private static final int PULL_REFRESH = 0;
+  private static final int LOAD_MORE = 1;
+
+  // Enable PullRefresh and Loadmore
+  private boolean mPullRefreshEnable = false;
+  private boolean mPullLoadEnable = false;
+
+  // Is Refreshing
+  volatile private boolean mRefreshing = false;
+
+  // RefreshView Height
+  private volatile float refreshViewHeight = 0;
+  private volatile float loadingViewHeight = 0;
+
+  // RefreshView Over Flow Height
+  private volatile float refreshViewFlowHeight = 0;
+  private volatile float loadingViewFlowHeight = 0;
+
+  private static final float overFlow = 1.0f;
+
+  private static final float DAMPING = 0.4f;
+
+  // Drag Action
+  private int mCurrentAction = -1;
+  private boolean isConfirm = false;
+
+  // RefreshView Attrs
+  private int mRefreshViewBgColor;
+  private int mProgressBgColor;
+  private int mProgressColor;
+
+  public WXSwipeLayout(Context context) {
+    super(context);
+    initAttrs(context, null);
+  }
+
+  public WXSwipeLayout(Context context, AttributeSet attrs) {
+    super(context, attrs);
+    initAttrs(context, attrs);
+  }
+
+  public WXSwipeLayout(Context context, AttributeSet attrs, int defStyleAttr) {
+    super(context, attrs, defStyleAttr);
+    initAttrs(context, attrs);
+  }
+
+  @TargetApi(Build.VERSION_CODES.LOLLIPOP)
+  public WXSwipeLayout(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
+    super(context, attrs, defStyleAttr, defStyleRes);
+    initAttrs(context, attrs);
+  }
+
+  private void initAttrs(Context context, AttributeSet attrs) {
+
+    if (getChildCount() > 1) {
+      throw new RuntimeException("WXSwipeLayout should not have more than one child");
+    }
+
+    mNestedScrollingParentHelper = new NestedScrollingParentHelper(this);
+    mNestedScrollingChildHelper = new NestedScrollingChildHelper(this);
+    setNestedScrollingEnabled(false);
+
+    if (isInEditMode() && attrs == null) {
+      return;
+    }
+
+    mRefreshViewBgColor = Color.TRANSPARENT;
+    mProgressBgColor = Color.TRANSPARENT;
+    mProgressColor = Color.RED;
+  }
+
+  @Override
+  protected void onAttachedToWindow() {
+    super.onAttachedToWindow();
+    if(mTargetView == null && getChildCount() > 0){
+      mTargetView = getChildAt(0);
+    }
+    if(mTargetView != null){
+      if(headerView == null || footerView == null){
+        setRefreshView();
+      }
+    }
+  }
+
+
+  public void addTargetView(View mInnerView){
+    this.addView(mInnerView, new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, FrameLayout.LayoutParams.MATCH_PARENT));
+    setRefreshView();
+  }
+  /**
+   * Init refresh view or loading view
+   */
+  private void setRefreshView() {
+    // SetUp HeaderView
+    FrameLayout.LayoutParams lp = new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, 0);
+    headerView = new WXRefreshView(getContext());
+    headerView.setStartEndTrim(0, 0.75f);
+    headerView.setBackgroundColor(mRefreshViewBgColor);
+    headerView.setProgressBgColor(mProgressBgColor);
+    headerView.setProgressColor(mProgressColor);
+    headerView.setContentGravity(Gravity.BOTTOM);
+    addView(headerView, lp);
+
+    // SetUp FooterView
+    lp = new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, 0);
+    lp.gravity = Gravity.BOTTOM;
+    footerView = new WXRefreshView(getContext());
+    footerView.setStartEndTrim(0.5f, 1.25f);
+    footerView.setBackgroundColor(mRefreshViewBgColor);
+    footerView.setProgressBgColor(mProgressBgColor);
+    footerView.setProgressColor(mProgressColor);
+    footerView.setContentGravity(Gravity.TOP);
+    addView(footerView, lp);
+  }
+
+  @Override
+  public boolean onInterceptTouchEvent(MotionEvent ev) {
+    if ((!mPullRefreshEnable && !mPullLoadEnable)) {
+      return false;
+    }
+    if (!isEnabled() || canChildScrollUp()
+            || mRefreshing || mNestedScrollInProgress) {
+      // Fail fast if we're not in a state where a swipe is possible
+      return false;
+    }
+
+    return super.onInterceptTouchEvent(ev);
+  }
+
+  // NestedScrollingChild
+
+  @Override
+  public void setNestedScrollingEnabled(boolean enabled) {
+    mNestedScrollingChildHelper.setNestedScrollingEnabled(enabled);
+  }
+
+  @Override
+  public boolean isNestedScrollingEnabled() {
+    return mNestedScrollingChildHelper.isNestedScrollingEnabled();
+  }
+
+  @Override
+  public boolean startNestedScroll(int axes) {
+    boolean result = mNestedScrollingChildHelper.startNestedScroll(axes);
+    if(result){
+      if(mNestedScrollAcceptedParent == null){
+        ViewParent parent  = this.getParent();
+        View child = this;
+        while (parent != null) {
+          if (ViewParentCompat.onStartNestedScroll(parent, child, this, axes)){
+            mNestedScrollAcceptedParent = parent;
+            break;
+          }
+          if(parent instanceof  View){
+            child = (View) parent;
+          }
+          parent = parent.getParent();
+        }
+      }
+    }
+    return result;
+  }
+
+  @Override
+  public void stopNestedScroll() {
+    mNestedScrollingChildHelper.stopNestedScroll();
+    if(mNestedScrollAcceptedParent != null){
+      mNestedScrollAcceptedParent = null;
+    }
+  }
+
+  @Override
+  public boolean hasNestedScrollingParent() {
+    return mNestedScrollingChildHelper.hasNestedScrollingParent();
+  }
+
+  @Override
+  public boolean dispatchNestedScroll(int dxConsumed, int dyConsumed, int dxUnconsumed,
+                                      int dyUnconsumed, int[] offsetInWindow) {
+    return mNestedScrollingChildHelper.dispatchNestedScroll(dxConsumed, dyConsumed,
+            dxUnconsumed, dyUnconsumed, offsetInWindow);
+  }
+
+  @Override
+  public boolean dispatchNestedPreScroll(int dx, int dy, int[] consumed, int[] offsetInWindow) {
+    return mNestedScrollingChildHelper.dispatchNestedPreScroll(
+            dx, dy, consumed, offsetInWindow);
+  }
+
+
+
+  @Override
+  public boolean dispatchNestedFling(float velocityX, float velocityY, boolean consumed) {
+    return mNestedScrollingChildHelper.dispatchNestedFling(velocityX, velocityY, consumed);
+  }
+
+  @Override
+  public boolean dispatchNestedPreFling(float velocityX, float velocityY) {
+    return mNestedScrollingChildHelper.dispatchNestedPreFling(velocityX, velocityY);
+  }
+
+  /*********************************** NestedScrollParent *************************************/
+
+
+  @Override
+  public boolean onNestedPreFling(View target, float velocityX,
+                                  float velocityY) {
+    if(isNestedScrollingEnabled()) {
+      return dispatchNestedPreFling(velocityX, velocityY);
+    }
+    return  false;
+  }
+
+  @Override
+  public boolean onNestedFling(View target, float velocityX, float velocityY,
+                               boolean consumed) {
+    if(isNestedScrollingEnabled()) {
+      return dispatchNestedFling(velocityX, velocityY, consumed);
+    }
+    return  false;
+  }
+
+  @Override
+  public boolean onStartNestedScroll(View child, View target, int nestedScrollAxes) {
+    boolean result =  isEnabled()  && !mRefreshing
+            && (nestedScrollAxes & ViewCompat.SCROLL_AXIS_VERTICAL) != 0;
+
+    return  result;
+  }
+
+  @Override
+  public void onNestedScrollAccepted(View child, View target, int axes) {
+    mNestedScrollingParentHelper.onNestedScrollAccepted(child, target, axes);
+    if(isNestedScrollingEnabled()){
+      startNestedScroll(axes & ViewCompat.SCROLL_AXIS_VERTICAL);
+      mNestedScrollInProgress = true;
+    }
+  }
+
+
+  /**
+   * With child view to processing move events
+   * @param target the child view
+   * @param dx move x
+   * @param dy move y
+   * @param consumed parent consumed move distance
+   */
+  @Override
+  public void onNestedPreScroll(View target, int dx, int dy, int[] consumed) {
+    // Now let our nested parent consume the leftovers
+    final int[] parentConsumed = mParentScrollConsumed;
+    if(isNestedScrollingEnabled()){
+      if (dispatchNestedPreScroll(dx - consumed[0], dy - consumed[1], parentConsumed, null)) {
+        consumed[0] += parentConsumed[0];
+        consumed[1] += parentConsumed[1];
+        return;
+      }
+    }
+    if ((!mPullRefreshEnable && !mPullLoadEnable)) {
+      return;
+    }
+
+    /**
+     * when in nest-scroll, list canChildScrollUp() false,
+     * maybe parent scroll can scroll up
+     * */
+    if(!canChildScrollUp() && isNestedScrollingEnabled()){
+      if(mNestedScrollAcceptedParent != null && mNestedScrollAcceptedParent != mTargetView){
+        ViewGroup group = (ViewGroup) mNestedScrollAcceptedParent;
+        if(group.getChildCount() > 0){
+          int count = group.getChildCount();
+          for(int i=0; i<count; i++){
+            View view  = group.getChildAt(i);
+            if(view.getVisibility() != View.GONE && view.getMeasuredHeight() > 0){
+              if(view.getTop() < 0){
+                return;
+              }else{
+                break;
+              }
+            }
+          }
+        }
+      }
+    }
+
+
+
+    int spinnerDy = (int) calculateDistanceY(target, dy);
+
+    mRefreshing = false;
+
+    if (!isConfirm) {
+      if (spinnerDy < 0 && !canChildScrollUp()) {
+        mCurrentAction = PULL_REFRESH;
+        isConfirm = true;
+      } else if (spinnerDy > 0 && !canChildScrollDown() && (!mRefreshing)) {
+        mCurrentAction = LOAD_MORE;
+        isConfirm = true;
+      }
+    }
+
+    if (moveSpinner(-spinnerDy)) {
+      if (!canChildScrollUp() && mPullRefreshEnable
+              && mTargetView.getTranslationY() > 0
+              && dy > 0) {
+        consumed[1] += dy;
+      }else if (!canChildScrollDown() && mPullLoadEnable
+              && mTargetView.getTranslationY() < 0
+              && dy < 0){
+        consumed[1] += dy;
+      }else{
+        consumed[1] += spinnerDy;
+      }
+    }
+  }
+
+  @Override
+  public int getNestedScrollAxes() {
+    return mNestedScrollingParentHelper.getNestedScrollAxes();
+  }
+
+
+  /**
+   * Callback on TouchEvent.ACTION_CANCLE or TouchEvent.ACTION_UP
+   * handler : refresh or loading
+   * @param child : child view of SwipeLayout,RecyclerView or Scroller
+   */
+  @Override
+  public void onStopNestedScroll(View child) {
+    mNestedScrollingParentHelper.onStopNestedScroll(child);
+    handlerAction();
+    if(isNestedScrollingEnabled()) {
+      mNestedScrollInProgress = true;
+      stopNestedScroll();
+    }
+  }
+
+
+  @Override
+  public void onNestedScroll(View target, int dxConsumed, int dyConsumed, int dxUnconsumed, int dyUnconsumed) {
+    if(isNestedScrollingEnabled()) {
+      dispatchNestedScroll(dxConsumed, dyConsumed, dxUnconsumed, dyUnconsumed, mParentOffsetInWindow);
+    }
+  }
+
+
+
+
+
+  private double calculateDistanceY(View target, int dy) {
+    int viewHeight = target.getMeasuredHeight();
+    double ratio = (viewHeight - Math.abs(target.getY())) / 1.0d / viewHeight * DAMPING;
+    if (ratio <= 0.01d) {
+      //Filter tiny scrolling action
+      ratio = 0.01d;
+    }
+    return ratio * dy;
+  }
+
+  /**
+   * Adjust the refresh or loading view according to the size of the gesture
+   *
+   * @param distanceY move distance of Y
+   */
+  private boolean moveSpinner(float distanceY) {
+    if (mRefreshing) {
+      return false;
+    }
+
+    if (!canChildScrollUp() && mPullRefreshEnable && mCurrentAction == PULL_REFRESH) {
+      // Pull Refresh
+      LayoutParams lp = (LayoutParams) headerView.getLayoutParams();
+      lp.height += distanceY;
+      if (lp.height < 0) {
+        lp.height = 0;
+      }
+
+      if (lp.height == 0) {
+        isConfirm = false;
+        mCurrentAction = INVALID;
+      }
+      headerView.setLayoutParams(lp);
+      onRefreshListener.onPullingDown(distanceY, lp.height, refreshViewFlowHeight);
+      notifyOnRefreshOffsetChangedListener(lp.height);
+      headerView.setProgressRotation(lp.height / refreshViewFlowHeight);
+      moveTargetView(lp.height);
+      return true;
+    } else if (!canChildScrollDown() && mPullLoadEnable && mCurrentAction == LOAD_MORE) {
+      // Load more
+      LayoutParams lp = (LayoutParams) footerView.getLayoutParams();
+      lp.height -= distanceY;
+      if (lp.height < 0) {
+        lp.height = 0;
+      }
+
+      if (lp.height == 0) {
+        isConfirm = false;
+        mCurrentAction = INVALID;
+      }
+      footerView.setLayoutParams(lp);
+      onLoadingListener.onPullingUp(distanceY, lp.height, loadingViewFlowHeight);
+      footerView.setProgressRotation(lp.height / loadingViewFlowHeight);
+      moveTargetView(-lp.height);
+      return true;
+    }
+    return false;
+  }
+
+  /**
+   * Adjust contentView(Scroller or List) at refresh or loading time
+   * @param h Height of refresh view or loading view
+   */
+  private void moveTargetView(float h) {
+    mTargetView.setTranslationY(h);
+  }
+
+  /**
+   * Decide on the action refresh or loadmore
+   */
+  private void handlerAction() {
+
+    if (isRefreshing()) {
+      return;
+    }
+    isConfirm = false;
+
+    LayoutParams lp;
+    if (mPullRefreshEnable && mCurrentAction == PULL_REFRESH) {
+      lp = (LayoutParams) headerView.getLayoutParams();
+      if (lp.height >= refreshViewHeight) {
+        startRefresh(lp.height);
+      } else if (lp.height > 0) {
+        resetHeaderView(lp.height);
+      } else {
+        resetRefreshState();
+      }
+    }
+
+    if (mPullLoadEnable && mCurrentAction == LOAD_MORE) {
+      lp = (LayoutParams) footerView.getLayoutParams();
+      if (lp.height >= loadingViewHeight) {
+        startLoadmore(lp.height);
+      } else if (lp.height > 0) {
+        resetFootView(lp.height);
+      } else {
+        resetLoadmoreState();
+      }
+    }
+  }
+
+  /**
+   * Start Refresh
+   * @param headerViewHeight
+   */
+  private void startRefresh(int headerViewHeight) {
+    mRefreshing = true;
+    ValueAnimator animator = ValueAnimator.ofFloat(headerViewHeight, refreshViewHeight);
+    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
+      @Override
+      public void onAnimationUpdate(ValueAnimator animation) {
+        LayoutParams lp = (LayoutParams) headerView.getLayoutParams();
+        lp.height = (int) ((Float) animation.getAnimatedValue()).floatValue();
+        notifyOnRefreshOffsetChangedListener(lp.height);
+        headerView.setLayoutParams(lp);
+        moveTargetView(lp.height);
+      }
+    });
+    animator.addListener(new WXRefreshAnimatorListener() {
+      @Override
+      public void onAnimationEnd(Animator animation) {
+        headerView.startAnimation();
+        //TODO updateLoadText
+        if (onRefreshListener != null) {
+          onRefreshListener.onRefresh();
+        }
+      }
+    });
+    animator.setDuration(300);
+    animator.start();
+  }
+
+  /**
+   * Reset refresh state
+   * @param headerViewHeight
+   */
+  private void resetHeaderView(int headerViewHeight) {
+    headerView.stopAnimation();
+    headerView.setStartEndTrim(0, 0.75f);
+    ValueAnimator animator = ValueAnimator.ofFloat(headerViewHeight, 0);
+    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
+      @Override
+      public void onAnimationUpdate(ValueAnimator animation) {
+        LayoutParams lp = (LayoutParams) headerView.getLayoutParams();
+        lp.height = (int) ((Float) animation.getAnimatedValue()).floatValue();
+        notifyOnRefreshOffsetChangedListener(lp.height);
+        headerView.setLayoutParams(lp);
+        moveTargetView(lp.height);
+      }
+    });
+    animator.addListener(new WXRefreshAnimatorListener() {
+      @Override
+      public void onAnimationEnd(Animator animation) {
+        resetRefreshState();
+
+      }
+    });
+    animator.setDuration(300);
+    animator.start();
+  }
+
+  private void resetRefreshState() {
+    mRefreshing = false;
+    isConfirm = false;
+    mCurrentAction = -1;
+    //TODO updateLoadText
+  }
+
+  /**
+   * Start loadmore
+   * @param headerViewHeight
+   */
+  private void startLoadmore(int headerViewHeight) {
+    mRefreshing = true;
+    ValueAnimator animator = ValueAnimator.ofFloat(headerViewHeight, loadingViewHeight);
+    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
+      @Override
+      public void onAnimationUpdate(ValueAnimator animation) {
+        LayoutParams lp = (LayoutParams) footerView.getLayoutParams();
+        lp.height = (int) ((Float) animation.getAnimatedValue()).floatValue();
+        footerView.setLayoutParams(lp);
+        moveTargetView(-lp.height);
+      }
+    });
+    animator.addListener(new WXRefreshAnimatorListener() {
+      @Override
+      public void onAnimationEnd(Animator animation) {
+        footerView.startAnimation();
+        //TODO updateLoadText
+        if (onLoadingListener != null) {
+          onLoadingListener.onLoading();
+        }
+      }
+    });
+    animator.setDuration(300);
+    animator.start();
+  }
+
+  /**
+   * Reset loadmore state
+   * @param headerViewHeight
+   */
+  private void resetFootView(int headerViewHeight) {
+    footerView.stopAnimation();
+    footerView.setStartEndTrim(0.5f, 1.25f);
+    ValueAnimator animator = ValueAnimator.ofFloat(headerViewHeight, 0);
+    animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
+      @Override
+      public void onAnimationUpdate(ValueAnimator animation) {
+        LayoutParams lp = (LayoutParams) footerView.getLayoutParams();
+        lp.height = (int) ((Float) animation.getAnimatedValue()).floatValue();
+        footerView.setLayoutParams(lp);
+        moveTargetView(-lp.height);
+      }
+    });
+    animator.addListener(new WXRefreshAnimatorListener() {
+      @Override
+      public void onAnimationEnd(Animator animation) {
+        resetLoadmoreState();
+
+      }
+    });
+    animator.setDuration(300);
+    animator.start();
+  }
+
+  private void resetLoadmoreState() {
+    mRefreshing = false;
+    isConfirm = false;
+    mCurrentAction = -1;
+    //TODO updateLoadText
+  }
+
+  /**
+   * Whether child view can scroll up
+   * @return
+   */
+  @SuppressLint("ObsoleteSdkInt")
+  public boolean canChildScrollUp() {
+    if (mTargetView == null) {
+      return false;
+    }
+    if (Build.VERSION.SDK_INT < 14) {
+      //The minimum version of Android platform that Weex supports is API 14,
+      //so this block should never enter.
+      if (mTargetView instanceof AbsListView) {
+        final AbsListView absListView = (AbsListView) mTargetView;
+        return absListView.getChildCount() > 0
+                && (absListView.getFirstVisiblePosition() > 0 || absListView.getChildAt(0)
+                .getTop() < absListView.getPaddingTop());
+      } else {
+        return ViewCompat.canScrollVertically(mTargetView, -1) || mTargetView.getScrollY() > 0;
+      }
+    } else {
+      return ViewCompat.canScrollVertically(mTargetView, -1);
+    }
+  }
+
+  /**
+   * Whether child view can scroll down
+   * @return
+   */
+  @SuppressLint("ObsoleteSdkInt")
+  public boolean canChildScrollDown() {
+    if (mTargetView == null) {
+      return false;
+    }
+    if (Build.VERSION.SDK_INT < 14) {
+      //The minimum version of Android platform that Weex supports is API 14,
+      //so this block should never enter.
+      if (mTargetView instanceof AbsListView) {
+        final AbsListView absListView = (AbsListView) mTargetView;
+        if (absListView.getChildCount() > 0) {
+          int lastChildBottom = absListView.getChildAt(absListView.getChildCount() - 1)
+                  .getBottom();
+          return absListView.getLastVisiblePosition() == absListView.getAdapter().getCount() - 1
+                  && lastChildBottom <= absListView.getMeasuredHeight();
+        } else {
+          return false;
+        }
+
+      } else {
+        return ViewCompat.canScrollVertically(mTargetView, 1) || mTargetView.getScrollY() > 0;
+      }
+    } else {
+      return ViewCompat.canScrollVertically(mTargetView, 1);
+    }
+  }
+
+  public float dipToPx(Context context, float value) {
+    DisplayMetrics metrics = context.getResources().getDisplayMetrics();
+    return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, value, metrics);
+  }
+
+  public void setOnLoadingListener(WXOnLoadingListener onLoadingListener) {
+    this.onLoadingListener = onLoadingListener;
+  }
+
+  public void setOnRefreshListener(WXOnRefreshListener onRefreshListener) {
+    this.onRefreshListener = onRefreshListener;
+  }
+
+  @SuppressWarnings("unused")
+  public void addOnRefreshOffsetChangedListener(@Nullable OnRefreshOffsetChangedListener listener) {
+    if(listener != null && !mRefreshOffsetChangedListeners.contains(listener)) {
+      mRefreshOffsetChangedListeners.add(listener);
+    }
+  }
+
+  @SuppressWarnings("unused")
+  public boolean removeOnRefreshOffsetChangedListener(@Nullable OnRefreshOffsetChangedListener listener) {
+    if(listener != null) {
+      return mRefreshOffsetChangedListeners.remove(listener);
+    }
+    return false;
+  }
+
+  private void notifyOnRefreshOffsetChangedListener(int verticalOffset) {
+    int size = mRefreshOffsetChangedListeners.size();
+    OnRefreshOffsetChangedListener listener;
+    for (int i=0; i<size; i++) {
+      if(i >= mRefreshOffsetChangedListeners.size()){
+        break;
+      }
+      listener = mRefreshOffsetChangedListeners.get(i);
+
+      if (listener != null) {
+        listener.onOffsetChanged(verticalOffset);
+      }
+    }
+  }
+
+  /**
+   * Callback on refresh finish
+   */
+  public void finishPullRefresh() {
+    if (mCurrentAction == PULL_REFRESH) {
+      resetHeaderView(headerView == null ? 0 : headerView.getMeasuredHeight());
+    }
+  }
+
+  /**
+   * Callback on loadmore finish
+   */
+  public void finishPullLoad() {
+    if (mCurrentAction == LOAD_MORE) {
+      resetFootView(footerView == null ? 0 : footerView.getMeasuredHeight());
+    }
+  }
+
+  public WXRefreshView getHeaderView() {
+    return headerView;
+  }
+
+  public WXRefreshView getFooterView() {
+    return footerView;
+  }
+
+  public boolean isPullLoadEnable() {
+    return mPullLoadEnable;
+  }
+
+  public void setPullLoadEnable(boolean mPullLoadEnable) {
+    this.mPullLoadEnable = mPullLoadEnable;
+  }
+
+  public boolean isPullRefreshEnable() {
+    return mPullRefreshEnable;
+  }
+
+  public void setPullRefreshEnable(boolean mPullRefreshEnable) {
+    this.mPullRefreshEnable = mPullRefreshEnable;
+  }
+
+  public boolean isRefreshing() {
+    return mRefreshing;
+  }
+
+  public void setRefreshHeight(int height) {
+    refreshViewHeight = height;
+    refreshViewFlowHeight = refreshViewHeight * overFlow;
+  }
+
+  public void setLoadingHeight(int height) {
+    loadingViewHeight = height;
+    loadingViewFlowHeight = loadingViewHeight * overFlow;
+  }
+
+  public void setRefreshBgColor(int color) {
+    headerView.setBackgroundColor(color);
+  }
+
+  public void setLoadingBgColor(int color) {
+    footerView.setBackgroundColor(color);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BaseBounceView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BaseBounceView.java
new file mode 100644
index 0000000..0e6070a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BaseBounceView.java
@@ -0,0 +1,226 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.refresh.wrapper;
+
+import android.content.Context;
+import android.graphics.Color;
+import android.support.v7.widget.OrientationHelper;
+import android.text.TextUtils;
+import android.util.AttributeSet;
+import android.view.View;
+import android.widget.FrameLayout;
+
+import org.apache.weex.common.Constants;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.view.WXLoadingLayout;
+import org.apache.weex.ui.view.WXRefreshLayout;
+import org.apache.weex.ui.view.refresh.core.WXRefreshView;
+import org.apache.weex.ui.view.refresh.core.WXSwipeLayout;
+import org.apache.weex.utils.WXResourceUtils;
+import org.apache.weex.utils.WXUtils;
+
+/**
+ * BounceView(SwipeLayout) contains Scroller/List and refresh/loading view
+ * @param <T> InnerView
+ */
+public abstract class BaseBounceView<T extends View> extends FrameLayout {
+
+    private int mOrientation = OrientationHelper.VERTICAL;
+    protected WXSwipeLayout swipeLayout;
+    private T mInnerView;
+
+    public BaseBounceView(Context context,int orientation) {
+        this(context, null,orientation);
+    }
+
+    public BaseBounceView(Context context, AttributeSet attrs,int orientation) {
+        super(context, attrs);
+        mOrientation = orientation;
+    }
+
+    public int getOrientation(){
+        return mOrientation;
+    }
+
+    public void init(Context context) {
+        createBounceView(context);
+    }
+
+    boolean isVertical(){
+        return mOrientation==OrientationHelper.VERTICAL;
+    }
+
+    public void setOnRefreshListener(WXSwipeLayout.WXOnRefreshListener onRefreshListener) {
+        if (swipeLayout != null)
+            swipeLayout.setOnRefreshListener(onRefreshListener);
+    }
+
+    public void setOnLoadingListener(WXSwipeLayout.WXOnLoadingListener onLoadingListener) {
+        if (swipeLayout != null)
+            swipeLayout.setOnLoadingListener(onLoadingListener);
+    }
+
+    public void finishPullRefresh() {
+        if (swipeLayout != null)
+            swipeLayout.finishPullRefresh();
+    }
+
+    public void finishPullLoad() {
+        if (swipeLayout != null)
+            swipeLayout.finishPullLoad();
+    }
+
+    /**
+     * Init wipelayout
+     */
+    private WXSwipeLayout createBounceView(Context context) {
+        swipeLayout = new WXSwipeLayout(context);
+        swipeLayout.setLayoutParams(new FrameLayout.LayoutParams(FrameLayout.LayoutParams.MATCH_PARENT, FrameLayout.LayoutParams.MATCH_PARENT));
+        mInnerView = setInnerView(context);
+        if (mInnerView == null)
+            return null;
+        swipeLayout.addTargetView(mInnerView);
+        addView(swipeLayout, LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
+        return swipeLayout;
+    }
+
+    /**
+     * @return the child of swipelayout : recyclerview or scrollview
+     */
+    public T getInnerView() {
+        return mInnerView;
+    }
+
+    public abstract T setInnerView(Context context);
+
+    /**
+     *
+     * @param refresh should be {@link WXRefreshView}
+     */
+    public void setHeaderView(WXComponent refresh) {
+        setRefreshEnable(true);
+        if (swipeLayout != null) {
+            WXRefreshView refreshView = swipeLayout.getHeaderView();
+            if (refreshView != null) {
+                if (refresh != null) {
+                    int refreshHeight = (int) refresh.getLayoutHeight();
+                    swipeLayout.setRefreshHeight(refreshHeight);
+                    String colorStr = (String) refresh.getStyles().get(Constants.Name.BACKGROUND_COLOR);
+                    String bgColor = WXUtils.getString(colorStr, null);
+                    if (bgColor != null) {
+                        if (!TextUtils.isEmpty(bgColor)) {
+                            int colorInt = WXResourceUtils.getColor(bgColor);
+                            if (!(colorInt == Color.TRANSPARENT)) {
+                                swipeLayout.setRefreshBgColor(colorInt);
+                            }
+                        }
+                    }
+                    refreshView.setRefreshView(refresh.getHostView());
+                }
+            }
+        }
+    }
+
+    /**
+     *
+     * @param loading should be {@link WXRefreshView}
+     */
+    public void setFooterView(WXComponent loading) {
+        setLoadmoreEnable(true);
+        if (swipeLayout != null) {
+            WXRefreshView refreshView = swipeLayout.getFooterView();
+            if (refreshView != null) {
+                if (loading != null) {
+                    int loadingHeight = (int) loading.getLayoutHeight();
+                    swipeLayout.setLoadingHeight(loadingHeight);
+                    String colorStr = (String) loading.getStyles().get(Constants.Name.BACKGROUND_COLOR);
+                    String bgColor = WXUtils.getString(colorStr, null);
+                    if (bgColor != null) {
+                        if (!TextUtils.isEmpty(bgColor)) {
+                            int colorInt = WXResourceUtils.getColor(bgColor);
+                            if (!(colorInt == Color.TRANSPARENT)) {
+                                swipeLayout.setLoadingBgColor(colorInt);
+                            }
+                        }
+                    }
+                    refreshView.setRefreshView(loading.getHostView());
+                }
+            }
+        }
+    }
+
+    public void removeFooterView(WXComponent loading){
+        setLoadmoreEnable(false);
+        if(swipeLayout!=null){
+            if(swipeLayout.getFooterView()!=null){
+                swipeLayout.setLoadingHeight(0);
+                swipeLayout.getFooterView().removeView(loading.getHostView());
+                swipeLayout.finishPullLoad();
+            }
+        }
+    }
+    //TODO There are bugs, will be more than a rolling height
+    public void removeHeaderView(WXComponent refresh){
+        setRefreshEnable(false);
+        if(swipeLayout!=null){
+            if(swipeLayout.getHeaderView()!=null){
+                swipeLayout.setRefreshHeight(0);
+                swipeLayout.getHeaderView().removeView(refresh.getHostView());
+                swipeLayout.finishPullRefresh();
+            }
+        }
+    }
+
+    public void setRefreshEnable(boolean enable) {
+        if (swipeLayout != null)
+            swipeLayout.setPullRefreshEnable(enable);
+    }
+
+    public void setLoadmoreEnable(boolean enable) {
+        if (swipeLayout != null)
+            swipeLayout.setPullLoadEnable(enable);
+    }
+
+    @Override
+    public void removeView(View view) {
+        if (view instanceof WXLoadingLayout) {
+            finishPullLoad();
+            setLoadmoreEnable(false);
+            if (swipeLayout != null) {
+                swipeLayout.removeView(swipeLayout.getFooterView());
+            }
+        } else if (view instanceof WXRefreshLayout) {
+            finishPullRefresh();
+            setRefreshEnable(false);
+            if (swipeLayout != null) {
+                swipeLayout.removeView(swipeLayout.getHeaderView());
+            }
+        } else {
+            super.removeView(view);
+        }
+    }
+
+    public WXSwipeLayout getSwipeLayout() {
+        return swipeLayout;
+    }
+
+    public abstract void onRefreshingComplete();
+
+    public abstract void onLoadmoreComplete();
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BounceRecyclerView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BounceRecyclerView.java
new file mode 100644
index 0000000..761cfb8
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BounceRecyclerView.java
@@ -0,0 +1,135 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.refresh.wrapper;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.support.annotation.Nullable;
+import android.view.MotionEvent;
+
+import org.apache.weex.ui.component.list.ListComponentView;
+import org.apache.weex.ui.component.list.StickyHeaderHelper;
+import org.apache.weex.ui.component.list.WXCell;
+import org.apache.weex.ui.view.gesture.WXGesture;
+import org.apache.weex.ui.view.gesture.WXGestureObservable;
+import org.apache.weex.ui.view.listview.WXRecyclerView;
+import org.apache.weex.ui.view.listview.adapter.RecyclerViewBaseAdapter;
+
+@SuppressLint("ViewConstructor")
+public class BounceRecyclerView extends BaseBounceView<WXRecyclerView> implements ListComponentView,WXGestureObservable {
+
+  public static final int DEFAULT_COLUMN_COUNT = 1;
+  public static final int DEFAULT_COLUMN_GAP = 1;
+  private RecyclerViewBaseAdapter adapter = null;
+  private WXGesture mGesture;
+  private int mLayoutType = WXRecyclerView.TYPE_LINEAR_LAYOUT;
+  private int mColumnCount = DEFAULT_COLUMN_COUNT;
+  private float mColumnGap = DEFAULT_COLUMN_GAP;
+  private StickyHeaderHelper mStickyHeaderHelper;
+
+  public BounceRecyclerView(Context context,int type,int columnCount,float columnGap,int orientation) {
+    super(context, orientation);
+    mLayoutType = type;
+    mColumnCount = columnCount;
+    mColumnGap = columnGap;
+    init(context);
+    mStickyHeaderHelper = new StickyHeaderHelper(this);
+  }
+
+  public BounceRecyclerView(Context context,int type,int orientation) {
+    this(context,type, DEFAULT_COLUMN_COUNT, DEFAULT_COLUMN_GAP,orientation);
+  }
+
+  public void setRecyclerViewBaseAdapter(RecyclerViewBaseAdapter adapter) {
+    this.adapter = adapter;
+    if (getInnerView() != null) {
+      getInnerView().setAdapter(adapter);
+    }
+  }
+
+  public RecyclerViewBaseAdapter getRecyclerViewBaseAdapter() {
+    return adapter;
+  }
+
+  @Override
+  public boolean dispatchTouchEvent(MotionEvent event) {
+    boolean result = super.dispatchTouchEvent(event);
+    if (mGesture != null) {
+      result |= mGesture.onTouch(this, event);
+    }
+    return result;
+  }
+
+  @Override
+  public WXRecyclerView setInnerView(Context context) {
+    WXRecyclerView wxRecyclerView = new WXRecyclerView(context);
+    wxRecyclerView.initView(context, mLayoutType,mColumnCount,mColumnGap,getOrientation());
+    return wxRecyclerView;
+  }
+
+  @Override
+  public void onRefreshingComplete() {
+    if (adapter != null) {
+      adapter.notifyDataSetChanged();
+    }
+  }
+
+  @Override
+  public void onLoadmoreComplete() {
+    if (adapter != null) {
+      adapter.notifyDataSetChanged();
+    }
+  }
+
+  /**
+   * @param component
+   */
+  public void notifyStickyShow(WXCell component) {
+    mStickyHeaderHelper.notifyStickyShow(component);
+  }
+
+  @Override
+  public void updateStickyView(int currentStickyPos) {
+    mStickyHeaderHelper.updateStickyView(currentStickyPos);
+  }
+
+  /**
+   *
+   * @param compToRemove
+   */
+  @Override
+  public void notifyStickyRemove(WXCell compToRemove) {
+    mStickyHeaderHelper.notifyStickyRemove(compToRemove);
+  }
+
+  public StickyHeaderHelper getStickyHeaderHelper() {
+    return mStickyHeaderHelper;
+  }
+
+  @Override
+  public void registerGestureListener(@Nullable WXGesture wxGesture) {
+    mGesture = wxGesture;
+    getInnerView().registerGestureListener(wxGesture);
+  }
+
+  @Override
+  public WXGesture getGestureListener() {
+    return mGesture;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BounceScrollerView.java b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BounceScrollerView.java
new file mode 100644
index 0000000..7a4b6f9
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/ui/view/refresh/wrapper/BounceScrollerView.java
@@ -0,0 +1,51 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.ui.view.refresh.wrapper;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+
+import org.apache.weex.ui.component.WXScroller;
+import org.apache.weex.ui.view.WXScrollView;
+
+@SuppressLint("ViewConstructor")
+public class BounceScrollerView extends BaseBounceView<WXScrollView> {
+
+    public BounceScrollerView(Context context, int orientation, WXScroller waScroller) {
+        super(context,orientation);
+        init(context);
+        if (getInnerView() != null)
+            getInnerView().setWAScroller(waScroller);
+    }
+
+    @Override
+    public WXScrollView setInnerView(Context context) {
+        return new WXScrollView(context);
+    }
+
+    @Override
+    public void onRefreshingComplete() {
+        //TODO update scroller dataset
+    }
+
+    @Override
+    public void onLoadmoreComplete() {
+        //TODO update scroller dataset
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/ATagUtil.java b/android/sdk/src/main/java/org/apache/weex/utils/ATagUtil.java
new file mode 100644
index 0000000..c7c133d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/ATagUtil.java
@@ -0,0 +1,42 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.utils;
+
+import android.net.Uri;
+import android.view.View;
+
+import com.alibaba.fastjson.JSONArray;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.URIAdapter;
+
+public class ATagUtil {
+  public static void onClick(View widget, String instanceId, String url) {
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (instance == null) {
+      return;
+    }
+    String href = instance.rewriteUri(Uri.parse(url), URIAdapter.LINK).toString();
+    JSONArray array = new JSONArray();
+    array.add(href);
+    WXSDKManager.getInstance().getWXBridgeManager().
+        callModuleMethod(instanceId, "event", "openURL", array);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/BoxShadowUtil.java b/android/sdk/src/main/java/org/apache/weex/utils/BoxShadowUtil.java
new file mode 100644
index 0000000..96872c6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/BoxShadowUtil.java
@@ -0,0 +1,669 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.graphics.BlurMaskFilter;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.ColorFilter;
+import android.graphics.LinearGradient;
+import android.graphics.Paint;
+import android.graphics.Path;
+import android.graphics.PixelFormat;
+import android.graphics.Point;
+import android.graphics.PointF;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.graphics.Region;
+import android.graphics.Shader;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.LayerDrawable;
+import android.os.Build;
+import android.os.Build.VERSION_CODES;
+import android.support.annotation.IntRange;
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+import android.util.Log;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewParent;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.common.WXThread;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * Created by moxun on 2017/9/4.
+ * Utils for create shadow layer on view
+ * Requires Android 4.3 and higher
+ *
+ * @see <a href="https://www.w3schools.com/cssref/css3_pr_box-shadow.asp">CSS3 box-shadow Property</>
+ */
+
+public class BoxShadowUtil {
+  private static final String TAG = "BoxShadowUtil";
+  private static boolean sBoxShadowEnabled = true /*disable box-shadow temporary*/;
+
+  private static Pattern sColorPattern;
+
+  public static void setBoxShadowEnabled(boolean enabled) {
+    sBoxShadowEnabled = enabled;
+    WXLogUtils.w(TAG, "Switch box-shadow status: " + enabled);
+  }
+
+  public static boolean isBoxShadowEnabled() {
+    return sBoxShadowEnabled;
+  }
+
+  public static void setBoxShadow(final View target, String style, final float[] radii, int viewPort, final float quality) {
+    if (!sBoxShadowEnabled) {
+      WXLogUtils.w(TAG, "box-shadow was disabled by config");
+      return;
+    }
+
+    if (target == null) {
+      WXLogUtils.w(TAG, "Target view is null!");
+      return;
+    }
+
+    if (TextUtils.isEmpty(style) && Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
+      target.getOverlay().clear();
+      WXLogUtils.d(TAG, "Remove all box-shadow");
+      return;
+    }
+
+    final BoxShadowOptions[] shadows = parseBoxShadows(style, viewPort);
+    if (shadows == null || shadows.length == 0) {
+      WXLogUtils.w(TAG, "Failed to parse box-shadow: " + style);
+      return;
+    }
+
+    final List<BoxShadowOptions> normalShadows = new ArrayList<>(), insetShadows = new ArrayList<>();
+    for (BoxShadowOptions shadow : shadows) {
+      if (shadow != null) {
+        if (shadow.isInset) {
+          insetShadows.add(0, shadow);
+        } else {
+          normalShadows.add(0, shadow);
+        }
+      }
+    }
+
+    if (radii != null) {
+      if (radii.length != 8) {
+        WXLogUtils.w(TAG, "Length of radii must be 8");
+      } else {
+        for (int i = 0; i < radii.length; i++) {
+          float realRadius = WXViewUtils.getRealSubPxByWidth(radii[i], viewPort);
+          radii[i] = realRadius;
+        }
+      }
+    }
+
+    target.post(WXThread.secure(new Runnable() {
+      @Override
+      public void run() {
+        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
+          target.getOverlay().clear();
+          if (normalShadows.size() > 0) {
+            setNormalBoxShadow(target, normalShadows, quality, radii);
+          }
+
+          if (insetShadows.size() > 0) {
+            setInsetBoxShadow(target, insetShadows, quality, radii);
+          }
+        }
+      }
+    }));
+  }
+
+  private static void drawShadow(Canvas canvas, BoxShadowOptions options) {
+    RectF shadowRect = new RectF(
+        0f, 0f,
+        options.viewWidth + 2f * options.spread, options.viewHeight + 2f * options.spread
+    );
+
+    if (options.topLeft != null) {
+      shadowRect.offset(options.topLeft.x, options.topLeft.y);
+    }
+
+    float shadowDx = options.blur;
+    float shadowDy = options.blur;
+    if (options.hShadow > 0) {
+      shadowDx = shadowDx + 2f * options.hShadow;
+    }
+    if (options.vShadow > 0) {
+      shadowDy = shadowDy + 2f * options.vShadow;
+    }
+    shadowRect.offset(shadowDx, shadowDy);
+
+    Paint shadowPaint = new Paint();
+    shadowPaint.setAntiAlias(true);
+    shadowPaint.setColor(options.color);
+    shadowPaint.setStyle(Paint.Style.FILL);
+
+    if (options.blur > 0) {
+      shadowPaint.setMaskFilter(new BlurMaskFilter(options.blur, BlurMaskFilter.Blur.NORMAL));
+    }
+
+    Path shadowPath = new Path();
+    float[] shadowRadii = new float[8];
+    for (int i = 0; i < options.radii.length; i++) {
+      float contentRadius = options.radii[i];
+      if (contentRadius == 0f) {
+        shadowRadii[i] = 0f;
+      } else {
+        shadowRadii[i] = options.radii[i] + options.spread;
+      }
+    }
+    shadowPath.addRoundRect(shadowRect, shadowRadii, Path.Direction.CCW);
+    canvas.drawPath(shadowPath, shadowPaint);
+
+    if (false && WXEnvironment.isApkDebugable()) {
+      Paint paint = new Paint();
+      paint.setAntiAlias(true);
+      paint.setColor(Color.BLACK);
+      paint.setStyle(Paint.Style.STROKE);
+      canvas.drawRect(shadowRect, paint);
+    }
+  }
+
+  private static void setNormalBoxShadow(View target, List<BoxShadowOptions> options, float quality, float[] radii) {
+    int h = target.getHeight();
+    int w = target.getWidth();
+
+    ViewGroup.LayoutParams p = target.getLayoutParams();
+
+    if (h == 0 || w == 0) {
+      Log.w(TAG, "Target view is invisible, ignore set shadow.");
+      return;
+    }
+
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
+      int maxWidth = 0, maxHeight = 0;
+      for (BoxShadowOptions option : options) {
+        option.viewWidth = w;
+        option.viewHeight = h;
+        option.radii = radii;
+
+        Rect rect = option.getTargetCanvasRect();
+        if (maxWidth < rect.width()) {
+          maxWidth = rect.width();
+        }
+
+        if (maxHeight < rect.height()) {
+          maxHeight = rect.height();
+        }
+      }
+
+      int canvasWidth = (int) (maxWidth * quality);
+      int canvasHeight = (int) (maxHeight * quality);
+      Bitmap output = Bitmap.createBitmap(canvasWidth, canvasHeight, Bitmap.Config.ARGB_4444);
+      if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
+        WXLogUtils.d(TAG, "Allocation memory for box-shadow: " + (output.getAllocationByteCount() / 1024) + " KB");
+      }
+      Canvas canvas = new Canvas(output);
+
+      if (false && WXEnvironment.isApkDebugable()) {
+        // Using for debug
+        Paint strokePaint = new Paint();
+        strokePaint.setColor(Color.BLACK);
+        strokePaint.setStrokeWidth(2);
+        strokePaint.setStyle(Paint.Style.STROKE);
+        canvas.drawRect(canvas.getClipBounds(), strokePaint);
+      }
+
+      for (BoxShadowOptions option : options) {
+        Rect rect = option.getTargetCanvasRect();
+        float left = (maxWidth - rect.width()) / 2f;
+        float top = (maxHeight - rect.height()) / 2f;
+        option.topLeft = new PointF(left, top);
+
+        BoxShadowOptions scaledOption = option.scale(quality);
+        drawShadow(canvas, scaledOption);
+      }
+
+      //Drawable's bounds must match the bitmap size, otherwise the shadows will be scaled
+      int paddingX = (maxWidth - w) / 2;
+      int paddingY = (maxHeight - h) / 2;
+      OverflowBitmapDrawable shadowDrawable = new OverflowBitmapDrawable(target.getResources(),
+          output, new Point(paddingX, paddingY), new Rect(0, 0, w, h), radii);
+
+      target.getOverlay().add(shadowDrawable);
+      //Relayout to ensure the shadows are fully drawn
+      ViewParent parent = target.getParent();
+      if (parent != null) {
+        parent.requestLayout();
+        if (parent instanceof ViewGroup) {
+          ((ViewGroup) parent).invalidate(shadowDrawable.getBounds());
+        }
+      }
+    } else {
+      // I have a dream that one day our minSdkVersion will equals or higher than 21
+      Log.w("BoxShadowUtil", "Call setNormalBoxShadow() requires API level 18 or higher.");
+    }
+  }
+
+  private static void setInsetBoxShadow(View target, List<BoxShadowOptions> options, float quality, float[] radii) {
+    if (target == null || options == null) {
+      WXLogUtils.w(TAG, "Illegal arguments");
+      return;
+    }
+
+    if (target.getWidth() == 0 || target.getHeight() == 0) {
+      WXLogUtils.w(TAG, "Target view is invisible, ignore set shadow.");
+      return;
+    }
+
+    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) {
+      Drawable[] drawables = new Drawable[options.size()];
+      for (int i = 0; i < options.size(); i++) {
+        BoxShadowOptions option = options.get(i);
+        Drawable shadow = new InsetShadowDrawable(target.getWidth(), target.getHeight(),
+            option.hShadow, option.vShadow,
+            option.blur, option.spread,
+            option.color, radii);
+        drawables[i] = shadow;
+      }
+
+      LayerDrawable layerDrawable = new LayerDrawable(drawables);
+      target.getOverlay().add(layerDrawable);
+      target.invalidate();
+    } else {
+      Log.w(TAG, "Call setInsetBoxShadow() requires API level 18 or higher.");
+    }
+  }
+
+  public static BoxShadowOptions[] parseBoxShadows(String boxShadowStyle, int viewport) {
+    // normalization color expression to #AARRGGBB
+    if (sColorPattern == null) {
+      sColorPattern = Pattern.compile("([rR][gG][bB][aA]?)\\((\\d+\\s*),\\s*(\\d+\\s*),\\s*(\\d+\\s*)(?:,\\s*(\\d+(?:\\.\\d+)?))?\\)");
+    }
+
+    Matcher matcher = sColorPattern.matcher(boxShadowStyle);
+
+    String processedStyle = boxShadowStyle;
+    while (matcher.find()) {
+      String color = matcher.group();
+      processedStyle = processedStyle.replace(color, "#" + String.format("%8s", Integer.toHexString(WXResourceUtils.getColor(color, Color.BLACK))).replaceAll("\\s", "0"));
+    }
+
+    String[] styles = processedStyle.split(",");
+    if (styles != null && styles.length > 0) {
+      BoxShadowOptions[] result = new BoxShadowOptions[styles.length];
+      for (int i = 0; i < styles.length; i++) {
+        result[i] = parseBoxShadow(styles[i], viewport);
+      }
+      return result;
+    }
+    return null;
+  }
+
+  private static BoxShadowOptions parseBoxShadow(String boxShadow, int viewport) {
+    BoxShadowOptions result = new BoxShadowOptions(viewport);
+    if (TextUtils.isEmpty(boxShadow)) {
+      return null;
+    }
+
+    String boxShadowCopy = boxShadow;
+
+    // trim rgb() & rgba()
+    boxShadowCopy = boxShadowCopy.replaceAll("\\s*,\\s+", ",");
+
+    // match inset first
+    if (boxShadowCopy.contains("inset")) {
+      result.isInset = true;
+      boxShadowCopy = boxShadowCopy.replace("inset", "");
+    }
+
+    boxShadowCopy = boxShadowCopy.trim();
+    List<String> params = new ArrayList<>(Arrays.asList(boxShadowCopy.split("\\s+")));
+
+    // match color
+    String maybeColor = params.get(params.size() - 1);
+    if (!TextUtils.isEmpty(maybeColor)) {
+      if (maybeColor.startsWith("#") || maybeColor.startsWith("rgb") || WXResourceUtils.isNamedColor(maybeColor)) {
+        result.color = WXResourceUtils.getColor(maybeColor, Color.BLACK);
+        params.remove(params.size() - 1);
+      }
+    }
+
+    try {
+      if (params.size() < 2) {
+        // Missing required param
+        return null;
+      } else {
+        if (!TextUtils.isEmpty(params.get(0))) {
+          float px = WXUtils.getFloat(params.get(0).trim(), 0f);
+          result.hShadow = WXViewUtils.getRealSubPxByWidth(px, viewport);
+        }
+
+        if (!TextUtils.isEmpty(params.get(1))) {
+          float px = WXUtils.getFloat(params.get(1).trim(), 0f);
+          result.vShadow = WXViewUtils.getRealPxByWidth(px, viewport);
+        }
+
+        for (int i = 2; i < params.size(); i++) {
+          int parserIndex = i - 2;
+          BoxShadowOptions.IParser parser = result.optionParamParsers.get(parserIndex);
+          parser.parse(params.get(i));
+        }
+      }
+    } catch (Throwable t) {
+      t.printStackTrace();
+    }
+    return result;
+  }
+
+  private static class OverflowBitmapDrawable extends BitmapDrawable {
+    private int paddingX;
+    private int paddingY;
+    private Rect viewRect;
+    private float[] radii;
+
+    private OverflowBitmapDrawable(Resources resources, Bitmap bitmap, Point topLeft, Rect viewRect, float[] radii) {
+      super(resources, bitmap);
+      this.paddingX = topLeft.x;
+      this.paddingY = topLeft.y;
+      this.viewRect = viewRect;
+      this.radii = radii;
+
+      setBounds(-paddingX, -paddingY, viewRect.width() + paddingX, viewRect.height() + paddingY);
+    }
+
+    public void draw(Canvas canvas) {
+      Rect bounds = canvas.getClipBounds();
+      Rect newRect = new Rect(bounds);
+      // Make the Canvas Rect bigger according to the padding.
+      newRect.inset(-paddingX * 2, -paddingY * 2);
+      try {
+        if(WXEnvironment.sApplication.getApplicationInfo().targetSdkVersion > VERSION_CODES.O){
+          canvas.clipRect(newRect);
+        }
+        else{
+          canvas.clipRect(newRect, Region.Op.REPLACE);
+        }
+      }catch (NullPointerException e) {
+        canvas.clipRect(newRect);
+      }
+
+      Path contentPath = new Path();
+      // the content area map must be aligned with bounds
+      RectF rectF = new RectF(bounds);
+      contentPath.addRoundRect(rectF, radii, Path.Direction.CCW);
+      // can not antialias
+      canvas.clipPath(contentPath, Region.Op.DIFFERENCE);
+
+      // translate the canvas to a suitable position and then draw the bitmap, otherwise draw from the origin(0, 0)
+      canvas.translate(bounds.left, bounds.top);
+
+      super.draw(canvas);
+    }
+  }
+
+  private static class InsetShadowDrawable extends Drawable {
+    private static final int LEFT_TO_RIGHT = 0;
+    private static final int TOP_TO_BOTTOM = 1;
+    private static final int RIGHT_TO_LEFT = 2;
+    private static final int BOTTOM_TO_TOP = 3;
+
+    private float blurRadius;
+    private int shadowColor;
+
+    private float[] radii;
+
+    private float width, height;
+
+    private float shadowXSize, shadowYSize;
+
+    private Shader[] shades = new Shader[4];
+    private Path[] paths = new Path[4];
+
+    private Paint paint;
+
+    private InsetShadowDrawable(int viewWidth, int viewHeight, float dx, float dy, float blurRadius, float spread, int shadowColor, float[] radii) {
+      this.blurRadius = blurRadius;
+      this.shadowColor = shadowColor;
+
+      this.width = viewWidth + 2 * dx;
+      this.height = viewHeight + 2 * dy;
+
+      this.shadowXSize = dx + spread;
+      this.shadowYSize = dy + spread;
+
+      this.radii = radii;
+
+      setBounds(0, 0, viewWidth, viewHeight);
+      prepare();
+    }
+
+    private void prepare() {
+      /*
+       *  A +++++++++++++++++++++++++ B
+       *  +  E ------------------- F  +
+       *  +  |                     |  +
+       *  +  |                     |  +
+       *  +  |                     |  +
+       *  +  H ------------------- G  +
+       *  D +++++++++++++++++++++++++ C
+       */
+
+      PointF a = new PointF(0, 0);
+      PointF b = new PointF(width, 0);
+      PointF c = new PointF(b.x, height);
+      PointF d = new PointF(a.x, c.y);
+
+      PointF e = new PointF(shadowXSize, shadowYSize);
+      PointF f = new PointF(b.x - shadowXSize, e.y);
+      PointF g = new PointF(f.x, c.y - shadowYSize);
+      PointF h = new PointF(e.x, g.y);
+
+      Shader ltr = new LinearGradient(e.x - blurRadius, e.y, e.x, e.y, shadowColor, Color.TRANSPARENT, Shader.TileMode.CLAMP);
+      Shader ttb = new LinearGradient(e.x, e.y - blurRadius, e.x, e.y, shadowColor, Color.TRANSPARENT, Shader.TileMode.CLAMP);
+      Shader rtl = new LinearGradient(g.x + blurRadius, g.y, g.x, g.y, shadowColor, Color.TRANSPARENT, Shader.TileMode.CLAMP);
+      Shader btt = new LinearGradient(g.x, g.y + blurRadius, g.x, g.y, shadowColor, Color.TRANSPARENT, Shader.TileMode.CLAMP);
+
+      shades[LEFT_TO_RIGHT] = ltr;
+      shades[TOP_TO_BOTTOM] = ttb;
+      shades[RIGHT_TO_LEFT] = rtl;
+      shades[BOTTOM_TO_TOP] = btt;
+
+      Path ltrPath = new Path();
+      ltrPath.moveTo(a.x, a.y);
+      ltrPath.lineTo(e.x, e.y);
+      ltrPath.lineTo(h.x, h.y);
+      ltrPath.lineTo(d.x, d.y);
+      ltrPath.close();
+
+      Path ttbPath = new Path();
+      ttbPath.moveTo(a.x, a.y);
+      ttbPath.lineTo(b.x, b.y);
+      ttbPath.lineTo(f.x, f.y);
+      ttbPath.lineTo(e.x, e.y);
+      ttbPath.close();
+
+      Path rtlPath = new Path();
+      rtlPath.moveTo(b.x, b.y);
+      rtlPath.lineTo(c.x, c.y);
+      rtlPath.lineTo(g.x, g.y);
+      rtlPath.lineTo(f.x, f.y);
+      rtlPath.close();
+
+      Path bttPath = new Path();
+      bttPath.moveTo(d.x, d.y);
+      bttPath.lineTo(c.x, c.y);
+      bttPath.lineTo(g.x, g.y);
+      bttPath.lineTo(h.x, h.y);
+      bttPath.close();
+
+      paths[LEFT_TO_RIGHT] = ltrPath;
+      paths[TOP_TO_BOTTOM] = ttbPath;
+      paths[RIGHT_TO_LEFT] = rtlPath;
+      paths[BOTTOM_TO_TOP] = bttPath;
+
+      paint = new Paint();
+      paint.setAntiAlias(true);
+      paint.setStyle(Paint.Style.FILL);
+      paint.setColor(shadowColor);
+    }
+
+    @Override
+    public void draw(Canvas canvas) {
+      Rect bounds = canvas.getClipBounds();
+      Path border = new Path();
+      RectF rectF = new RectF(bounds);
+      border.addRoundRect(rectF, radii, Path.Direction.CCW);
+      canvas.clipPath(border);
+      //TODO: we need clip border-width too
+
+      // translate the canvas to the right place and then draw the inner shadow
+      canvas.translate(bounds.left, bounds.top);
+
+      for (int i = 0; i < 4; i++) {
+        Shader shader = shades[i];
+        Path path = paths[i];
+        paint.setShader(shader);
+        canvas.drawPath(path, paint);
+      }
+    }
+
+    @Override
+    public void setAlpha(@IntRange(from = 0, to = 255) int alpha) {
+
+    }
+
+    @Override
+    public void setColorFilter(@Nullable ColorFilter colorFilter) {
+
+    }
+
+    @Override
+    public int getOpacity() {
+      return PixelFormat.OPAQUE;
+    }
+  }
+
+  public static class BoxShadowOptions {
+    private List<IParser> optionParamParsers;
+    private int viewport = 750;
+
+    public float hShadow;
+    public float vShadow;
+    public float blur = 0f;
+    public float spread = 0f;
+    public float[] radii = new float[]{0, 0, 0, 0, 0, 0, 0, 0};
+    public int color = Color.BLACK;
+    public boolean isInset = false;
+
+    public int viewWidth = 0;
+    public int viewHeight = 0;
+    public PointF topLeft = null;
+
+    private BoxShadowOptions(int vp) {
+      if (viewport != 0) {
+        this.viewport = vp;
+      }
+      optionParamParsers = new ArrayList<>();
+
+      IParser spreadParser = new IParser() {
+        @Override
+        public void parse(String param) {
+          if (!TextUtils.isEmpty(param)) {
+            float px = WXUtils.getFloat(param, 0f);
+            spread = WXViewUtils.getRealSubPxByWidth(px, viewport);
+            WXLogUtils.w(TAG, "Experimental box-shadow attribute: spread");
+          }
+        }
+      };
+
+      IParser blurParser = new IParser() {
+        @Override
+        public void parse(String param) {
+          if (!TextUtils.isEmpty(param)) {
+            float px = WXUtils.getFloat(param, 0f);
+            blur = WXViewUtils.getRealSubPxByWidth(px, viewport);
+          }
+        }
+      };
+
+      optionParamParsers.add(blurParser);
+      optionParamParsers.add(spreadParser);
+    }
+
+    public BoxShadowOptions scale(float scale) {
+      if (scale > 0f && scale <= 1f) {
+        BoxShadowOptions scaledOptions = new BoxShadowOptions(viewport);
+        scaledOptions.hShadow = hShadow * scale;
+        scaledOptions.vShadow = vShadow * scale;
+        scaledOptions.blur = blur * scale;
+        scaledOptions.spread = spread * scale;
+        for (int i = 0; i < radii.length ; i++) {
+          scaledOptions.radii[i] = radii[i] * scale;
+        }
+        scaledOptions.viewHeight = (int) (viewHeight * scale);
+        scaledOptions.viewWidth = (int) (viewWidth * scale);
+
+        if (topLeft != null) {
+          scaledOptions.topLeft = new PointF();
+          scaledOptions.topLeft.x = topLeft.x * scale;
+          scaledOptions.topLeft.y = topLeft.y * scale;
+        }
+
+        scaledOptions.color = color;
+        scaledOptions.isInset = isInset;
+        WXLogUtils.d(TAG, "Scaled BoxShadowOptions: [" + scale + "] " + scaledOptions);
+        return scaledOptions;
+      }
+      return null;
+    }
+
+    public Rect getTargetCanvasRect() {
+      int canvasWidth = viewWidth + 2 * (int) (blur + spread + Math.abs(hShadow));
+      int canvasHeight = viewHeight + 2 * (int) (blur + spread + Math.abs(vShadow));
+      return new Rect(0, 0, canvasWidth, canvasHeight);
+    }
+
+    @Override
+    public String toString() {
+
+      String r = "[" + radii[0] + "," + radii[2] + "," + radii[4] + "," + radii[6] + "]";
+
+      final StringBuffer sb = new StringBuffer("BoxShadowOptions{");
+      sb.append("h-shadow=").append(hShadow);
+      sb.append(", v-shadow=").append(vShadow);
+      sb.append(", blur=").append(blur);
+      sb.append(", spread=").append(spread);
+      sb.append(", corner-radius=").append(r);
+      sb.append(", color=#").append(Integer.toHexString(color));
+      sb.append(", inset=").append(isInset);
+      sb.append('}');
+      return sb.toString();
+    }
+
+    private interface IParser {
+      void parse(String param);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/FontDO.java b/android/sdk/src/main/java/org/apache/weex/utils/FontDO.java
new file mode 100644
index 0000000..2e91459
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/FontDO.java
@@ -0,0 +1,185 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.graphics.Typeface;
+import android.net.Uri;
+import android.text.TextUtils;
+import android.util.Base64;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.adapter.URIAdapter;
+import org.apache.weex.common.Constants;
+import java.io.File;
+
+public class FontDO {
+  private final String mFontFamilyName;
+  private String mUrl = "";
+  private String mFilePath;
+  private int mType = TYPE_NETWORK;
+  private Typeface mTypeface;
+  private int mState = STATE_INVALID;
+
+  public final static int STATE_INVALID = -1;
+  public final static int STATE_INIT = 0;
+  public final static int STATE_LOADING = 1;
+  public final static int STATE_SUCCESS = 2;
+  public final static int STATE_FAILED = 3;
+
+  public final static int TYPE_UNKNOWN = 0;
+  public final static int TYPE_NETWORK = 1;
+  public final static int TYPE_FILE = 2;
+  public final static int TYPE_LOCAL = 3;
+  public final static int TYPE_NATIVE = 4;
+  public final static int TYPE_BASE64 = 5;
+
+
+  public FontDO (String fontFamilyName, String src, WXSDKInstance instance) {
+    this.mFontFamilyName = fontFamilyName;
+    parseSrc(src,instance);
+  }
+
+  public FontDO (String fontFamilyName, Typeface typeface) {
+    this.mFontFamilyName = fontFamilyName;
+    this.mTypeface = typeface;
+    this.mType = TYPE_NATIVE;
+    this.mState = STATE_SUCCESS;
+  }
+
+  public String getFontFamilyName() {
+    return mFontFamilyName;
+  }
+
+  private void parseSrc(String src, WXSDKInstance instance) {
+    src = (src != null )? src.trim() : "";
+
+    if (instance != null) {
+      if (instance.getCustomFontNetworkHandler() != null) {
+        String localUrl = instance.getCustomFontNetworkHandler().fetchLocal(src);
+        if (!TextUtils.isEmpty(localUrl)) {
+          src = localUrl;
+        }
+      }
+    }
+
+    if (src.isEmpty()) {
+      mState = STATE_INVALID;
+      WXLogUtils.e("TypefaceUtil", "font src is empty.");
+      return;
+    }
+
+    if (src.matches("^url\\((('.*')|(\".*\"))\\)$")) {
+      String url = src.substring(5, src.length() - 2);
+      Uri uri = Uri.parse(url);
+      if( instance != null){
+        uri = instance.rewriteUri(uri, URIAdapter.FONT);
+      }
+      mUrl = uri.toString();
+      try {
+        String scheme = uri.getScheme();
+        if (Constants.Scheme.HTTP.equals(scheme) ||
+                Constants.Scheme.HTTPS.equals(scheme)) {
+          mType = TYPE_NETWORK;
+        } else if (Constants.Scheme.FILE.equals(scheme)) {
+          mType = TYPE_FILE;
+            /**
+             * eg: file://name/A/B.ttf
+             * getPath() = "A/B.ttf",but the real absolute path is "/name/A/B.ttf"
+             * so use getEncodedSchemeSpecificPart() to replaced = "//name/A/B.ttf"
+             */
+            mUrl = uri.getEncodedSchemeSpecificPart();
+        } else if (Constants.Scheme.LOCAL.equals(scheme)){
+          mType = TYPE_LOCAL;
+        } else if (Constants.Scheme.DATA.equals(scheme)) {
+          long start = System.currentTimeMillis();
+          String[] data = mUrl.split(",");
+          if (data != null && data.length == 2) {
+            String identify = data[0];
+            if (!TextUtils.isEmpty(identify) && identify.endsWith("base64")) {
+              //Do not check mime type and charset for now
+              String base64Data = data[1];
+              if (!TextUtils.isEmpty(base64Data)) {
+                String md5 = WXFileUtils.md5(base64Data);
+                File cacheDir = new File(WXEnvironment.getApplication().getCacheDir(),
+                    "font-family");
+                if (!cacheDir.exists()) {
+                  cacheDir.mkdirs();
+                }
+                File tmpFile = new File(cacheDir, md5);
+                if(!tmpFile.exists()){
+                  tmpFile.createNewFile();
+                  WXFileUtils.saveFile(tmpFile.getPath(), Base64.decode(base64Data, Base64.DEFAULT), WXEnvironment.getApplication());
+                }
+                mUrl = tmpFile.getPath();
+                mType = TYPE_BASE64;
+                WXLogUtils.d("TypefaceUtil", "Parse base64 font cost " + (System.currentTimeMillis() - start) + " ms");
+              }
+            }
+          }
+        } else {
+          WXLogUtils.e("TypefaceUtil", "Unknown scheme for font url: " + mUrl);
+          mType = TYPE_UNKNOWN;
+        }
+        mState = STATE_INIT;
+      } catch (Exception e) {
+        mType = STATE_INVALID;
+        WXLogUtils.e("TypefaceUtil", "URI.create(mUrl) failed mUrl: " + mUrl+ "\n"+ WXLogUtils.getStackTrace(e));
+      }
+    } else {
+      mUrl = src;
+      mState = STATE_INVALID;
+    }
+
+    if(WXEnvironment.isApkDebugable()) {
+      WXLogUtils.d("TypefaceUtil", "src:" + src + ", mUrl:" + mUrl + ", mType:" + mType);
+    }
+  }
+
+  public String getUrl() {
+    return mUrl;
+  }
+
+  public int getType() {
+    return mType;
+  }
+
+  public Typeface getTypeface() {
+    return mTypeface;
+  }
+
+  public void setTypeface(Typeface typeface) {
+    this.mTypeface = typeface;
+  }
+
+  public int getState() {
+    return mState;
+  }
+
+  public void setState(int state) {
+    this.mState = state;
+  }
+
+  public String getFilePath() {
+    return mFilePath;
+  }
+
+  public void setFilePath(String mFilePath) {
+    this.mFilePath = mFilePath;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/FunctionParser.java b/android/sdk/src/main/java/org/apache/weex/utils/FunctionParser.java
new file mode 100644
index 0000000..72953cd
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/FunctionParser.java
@@ -0,0 +1,240 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.support.annotation.NonNull;
+
+import java.util.LinkedHashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Parser for function like "rotate(30 ) transform(50 , 20)".
+ * This class will translate the raw string presentation of a group of function(s) to give type
+ * according to the {@link FunctionParser.Mapper}
+ */
+public class FunctionParser<K, V> {
+
+  public static final char SPACE = ' ';
+
+  private Mapper<K, V> mapper;
+  private Lexer lexer;
+
+  /**
+   * Construct a function parser
+   * @param source the raw string representation of a group of function(s)
+   * @param mapper the mapping rule between string and corresponding type of object.
+   */
+  public FunctionParser(@NonNull String source, @NonNull Mapper<K, V> mapper) {
+    this.lexer = new Lexer(source);
+    this.mapper = mapper;
+  }
+
+  /**
+   * Start to parse the raw string. The result will be stored in a sorted map where the order
+   * is defined by the function order in the raw string.
+   * @return
+   */
+  public LinkedHashMap<K, V> parse() {
+    lexer.moveOn();
+    return definition();
+  }
+
+  private LinkedHashMap<K, V> definition() {
+    LinkedHashMap<K, V> result = new LinkedHashMap<>();
+    do {
+      result.putAll(function());
+    } while (lexer.getCurrentToken() == Token.FUNC_NAME);
+    return result;
+  }
+
+  private Map<K, V> function() {
+    List<String> list = new LinkedList<>();
+    String functionName = match(Token.FUNC_NAME);
+    match(Token.LEFT_PARENT);
+    list.add(match(Token.PARAM_VALUE));
+    while (lexer.getCurrentToken() == Token.COMMA) {
+      match(Token.COMMA);
+      list.add(match(Token.PARAM_VALUE));
+    }
+    match(Token.RIGHT_PARENT);
+    return mapper.map(functionName, list);
+  }
+
+  private String match(Token token) {
+    try {
+      if (token == lexer.getCurrentToken()) {
+        String value = lexer.getCurrentTokenValue();
+        lexer.moveOn();
+        return value;
+      }
+    } catch (Exception e) {
+      WXLogUtils.e(token + "Token doesn't match" + lexer.source);
+    }
+    return "";
+  }
+
+  private enum Token {
+    FUNC_NAME, PARAM_VALUE, LEFT_PARENT, RIGHT_PARENT, COMMA
+  }
+
+  public interface Mapper<K, V> {
+
+    /**
+     * Map one function to a specified type of object
+     * @param functionName the name of the raw function.
+     * @param raw the list of parameter of the raw function
+     * @return the expected mapping relationship, where the key in the map is the same as the
+     * key in the return value of {{@link #parse()}},
+     * and the value in the map is the type of object that expected by user.
+     */
+    Map<K, V> map(String functionName, List<String> raw);
+  }
+
+  private static class WXInterpretationException extends RuntimeException {
+
+    private WXInterpretationException(String msg) {
+      super(msg);
+    }
+  }
+
+  /**
+   * Lexer for the parser. For now,  digit, alphabet, '(', ')', '.', ',', '+', '-' and '%' is
+   * valid character, and '(', ')', ',', parameter value and function name is valid token.
+   * Parameter value is defined as "(?i)[\+-]?[0-9]+(\.[0-9]+)?(%||deg||px)?" while function
+   * name is defined as "[a-zA-Z]+".
+   *
+   * The Lexer can also be expressed using the following EBNF format.
+   * <ul>
+   *   <li>definition = {function};</li>
+   *   <li>function = name, "(", value, { ",", value } , ")";</li>
+   *   <li>name = character, {character};</li>
+   *   <li>value = identifier, {identifier};</li>
+   *   <li>identifier = character | "." | "%" | "+" | "-";</li>
+   *   <li>character = digit | letter;</li>
+   *   <li>digit =  "0" | "1" | "2" | "3" | "4" | "5" | "6" | "7" | "8" | "9" ;</li>
+   *   <li>letter = "A" | "B" | "C" | "D" | "E" | "F" | "G" | "H" | "I" | "J" | "K" | "L" | "M" |
+   *   "N" | "O" | "P" | "Q" | "R" | "S" | "T" | "U" | "V" | "W" | "X" | "Y" | "Z" | "a" | "b" |
+   *   "c" | "d" | "e" | "f" | "g" | "h" | "i" | "j" | "k" | "l" | "m" | "n" | "o" | "p" | "q" |
+   *   "r" | "s" | "t" | "u" | "v" | "w" | "x" | "y" | "z" ;</li>
+   * </ul>
+   */
+  private static class Lexer {
+
+    private static final String LEFT_PARENT = "(";
+    private static final String RIGHT_PARENT = ")";
+    private static final String COMMA = ",";
+    private static final char A_LOWER = 'a';
+    private static final char Z_LOWER = 'z';
+    private static final char A_UPPER = 'A';
+    private static final char Z_UPPER = 'Z';
+    private static final char ZERO = '0';
+    private static final char NINE = '9';
+    private static final char DOT = '.';
+    private static final char MINUS = '-';
+    private static final char PLUS = '+';
+    private String source;
+    private Token current;
+    private String value;
+    private int pointer = 0;
+
+    private Lexer(String source) {
+      this.source = source;
+    }
+
+    private Token getCurrentToken() {
+      return current;
+    }
+
+    private String getCurrentTokenValue() {
+      return value;
+    }
+
+    private boolean moveOn() {
+      int start = pointer;
+      char curChar;
+      while (pointer < source.length()) {
+        curChar = source.charAt(pointer);
+        if (curChar == SPACE) {
+          if (start == pointer++) {
+            start++;
+          } else {
+            break;
+          }
+        } else if (isCharacterOrDigit(curChar) || curChar == DOT
+                || curChar == WXUtils.PERCENT || curChar == MINUS || curChar == PLUS) {
+          pointer++;
+        } else {
+          if (start == pointer) {
+            pointer++;
+          }
+          break;
+        }
+      }
+      if (start != pointer) {
+        String symbol = source.substring(start, pointer);
+        moveOn(symbol);
+        return true;
+      } else {
+        current = null;
+        value = null;
+        return false;
+      }
+    }
+
+    private void moveOn(String token) {
+      if (LEFT_PARENT.equals(token)) {
+        current = Token.LEFT_PARENT;
+        value = LEFT_PARENT;
+      } else if (RIGHT_PARENT.equals(token)) {
+        current = Token.RIGHT_PARENT;
+        value = RIGHT_PARENT;
+      } else if (COMMA.equals(token)) {
+        current = Token.COMMA;
+        value = COMMA;
+      } else if (isFuncName(token)) {
+        current = Token.FUNC_NAME;
+        value = token;
+      } else {
+        current = Token.PARAM_VALUE;
+        value = token;
+      }
+    }
+
+    private boolean isFuncName(CharSequence funcName) {
+      char letter;
+      for (int i = 0; i < funcName.length(); i++) {
+        letter = funcName.charAt(i);
+        if (!((A_LOWER <= letter && letter <= Z_LOWER) ||
+                (A_UPPER <= letter && letter <= Z_UPPER) ||
+                letter == MINUS)) {
+          return false;
+        }
+      }
+      return true;
+    }
+
+    private boolean isCharacterOrDigit(char letter) {
+      return (ZERO <= letter && letter <= NINE) || (A_LOWER <= letter && letter <= Z_LOWER) ||
+              (A_UPPER <= letter && letter <= Z_UPPER);
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/ImageDrawable.java b/android/sdk/src/main/java/org/apache/weex/utils/ImageDrawable.java
new file mode 100644
index 0000000..6714a39
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/ImageDrawable.java
@@ -0,0 +1,155 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.utils;
+
+import android.graphics.Bitmap;
+import android.graphics.BitmapShader;
+import android.graphics.Canvas;
+import android.graphics.Matrix;
+import android.graphics.Paint;
+import android.graphics.RectF;
+import android.graphics.Shader;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.PaintDrawable;
+import android.graphics.drawable.shapes.Shape;
+import android.os.Build;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.widget.ImageView;
+
+public class ImageDrawable extends PaintDrawable {
+
+  public static Drawable createImageDrawable(@Nullable Drawable original,
+                                             @NonNull ImageView.ScaleType scaleType,
+                                             @Nullable float[] borderRadius,
+                                             int vWidth,
+                                             int vHeight,
+                                             boolean gif) {
+    Bitmap bm;
+    if (!gif && vWidth > 0 && vHeight > 0) {
+      if (original instanceof BitmapDrawable &&
+              (bm = ((BitmapDrawable) original).getBitmap()) != null) {
+        ImageDrawable imageDrawable;
+        imageDrawable = new ImageDrawable();
+        // fix android 9 image antialiasing
+        imageDrawable.getPaint().setFilterBitmap(true);
+        imageDrawable.bitmapWidth = bm.getWidth();
+        imageDrawable.bitmapHeight = bm.getHeight();
+        BitmapShader bitmapShader = new BitmapShader(bm, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
+        updateShaderAndSize(scaleType, vWidth, vHeight, imageDrawable, bitmapShader);
+        imageDrawable.getPaint().setShader(bitmapShader);
+        return imageDrawable;
+      } else if (original instanceof ImageDrawable) {
+        ImageDrawable imageDrawable = (ImageDrawable) original;
+        if (imageDrawable.getPaint() != null &&
+                imageDrawable.getPaint().getShader() instanceof BitmapShader) {
+          BitmapShader bitmapShader = (BitmapShader) imageDrawable.getPaint().getShader();
+          updateShaderAndSize(scaleType, vWidth, vHeight, imageDrawable, bitmapShader);
+          return imageDrawable;
+        }
+      }
+    }
+    return original;
+  }
+
+  private static void updateShaderAndSize(@NonNull ImageView.ScaleType scaleType, int vWidth, int vHeight, ImageDrawable imageDrawable, BitmapShader bitmapShader) {
+    Matrix matrix = createShaderMatrix(scaleType, vWidth, vHeight,
+            imageDrawable.bitmapWidth,
+            imageDrawable.bitmapHeight);
+    int intrinsicWidth = vWidth, intrinsicHeight = vHeight;
+    if (scaleType == ImageView.ScaleType.FIT_CENTER) {
+      RectF bitmapRect = new RectF(0, 0, imageDrawable.bitmapWidth, imageDrawable.bitmapHeight), contentRect = new RectF();
+      matrix.mapRect(contentRect, bitmapRect);
+      intrinsicWidth = (int) contentRect.width();
+      intrinsicHeight = (int) contentRect.height();
+      matrix = createShaderMatrix(scaleType, intrinsicWidth, intrinsicHeight, imageDrawable
+              .bitmapWidth, imageDrawable.bitmapHeight);
+    }
+    imageDrawable.setIntrinsicWidth(intrinsicWidth);
+    imageDrawable.setIntrinsicHeight(intrinsicHeight);
+    bitmapShader.setLocalMatrix(matrix);
+  }
+
+  @NonNull
+  private static Matrix createShaderMatrix(@NonNull ImageView.ScaleType scaleType, int vWidth,
+                                           int vHeight, int bmWidth, int bmHeight) {
+    float scale, translateX = 0, translateY = 0;
+
+    if (bmWidth * vHeight > bmHeight * vWidth) {
+      scale = vHeight / (float) bmHeight;
+      translateX = (vWidth - bmWidth * scale) * 0.5f;
+    } else {
+      scale = vWidth / (float) bmWidth;
+      translateY = (vHeight - bmHeight * scale) * 0.5f;
+    }
+
+    Matrix mMatrix = new Matrix();
+    if (scaleType == ImageView.ScaleType.FIT_XY) {
+      mMatrix.setScale(vWidth / (float) bmWidth, vHeight / (float) bmHeight);
+    } else if (scaleType == ImageView.ScaleType.FIT_CENTER) {
+      RectF src = new RectF(0, 0, bmWidth, bmHeight);
+      RectF dist = new RectF(0, 0, vWidth, vHeight);
+      mMatrix.setRectToRect(src, dist, Matrix.ScaleToFit.CENTER);
+    } else if (scaleType == ImageView.ScaleType.CENTER_CROP) {
+      mMatrix.setScale(scale, scale);
+      mMatrix.postTranslate(translateX + 0.5f, translateY + 0.5f);
+    }
+    return mMatrix;
+  }
+
+  private float[] radii;
+  private int bitmapHeight;
+  private int bitmapWidth;
+
+  private ImageDrawable() {
+
+  }
+
+  @Override
+  public void setCornerRadii(float[] radii) {
+    this.radii = radii;
+    super.setCornerRadii(radii);
+  }
+
+  @Override
+  protected void onDraw(Shape shape, Canvas canvas, Paint paint) {
+    if (Build.VERSION.SDK_INT == Build.VERSION_CODES.LOLLIPOP) {
+      // fix api 21 PaintDrawable crash
+      paint.setAntiAlias(false);
+    }
+    super.onDraw(shape, canvas, paint);
+  }
+
+  public
+  @Nullable
+  float[] getCornerRadii() {
+    return this.radii;
+  }
+
+  public int getBitmapHeight() {
+    return bitmapHeight;
+  }
+
+  public int getBitmapWidth() {
+    return bitmapWidth;
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/ImgURIUtil.java b/android/sdk/src/main/java/org/apache/weex/utils/ImgURIUtil.java
new file mode 100644
index 0000000..15f56d4
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/ImgURIUtil.java
@@ -0,0 +1,42 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.utils;
+
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.drawable.Drawable;
+import android.net.Uri;
+import android.support.v4.content.res.ResourcesCompat;
+
+import java.util.List;
+
+public class ImgURIUtil {
+
+  public static Drawable getDrawableFromLoaclSrc(Context context, Uri rewrited) {
+    Resources resources = context.getResources();
+    List<String> segments = rewrited.getPathSegments();
+    if (segments.size() != 1) {
+      WXLogUtils.e("Local src format is invalid.");
+      return null;
+    }
+    int id = resources.getIdentifier(segments.get(0), "drawable", context.getPackageName());
+    return id == 0 ? null : ResourcesCompat.getDrawable(resources, id, null);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/LogLevel.java b/android/sdk/src/main/java/org/apache/weex/utils/LogLevel.java
new file mode 100644
index 0000000..9279a65
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/LogLevel.java
@@ -0,0 +1,57 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.util.Log;
+
+/**
+ * Created by lixinke on 16/5/11.
+ */
+public enum LogLevel {
+  OFF("off",8, Log.ASSERT),
+  WTF("wtf", 7, Log.ASSERT),
+  TLOG("tlog",6,Log.ERROR), //Add For Son Process
+  ERROR("error", 5, Log.ERROR),
+  WARN("warn", 4, Log.WARN),
+  INFO("info", 3, Log.INFO),
+  DEBUG("debug", 2, Log.DEBUG),
+  VERBOSE("verbose", 1, Log.VERBOSE),
+  ALL("all", 0, Log.VERBOSE),;
+  String name;
+  int value;
+  int priority;
+
+  LogLevel(String name, int value,int priority) {
+    this.name = name;
+    this.value = value;
+    this.priority = priority;
+  }
+  public String getName(){
+    return name;
+  }
+  public int getValue(){
+    return value;
+  }
+  public int getPriority(){
+    return priority;
+  }
+  public int compare(LogLevel level){
+    return value-level.value;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/OsVersion.java b/android/sdk/src/main/java/org/apache/weex/utils/OsVersion.java
new file mode 100644
index 0000000..9f39f31
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/OsVersion.java
@@ -0,0 +1,47 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+/**
+ * Android OS version utilities.
+ */
+public class OsVersion {
+  private static boolean sIsAtLeastJB_MR2;
+
+
+  static {
+    final int v = getApiVersion();
+    sIsAtLeastJB_MR2 = v >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR2;
+  }
+
+  /**
+   * @return True if the version of Android that we're running on is at
+   * least Jelly Bean MR2(API level 18).
+   */
+  public static boolean isAtLeastJB_MR2() {
+    return sIsAtLeastJB_MR2;
+  }
+
+  /**
+   * @return The Android API version of the running OS.
+   */
+  public static int getApiVersion() {
+    return android.os.Build.VERSION.SDK_INT;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/SingleFunctionParser.java b/android/sdk/src/main/java/org/apache/weex/utils/SingleFunctionParser.java
new file mode 100644
index 0000000..ac0f771
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/SingleFunctionParser.java
@@ -0,0 +1,83 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.utils;
+
+import android.support.annotation.NonNull;
+
+import java.util.HashMap;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+
+public class SingleFunctionParser<V> extends FunctionParser<String, List<V>> {
+
+  public interface FlatMapper<V> {
+
+    V map(String raw);
+  }
+
+  public interface NonUniformMapper<V>{
+    List<V> map(List<String> raw);
+  }
+
+  /**
+   * Construct a function parser for uniform parameters.
+   * @param source the raw string representation of a group of function(s)
+   * @param mapper the mapping rule between string and corresponding type of object.
+   */
+  public SingleFunctionParser(@NonNull String source, @NonNull final FlatMapper<V> mapper) {
+    super(source, new Mapper<String, List<V>>() {
+      @Override
+      public Map<String, List<V>> map(String functionName, List<String> raw) {
+        Map<String, List<V>> map = new HashMap<String, List<V>>();
+        List<V> list = new LinkedList<V>();
+        for (String item : raw) {
+          list.add(mapper.map(item));
+        }
+        map.put(functionName, list);
+        return map;
+      }
+    });
+  }
+
+  /**
+   * Construct a function parser for non-uniform parameters.
+   * @param source the raw string representation of a group of function(s)
+   * @param mapper the mapping rule between string and corresponding type of object.
+   */
+  public SingleFunctionParser(@NonNull String source, @NonNull final NonUniformMapper<V> mapper) {
+    super(source, new Mapper<String, List<V>>() {
+      @Override
+      public Map<String, List<V>> map(String functionName, List<String> raw) {
+        Map<String, List<V>> map = new HashMap<String, List<V>>();
+        map.put(functionName, mapper.map(raw));
+        return map;
+      }
+    });
+  }
+
+  public List<V> parse(String functionName) {
+    Map<String, List<V>> map = parse();
+    if(map.containsKey(functionName)){
+      return map.get(functionName);
+    }
+    return null;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/StaticLayoutProxy.java b/android/sdk/src/main/java/org/apache/weex/utils/StaticLayoutProxy.java
new file mode 100644
index 0000000..cacd2b6
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/StaticLayoutProxy.java
@@ -0,0 +1,78 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.text.Layout;
+import android.text.StaticLayout;
+import android.text.TextDirectionHeuristic;
+import android.text.TextDirectionHeuristics;
+import android.text.TextPaint;
+
+import java.lang.reflect.Constructor;
+
+/**
+ * Created by moxun on 2017/9/26.
+ */
+
+public class StaticLayoutProxy {
+  private static Constructor<StaticLayout> layoutConstructor;
+  public static StaticLayout create(CharSequence source, TextPaint paint,
+                                    int width,
+                                    Layout.Alignment align, float spacingmult, float spacingadd,
+                                    boolean includepad, boolean forceRtl) {
+    if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR2 && forceRtl) {
+      TextDirectionHeuristic textDir = TextDirectionHeuristics.RTL;
+      StaticLayout rtlLayout =  createInternal(source, paint, width, align, textDir, spacingmult, spacingadd, includepad);
+      if (rtlLayout != null) {
+        return rtlLayout;
+      } else {
+        return new StaticLayout(source, paint, width, align, spacingmult, spacingadd, includepad);
+      }
+    }
+    return new StaticLayout(source, paint, width, align, spacingmult, spacingadd, includepad);
+  }
+
+  private static StaticLayout createInternal(CharSequence source, TextPaint paint,
+                                             int width, Layout.Alignment align, TextDirectionHeuristic textDir,
+                                             float spacingmult, float spacingadd,
+                                             boolean includepad) {
+    if (android.os.Build.VERSION.SDK_INT < android.os.Build.VERSION_CODES.JELLY_BEAN_MR2) {
+      return null;
+    } else {
+      try {
+        if (layoutConstructor == null) {
+          Class<StaticLayout> clazz = StaticLayout.class;
+          Constructor<StaticLayout> constructor = clazz.getConstructor(CharSequence.class, TextPaint.class,
+                  int.class, Layout.Alignment.class, TextDirectionHeuristic.class,
+                  float.class, float.class,
+                  boolean.class);
+          layoutConstructor = constructor;
+        }
+        if (layoutConstructor != null) {
+          return layoutConstructor.newInstance(source, paint, width,
+                  align, textDir, spacingmult, spacingadd, includepad);
+        }
+
+      } catch (Throwable e) {
+        e.printStackTrace();
+      }
+    }
+    return null;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/Trace.java b/android/sdk/src/main/java/org/apache/weex/utils/Trace.java
new file mode 100644
index 0000000..0544555
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/Trace.java
@@ -0,0 +1,113 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.annotation.TargetApi;
+import android.os.Build;
+
+/**
+ * Hepler class for systrace.
+ *
+ * Note that this will run only on JBMR2 or later.
+ *
+ * Trace will be enabled in debug production and be disabled in release
+ * production, see build.gradle.
+ * If you want to enable it in release, just set sEnabled to true.
+ */
+public class Trace {
+  private static final String TAG = "Weex_Trace";
+  private abstract static class AbstractTrace {
+    abstract void beginSection(String sectionName);
+    abstract void endSection();
+  }
+
+  private static final AbstractTrace sTrace;
+  private static final boolean sEnabled;
+
+  // Pick the correct trace class to handle tracing.
+  static {
+    // If you want to enable it in release, just set sEnabled to true.
+    // If you turn sEnabled on, weex would trace logs on Java side
+    // as well as on V8 side, please take care of turning sEnabled on
+    // to avoid performance impact.
+    // FIXME: weex sdk may use another build files to build and cause
+    // compiling errors if these build files don't contain any
+    // ENABLE_TRACE, just comment out the line below.
+    //sEnabled = com.taobao.weappplus_sdk.BuildConfig.ENABLE_TRACE;
+    sEnabled = false;
+
+    if (sEnabled == true && OsVersion.isAtLeastJB_MR2()) {
+      sTrace = new TraceJBMR2();
+    } else {
+      sTrace = new TraceDummy();
+    }
+  }
+
+  public static final boolean getTraceEnabled() {
+    return sEnabled;
+  }
+
+  /**
+   * Writes a trace message to indicate that a given section of code has begun.
+   * This call must be followed by a corresponding call to {@link #endSection()}
+   * on the same thread.
+   *
+   * <p class="note"> If sectionName contains '|', '\n' and '\0', these characters
+   * will be repaced with a space character.
+   *
+   * @param sectionName The name of code section to appear in the trace.
+   */
+  public static void beginSection(String sectionName) {
+    android.util.Log.i(TAG, "beginSection() " + sectionName);
+    sTrace.beginSection(sectionName);
+  }
+
+  /**
+   * Writes a trace message to indicate that a given section of code has ended.
+   * This call must be preceeded by a corresponding call to {@link #beginSection(String)}
+   * on the same thread.
+   */
+  public static void endSection() {
+    sTrace.endSection();
+    android.util.Log.i(TAG, "endSection()");
+  }
+
+  @TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR2)
+  private static final class TraceJBMR2 extends AbstractTrace {
+    @Override
+    void beginSection(String sectionName) {
+      android.os.Trace.beginSection(sectionName);
+    }
+
+    @Override
+    void endSection() {
+      android.os.Trace.endSection();
+    }
+  }
+
+  private static final class TraceDummy extends AbstractTrace {
+    @Override
+    void beginSection(String sectionName) {
+    }
+
+    @Override
+    void endSection() {
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/TypefaceUtil.java b/android/sdk/src/main/java/org/apache/weex/utils/TypefaceUtil.java
new file mode 100644
index 0000000..a028c4d
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/TypefaceUtil.java
@@ -0,0 +1,297 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.content.Intent;
+import android.graphics.Paint;
+import android.graphics.Typeface;
+import android.net.Uri;
+import android.support.v4.content.LocalBroadcastManager;
+import android.text.TextUtils;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXHttpAdapter;
+import org.apache.weex.common.WXRequest;
+import org.apache.weex.common.WXResponse;
+import org.apache.weex.dom.WXStyle;
+import org.apache.weex.font.FontAdapter;
+
+import java.io.File;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Created by sospartan on 7/13/16.
+ */
+public class TypefaceUtil {
+  public static final String FONT_CACHE_DIR_NAME = "font-family";
+  private final static String TAG = "TypefaceUtil";
+  private final static Map<String, FontDO> sCacheMap = new HashMap<>(); //Key: fontFamilyName
+
+  public static final String ACTION_TYPE_FACE_AVAILABLE = "type_face_available";
+
+  public static void putFontDO(FontDO fontDO) {
+    if (fontDO != null && !TextUtils.isEmpty(fontDO.getFontFamilyName())) {
+      sCacheMap.put(fontDO.getFontFamilyName(), fontDO);
+    }
+  }
+
+  public static void registerNativeFont(Map<String, Typeface> fonts) {
+    if (fonts != null && fonts.size() > 0) {
+      for (Map.Entry<String, Typeface> font : fonts.entrySet()) {
+        FontDO fontDO = new FontDO(font.getKey(), font.getValue());
+        putFontDO(fontDO);
+        if (WXEnvironment.isApkDebugable()){
+          WXLogUtils.d("TypefaceUtil", "register new typeface: " + font.getKey());
+        }
+      }
+    }
+  }
+
+  public static FontDO getFontDO(String fontFamilyName) {
+    return sCacheMap.get(fontFamilyName);
+  }
+
+  public static void removeFontDO(String fontFamilyName) {
+    sCacheMap.remove(fontFamilyName);
+  }
+
+  public static void applyFontStyle(Paint paint, int style, int weight, String family) {
+    int oldStyle;
+    Typeface typeface = paint.getTypeface();
+    if (typeface == null) {
+      oldStyle = 0;
+    } else {
+      oldStyle = typeface.getStyle();
+    }
+
+    int want = 0;
+    if ((weight == Typeface.BOLD)
+            || ((oldStyle & Typeface.BOLD) != 0 && weight == WXStyle.UNSET)) {
+      want |= Typeface.BOLD;
+    }
+
+    if ((style == Typeface.ITALIC)
+            || ((oldStyle & Typeface.ITALIC) != 0 && style == WXStyle.UNSET)) {
+      want |= Typeface.ITALIC;
+    }
+
+    if (family != null) {
+      typeface = getOrCreateTypeface(family, want);
+    }
+
+    if (typeface != null) {
+      paint.setTypeface(Typeface.create(typeface, want));
+    } else {
+      paint.setTypeface(Typeface.defaultFromStyle(want));
+    }
+  }
+
+  public static Typeface getOrCreateTypeface(String family, int style) {
+    FontDO fontDo = sCacheMap.get(family);
+    if (fontDo != null && fontDo.getTypeface() != null) {
+      return fontDo.getTypeface();
+    }
+
+    return Typeface.create(family, style);
+  }
+
+  private static void loadFromAsset(FontDO fontDo,String path){
+    try {
+      Typeface typeface = Typeface.createFromAsset(WXEnvironment.getApplication().getAssets(), path);
+      if (typeface != null) {
+        if(WXEnvironment.isApkDebugable()) {
+          WXLogUtils.d(TAG, "load asset file success");
+        }
+        fontDo.setState(FontDO.STATE_SUCCESS);
+        fontDo.setTypeface(typeface);
+      } else {
+        WXLogUtils.e(TAG, "Font asset file not found " + fontDo.getUrl());
+      }
+    } catch (Exception e) {
+      WXLogUtils.e(TAG, e.toString());
+    }
+  }
+
+  public static void loadTypeface(final FontDO fontDo, boolean notify) {
+    if (fontDo != null && fontDo.getTypeface() == null &&
+            (fontDo.getState() == FontDO.STATE_FAILED || fontDo.getState() == FontDO.STATE_INIT)) {
+      fontDo.setState(FontDO.STATE_LOADING);
+      if (fontDo.getType() == FontDO.TYPE_LOCAL) {
+        Uri uri = Uri.parse(fontDo.getUrl());
+        loadFromAsset(fontDo,uri.getPath().substring(1));//exclude slash
+      } else if (fontDo.getType() == FontDO.TYPE_NETWORK) {
+        final String url = fontDo.getUrl();
+        final String fontFamily = fontDo.getFontFamilyName();
+        final String fileName = WXFileUtils.md5(url);
+        //url.replace('/', '_').replace(':', '_');
+        File dir = new File(getFontCacheDir());
+        if(!dir.exists()){
+          dir.mkdirs();
+        }
+        final String fullPath =  dir.getAbsolutePath()+ File.separator +fileName;
+        if (!loadLocalFontFile(fullPath, fontFamily, false)) {
+          downloadFontByNetwork(url, fullPath, fontFamily);
+        }
+      } else if (fontDo.getType() == FontDO.TYPE_FILE || fontDo.getType() == FontDO.TYPE_BASE64) {
+        boolean result = loadLocalFontFile(fontDo.getUrl(), fontDo.getFontFamilyName(), false);
+        if (!result) {
+          fontDo.setState(FontDO.STATE_FAILED);
+        }
+      }
+      return;
+    }
+    if(notify){
+         notifyFontAvailable(false, fontDo);
+    }
+  }
+
+  private static void downloadFontByNetwork(final String url, final String fullPath, final String fontFamily) {
+    IWXHttpAdapter adapter = WXSDKManager.getInstance().getIWXHttpAdapter();
+    if (adapter == null) {
+      WXLogUtils.e(TAG, "downloadFontByNetwork() IWXHttpAdapter == null");
+      return;
+    }
+    WXRequest request = new WXRequest();
+    request.url = url;
+    request.method = "GET";
+    adapter.sendRequest(request, new IWXHttpAdapter.OnHttpListener() {
+      @Override
+      public void onHttpStart() {
+        if(WXEnvironment.isApkDebugable()) {
+          WXLogUtils.d(TAG, "downloadFontByNetwork begin url:" + url);
+        }
+      }
+
+      @Override
+      public void onHeadersReceived(int statusCode, Map<String, List<String>> headers) {
+
+      }
+
+      @Override
+      public void onHttpUploadProgress(int uploadProgress) {
+
+      }
+
+      @Override
+      public void onHttpResponseProgress(int loadedLength) {
+
+      }
+
+      @Override
+      public void onHttpFinish(WXResponse response) {
+        int statusCode = 0;
+        if (!TextUtils.isEmpty(response.statusCode)) {
+          try {
+            statusCode = Integer.parseInt(response.statusCode);
+          } catch (NumberFormatException e) {
+            statusCode = 0;
+            WXLogUtils.e(TAG, "IWXHttpAdapter onHttpFinish statusCode:" + response.statusCode);
+          }
+        }
+        boolean result;
+        if (statusCode >= 200 && statusCode <= 299 && response.originalData != null) {
+          result = WXFileUtils.saveFile(fullPath, response.originalData, WXEnvironment.getApplication());
+          if (result) {
+            result = loadLocalFontFile(fullPath, fontFamily, true);
+          } else {
+            if(WXEnvironment.isApkDebugable()) {
+              WXLogUtils.d(TAG, "downloadFontByNetwork() onHttpFinish success, but save file failed.");
+            }
+          }
+        } else {
+          result = false;
+        }
+
+        if (!result) {
+          FontDO fontDO = sCacheMap.get(fontFamily);
+          if (fontDO != null) {
+            fontDO.setState(FontDO.STATE_FAILED);
+          }
+        }
+      }
+    });
+  }
+
+  private static boolean loadLocalFontFile(final String path, final String fontFamily, boolean hasNetworkDowload) {
+    if (TextUtils.isEmpty(path) || TextUtils.isEmpty(fontFamily)) {
+      return false;
+    }
+    try {
+      File file = new File(path);
+      if (!file.exists()) {
+        return false;
+      }
+      Typeface typeface = Typeface.createFromFile(path);
+      if (typeface != null) {
+        final FontDO fontDo = sCacheMap.get(fontFamily);
+        if (fontDo != null) {
+          fontDo.setState(FontDO.STATE_SUCCESS);
+          fontDo.setTypeface(typeface);
+          fontDo.setFilePath(path);
+          if(WXEnvironment.isApkDebugable()) {
+            WXLogUtils.d(TAG, "load local font file success");
+          }
+
+          if(hasNetworkDowload) {
+            /**
+             * wxtext may be measured when font not load, when register broadcast receiver,
+             * this broadcast has been send, which cause textview not rendered right.
+             * delay broadcast ensure text will render right
+             * */
+            WXSDKManager.getInstance().getWXRenderManager().postOnUiThread(new Runnable() {
+              @Override
+              public void run() {
+               notifyFontAvailable(true, fontDo);
+              }
+            }, 100);
+          }else{
+             notifyFontAvailable(true, fontDo);
+          }
+          return true;
+        }
+      } else {
+        WXLogUtils.e(TAG, "load local font file failed, can't create font.");
+      }
+    } catch (Exception e) {
+      WXLogUtils.e(TAG, e.toString());
+    }
+    return false;
+  }
+
+  private static void notifyFontAvailable(boolean sendBroadcast, FontDO fontDO){
+    if(sendBroadcast){
+      Intent intent = new Intent(ACTION_TYPE_FACE_AVAILABLE);
+      intent.putExtra("fontFamily", fontDO.getFontFamilyName());
+      intent.putExtra("filePath", fontDO.getFilePath());
+      intent.putExtra("fontUrl", fontDO.getUrl());
+      LocalBroadcastManager.getInstance(WXEnvironment.getApplication()).sendBroadcast(intent);
+    }
+    FontAdapter fontAdapter = WXSDKManager.getInstance().getFontAdapter();
+    if(fontAdapter != null){
+        fontAdapter.onFontLoad(fontDO.getFontFamilyName(), fontDO.getUrl(), fontDO.getFilePath());
+    }
+  }
+
+  private static String getFontCacheDir() {
+    return WXEnvironment.getApplication().getCacheDir() + "/" + FONT_CACHE_DIR_NAME;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXDataStructureUtil.java b/android/sdk/src/main/java/org/apache/weex/utils/WXDataStructureUtil.java
new file mode 100644
index 0000000..72b45ea
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXDataStructureUtil.java
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2007 The Guava Authors
+ *
+ * Licensed 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
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import java.util.HashMap;
+
+public class WXDataStructureUtil {
+
+  /**
+   * The largest power of two that can be represented as an {@code int}.
+   */
+  private static final int MAX_POWER_OF_TWO = 1 << (Integer.SIZE - 2);
+
+  /**
+   * Creates a {@code HashMap} instance, with a high enough "initial capacity" that it <i>should</i>
+   * hold {@code expectedSize} elements without growth. This behavior cannot be broadly guaranteed,
+   * but it is observed to be true for OpenJDK 1.7. It also can't be guaranteed that the method
+   * isn't inadvertently <i>oversizing</i> the returned map.
+   *
+   * @param expectedSize the number of entries you expect to add to the returned map
+   * @return a new, empty {@code HashMap} with enough capacity to hold {@code expectedSize} entries
+   * without resizing
+   * @throws IllegalArgumentException if {@code expectedSize} is negative
+   */
+  public static <K, V> HashMap<K, V> newHashMapWithExpectedSize(int expectedSize) {
+    return new HashMap<>(capacity(expectedSize));
+  }
+
+  /**
+   * Returns a capacity that is sufficient to keep the map from being resized as long as it grows no
+   * larger than expectedSize and the load factor is >= its default (0.75).
+   */
+  private static int capacity(int expectedSize) {
+    if (expectedSize < 3) {
+      checkNonnegative(expectedSize, "expectedSize");
+      return expectedSize + 1;
+    }
+    if (expectedSize < MAX_POWER_OF_TWO) {
+      // This is the calculation used in JDK8 to resize when a putAll
+      // happens; it seems to be the most conservative calculation we
+      // can make.  0.75 is the default load factor.
+      return (int) ((float) expectedSize / 0.75F + 1.0F);
+    }
+    return Integer.MAX_VALUE; // any large value
+  }
+
+  private static int checkNonnegative(int value, String name) {
+    if (value < 0) {
+      throw new IllegalArgumentException(name + " cannot be negative but was: " + value);
+    }
+    return value;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXDeviceUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXDeviceUtils.java
new file mode 100644
index 0000000..e6ff59f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXDeviceUtils.java
@@ -0,0 +1,54 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.content.Context;
+import android.os.Build;
+
+public class WXDeviceUtils {
+
+
+    public static boolean isAutoResize(Context context){
+        if(context == null){
+            return false;
+        }
+        return isMateX(context) || isGalaxyFold(context);
+    }
+
+    /**
+     * Mate X
+     * */
+    public static boolean isMateX(Context context) {
+        return "HUAWEI".equalsIgnoreCase(Build.BRAND) && ("unknownRLI".equalsIgnoreCase(Build.DEVICE) || ("HWTAH".equalsIgnoreCase(Build.DEVICE)));
+    }
+
+
+    /**
+     * Galaxy Fopld
+     * */
+    public static boolean isGalaxyFold(Context context) {
+
+        if("samsung".equalsIgnoreCase(Build.BRAND) && "SM-F9000".equalsIgnoreCase(Build.MODEL)) {
+            return true;
+        }
+
+        return false;
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXDomUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXDomUtils.java
new file mode 100644
index 0000000..2d26a27
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXDomUtils.java
@@ -0,0 +1,105 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+package org.apache.weex.utils;
+
+import android.support.annotation.NonNull;
+import org.apache.weex.dom.CSSConstants;
+import org.apache.weex.dom.CSSShorthand.EDGE;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.dom.CSSShorthand;
+
+public class WXDomUtils {
+
+  /**
+   * Get the content width of the dom.
+   * @return the width of the dom that excludes left-padding, left-border-width,
+   * right-border-width and right-padding.
+   */
+  public static float getContentWidth(WXComponent component) {
+    float rawWidth = component.getLayoutWidth();
+    float leftPadding, rightPadding, leftBorder, rightBorder;
+    CSSShorthand padding = component.getPadding();
+    CSSShorthand border = component.getBorder();
+
+    if (!CSSConstants.isUndefined((leftPadding = padding.get(CSSShorthand.EDGE.LEFT)))) {
+      rawWidth -= leftPadding;
+    }
+    if (!CSSConstants.isUndefined((rightPadding = padding.get(CSSShorthand.EDGE.RIGHT)))) {
+      rawWidth -= rightPadding;
+    }
+
+    if (!CSSConstants.isUndefined(leftBorder = border.get(CSSShorthand.EDGE.LEFT))) {
+      rawWidth -= leftBorder;
+    }
+    if (!CSSConstants.isUndefined(rightBorder = border.get(CSSShorthand.EDGE.RIGHT))) {
+      rawWidth -= rightBorder;
+    }
+    return rawWidth;
+  }
+
+  /**
+   * Get the content height of the dom.
+   * @return the height of the dom that excludes top-padding, top-border-width, bottom-padding
+   * and bottom-border-width.
+   */
+  public static float getContentHeight(WXComponent component) {
+    float rawHeight = component.getLayoutHeight();
+    float topPadding, bottomPadding, topBorder, bottomBorder;
+    CSSShorthand padding = component.getPadding();
+    CSSShorthand border = component.getBorder();
+
+    if (!CSSConstants.isUndefined((topPadding = padding.get(CSSShorthand.EDGE.TOP)))) {
+      rawHeight -= topPadding;
+    }
+    if (!CSSConstants.isUndefined((bottomPadding = padding.get(CSSShorthand.EDGE.BOTTOM)))) {
+      rawHeight -= bottomPadding;
+    }
+
+    if (!CSSConstants.isUndefined(topBorder = border.get(CSSShorthand.EDGE.TOP))) {
+      rawHeight -= topBorder;
+    }
+    if (!CSSConstants.isUndefined(bottomBorder = border.get(CSSShorthand.EDGE.BOTTOM))) {
+      rawHeight -= bottomBorder;
+    }
+    return rawHeight;
+  }
+
+  public static float getContentWidth(
+      @NonNull CSSShorthand padding,
+      @NonNull CSSShorthand border,
+      float layoutWidth){
+    float leftPadding, rightPadding, leftBorder, rightBorder;
+
+    if (!CSSConstants.isUndefined((leftPadding = padding.get(EDGE.LEFT)))) {
+      layoutWidth -= leftPadding;
+    }
+    if (!CSSConstants.isUndefined((rightPadding = padding.get(EDGE.RIGHT)))) {
+      layoutWidth -= rightPadding;
+    }
+
+    if (!CSSConstants.isUndefined(leftBorder = border.get(EDGE.LEFT))) {
+      layoutWidth -= leftBorder;
+    }
+    if (!CSSConstants.isUndefined(rightBorder = border.get(EDGE.RIGHT))) {
+      layoutWidth -= rightBorder;
+    }
+    return layoutWidth;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXExceptionUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXExceptionUtils.java
new file mode 100644
index 0000000..84705f2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXExceptionUtils.java
@@ -0,0 +1,240 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.Comparator;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Map.Entry;
+import java.util.Set;
+import java.util.concurrent.CopyOnWriteArraySet;
+
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.adapter.IWXJSExceptionAdapter;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXErrorCode.ErrorGroup;
+import org.apache.weex.common.WXJSExceptionInfo;
+import org.apache.weex.common.WXPerformance;
+import org.apache.weex.performance.WXAnalyzerDataTransfer;
+import org.apache.weex.performance.WXInstanceApm;
+import org.apache.weex.performance.WXStateRecord;
+
+/**
+ * Created on 2017/10/13.
+ */
+
+public class WXExceptionUtils {
+
+    private static Set<String> sGlobalExceptionRecord = new CopyOnWriteArraySet<String>();
+
+	/**
+	 * degradeUrl for degrade case
+	 */
+	public static String degradeUrl = "BundleUrlDefaultDegradeUrl";
+
+	private static boolean checkNeedReportCauseRepeat(String instanceId, WXErrorCode errCode,String exception){
+
+	    if (TextUtils.isEmpty(exception)){
+	        return true;
+        }
+
+        if (null != errCode && errCode.getErrorGroup() != ErrorGroup.JS){
+	        return true;
+        }
+
+        if (TextUtils.isEmpty(instanceId)){
+            instanceId = "instanceIdNull";
+        }
+
+        String targetException = exception.length() > 200 ?exception.substring(0,200) : exception;
+        Set<String> recordExceptionHistory= null;
+
+        WXSDKInstance instance =  WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
+        if (null == instance){
+            recordExceptionHistory = sGlobalExceptionRecord;
+        }else {
+            recordExceptionHistory =  instance.getApmForInstance().exceptionRecord;
+        }
+
+        if (null == recordExceptionHistory){
+            return true;
+        }
+
+        if (recordExceptionHistory.contains(targetException)){
+            return false;
+        }
+        recordExceptionHistory.add(targetException);
+        return true;
+    }
+
+
+
+
+	/**
+	 * commitCriticalExceptionRT eg:JsRuntime Exception or JsFramework Init Exception
+	 * @param instanceId
+	 * @param errCode
+	 * @param function
+	 * @param exception
+	 * @param extParams
+	 */
+	public static void commitCriticalExceptionRT(@Nullable final String instanceId,
+												 @Nullable final WXErrorCode errCode,
+												 @Nullable final String function,
+												 @Nullable final String exception,
+												 @Nullable final Map<String,String> extParams ) {
+
+        try {
+            WXLogUtils.e("weex","commitCriticalExceptionRT :"+errCode+"exception"+exception);
+            WXStateRecord.getInstance().recordException(instanceId,exception);
+            IWXConfigAdapter configAdapter = WXSDKManager.getInstance().getWxConfigAdapter();
+            boolean doCheck = true;
+            if (null != configAdapter){
+                String value = configAdapter.getConfig("wxapm","check_repeat_report","true");
+                doCheck = "true".equalsIgnoreCase(value);
+            }
+            boolean doReport =true;
+            if (doCheck){
+                doReport = checkNeedReportCauseRepeat(instanceId,errCode,exception);
+            }
+            if (!doReport){
+                return;
+            }
+        }catch (Throwable e){
+            e.printStackTrace();
+        }
+
+
+		commitCriticalExceptionWithDefaultUrl(
+		    "BundleUrlDefault",
+            instanceId,
+            errCode,
+            function,
+            exception,
+            extParams
+        );
+	}
+
+    public static void commitCriticalExceptionWithDefaultUrl(
+        @Nullable final String defaultUrl,
+        @Nullable final String instanceId,
+        @Nullable final WXErrorCode errCode,
+        @Nullable final String function,
+        @Nullable final String exception,
+        @Nullable final Map<String,String> extParams
+    ){
+        IWXJSExceptionAdapter adapter = WXSDKManager.getInstance().getIWXJSExceptionAdapter();
+        WXSDKInstance instance = null;
+        WXJSExceptionInfo exceptionCommit;
+        String bundleUrlCommit = TextUtils.isEmpty(defaultUrl)?"BundleUrlDefault":defaultUrl;
+        String instanceIdCommit = "InstanceIdDefalut";
+        String exceptionMsgCommit = exception;
+        Map<String, String> commitMap = extParams;
+        if (null == commitMap){
+            commitMap = new HashMap<>();
+        }
+        commitMap.put("wxSdkInitStartTime", String.valueOf(WXEnvironment.sSDKInitStart));
+        commitMap.put("wxSDKInitCostTime", String.valueOf(WXEnvironment.sSDKInitTime));
+        commitMap.put("wxSDKCurExceptionTime", String.valueOf(System.currentTimeMillis()));
+        commitMap.put("wxUseRuntimeApi",String.valueOf(WXEnvironment.sUseRunTimeApi));
+        if (!TextUtils.isEmpty(instanceId)) {
+            instanceIdCommit = instanceId;
+            instance = WXSDKManager.getInstance().getAllInstanceMap().get(instanceId);
+
+            if (null != instance) {
+                bundleUrlCommit = instance.getApmForInstance().reportPageName;
+                Object loadLength = instance.getApmForInstance().extInfo.get(WXInstanceApm.VALUE_BUNDLE_LOAD_LENGTH);
+                String loadLengthStr = (loadLength instanceof Integer)?String.valueOf(loadLength):"unknownLength";
+                commitMap.put(WXInstanceApm.VALUE_BUNDLE_LOAD_LENGTH,loadLengthStr);
+                commitMap.put("templateInfo",instance.getTemplateInfo());
+                if (TextUtils.isEmpty(bundleUrlCommit) || bundleUrlCommit.equals(WXPerformance.DEFAULT)) {
+                    if (!TextUtils.equals(degradeUrl, "BundleUrlDefaultDegradeUrl")) {
+                        bundleUrlCommit = degradeUrl;
+                    } else
+                        bundleUrlCommit = WXSDKInstance.requestUrl;
+                }
+                for (Map.Entry<String,String> entry: instance.getContainerInfo().entrySet()){
+                    commitMap.put(entry.getKey(),entry.getValue());
+                }
+                commitMap.put("wxStageList",convertStageToStr(instance));
+                String bundleTemplate = instance.getTemplate();
+                if (null == bundleTemplate){
+                    bundleTemplate = "has recycle by gc";
+                }else {
+                    int length = bundleTemplate.length();
+                    bundleTemplate = bundleTemplate.substring(0,Math.min(length,300));
+                }
+                commitMap.put("wxTemplateOfBundle",bundleTemplate);
+
+                Long pageStartTime = instance.getApmForInstance().stageMap.get(WXInstanceApm.KEY_PAGE_STAGES_DOWN_BUNDLE_START);
+                if (null == pageStartTime){
+                    pageStartTime = instance.getApmForInstance().stageMap.get(WXInstanceApm.KEY_PAGE_STAGES_RENDER_ORGIGIN);
+                }
+                if (null != pageStartTime){
+                    commitMap.put("wxUseTime", String.valueOf(WXUtils.getFixUnixTime() - pageStartTime));
+                }
+            }
+        } else {//instance is null for instance id is null
+            if (commitMap.size() > 0) {
+                bundleUrlCommit = TextUtils.isEmpty(commitMap.get("weexUrl")) ? commitMap.get("weexUrl")
+                    : commitMap.get("bundleUrl");
+            }
+        }
+
+        String illegalValue = commitMap.get("errorCode");
+        if (null != illegalValue && illegalValue.length()>200){
+            commitMap.remove("errorCode");
+        }
+
+        exceptionCommit = new WXJSExceptionInfo(instanceIdCommit, bundleUrlCommit, errCode, function, exceptionMsgCommit, commitMap);
+        if (adapter != null) {
+            adapter.onJSException(exceptionCommit);
+        }
+
+        WXAnalyzerDataTransfer.transferError(exceptionCommit, instanceId);
+    }
+
+    private static String convertStageToStr(WXSDKInstance instance) {
+        if (null == instance || null == instance.getApmForInstance() || instance.getApmForInstance().stageMap.isEmpty()) {
+            return "noStageRecord";
+        }
+        List<Entry<String, Long>> list = new ArrayList<>(instance.getApmForInstance().stageMap.entrySet());
+        Collections.sort(list, new Comparator<Entry<String, Long>>() {
+            @Override
+            public int compare(Entry<String, Long> o1, Entry<String, Long> o2) {
+                return (int)(o1.getValue() - o2.getValue());
+            }
+        });
+
+        StringBuilder builder = new StringBuilder();
+        for (Map.Entry<String, Long> entry : list) {
+            builder.append(entry.getKey()).append(':').append(entry.getValue()).append("->");
+        }
+        return builder.toString();
+    }
+
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXFileUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXFileUtils.java
new file mode 100644
index 0000000..6b1e941
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXFileUtils.java
@@ -0,0 +1,304 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.content.Context;
+import android.text.TextUtils;
+import android.util.Base64;
+
+import java.io.BufferedInputStream;
+import java.io.BufferedReader;
+import java.io.Closeable;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.UnsupportedEncodingException;
+import java.math.BigInteger;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.util.Locale;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipFile;
+import java.util.zip.ZipInputStream;
+import org.apache.weex.WXEnvironment;
+
+import static org.apache.weex.utils.WXSoInstallMgrSdk._cpuType;
+
+public class WXFileUtils {
+
+  /**
+   * Load file in device directory, if not exist, load from asset directory.
+   * @param path FilePath
+   * @param context Weex Context
+   * @return the Content of the file
+   */
+  public static String loadFileOrAsset(String path, Context context) {
+    if (!TextUtils.isEmpty(path)) {
+      File file = new File(path);
+      if (file.exists()) {
+        try {
+          FileInputStream fis = new FileInputStream(file);
+          return readStreamToString(fis);
+        } catch (FileNotFoundException e) {
+          e.printStackTrace();
+        }
+      } else {
+        return loadAsset(path, context);
+      }
+    }
+    return "";
+  }
+
+  /**
+   * Load file in asset directory.
+   * @param path FilePath
+   * @param context Weex Context
+   * @return the Content of the file
+   */
+  public static String loadAsset(String path, Context context) {
+    if (context == null || TextUtils.isEmpty(path)) {
+      return null;
+    }
+    InputStream inputStream = null;
+    try {
+      inputStream = context.getAssets().open(path);
+      return readStreamToString(inputStream);
+    } catch (IOException e) {
+      e.printStackTrace();
+    }
+    return "";
+  }
+
+  public static String readStreamToString(InputStream inputStream) {
+    BufferedReader bufferedReader = null;
+    try {
+      StringBuilder builder = new StringBuilder(inputStream.available() + 10);
+      bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
+      char[] data = new char[4096];
+      int len = -1;
+      while ((len = bufferedReader.read(data)) > 0) {
+        builder.append(data, 0, len);
+      }
+
+      return builder.toString();
+    } catch (IOException e) {
+      e.printStackTrace();
+      WXLogUtils.e("", e);
+    } finally {
+      try {
+        if (bufferedReader != null)
+          bufferedReader.close();
+      } catch (IOException e) {
+        WXLogUtils.e("WXFileUtils loadAsset: ", e);
+      }
+      try {
+        if (inputStream != null)
+          inputStream.close();
+      } catch (IOException e) {
+        WXLogUtils.e("WXFileUtils loadAsset: ", e);
+      }
+    }
+
+    return "";
+  }
+
+  public static byte[] readBytesFromAssets(String path, Context context) {
+    if (context == null || TextUtils.isEmpty(path)) {
+      return null;
+    }
+    InputStream inputStream = null;
+    try {
+      inputStream = context.getAssets().open(path);
+      byte[] data = new byte[4096];
+      int length = inputStream.read(data);
+      byte[] result = new byte[length];
+      System.arraycopy(data, 0, result, 0, length);
+      return result;
+    } catch (IOException e) {
+      e.printStackTrace();
+    }
+    return null;
+  }
+
+  public static boolean saveFile(String path, byte[] content, Context context) {
+    if (TextUtils.isEmpty(path) || content == null || context == null) {
+      return false;
+    }
+    FileOutputStream outStream = null;
+    try {
+      outStream = new FileOutputStream(path);
+      outStream.write(content);
+      return true;
+    } catch (Exception e) {
+      WXLogUtils.e("WXFileUtils saveFile: " + WXLogUtils.getStackTrace(e));
+    } finally {
+      if (outStream != null) {
+        try {
+          outStream.close();
+        } catch (IOException e) {
+          e.printStackTrace();
+        }
+      }
+    }
+    return false;
+  }
+
+  public static String md5(String  template){
+    try {
+      if(template == null){
+        return  "";
+      }
+      return  md5(template.getBytes("UTF-8"));
+    } catch (UnsupportedEncodingException e) {
+      return  "";
+    }
+  }
+
+  public static String md5(byte[] bts){
+    try {
+      MessageDigest digest = MessageDigest.getInstance("MD5");
+      digest.update(bts);
+      BigInteger bigInt = new BigInteger(1, digest.digest());
+      return  bigInt.toString(16);
+    } catch (NoSuchAlgorithmException e) {;
+      return  "";
+    }
+  }
+
+  public static String base64Md5(String  template){
+    try {
+      if(template == null){
+        return  "";
+      }
+      return  base64Md5(template.getBytes("UTF-8"));
+    } catch (UnsupportedEncodingException e) {
+      return  "";
+    }
+  }
+
+  public static String base64Md5(byte[] bts){
+    try {
+      MessageDigest digest = MessageDigest.getInstance("MD5");
+      digest.update(bts);
+      return Base64.encodeToString(digest.digest(), Base64.NO_WRAP);
+    } catch (NoSuchAlgorithmException e) {;
+      return  "";
+    }
+  }
+
+  public static void extractSo(String apkFile, String path) throws IOException {
+    ZipFile zip = new ZipFile(apkFile);
+    InputStream zipInputStream = new BufferedInputStream(new FileInputStream(apkFile));
+    ZipInputStream zin = new ZipInputStream(zipInputStream);
+    ZipEntry zipEntry;
+    while ((zipEntry = zin.getNextEntry()) != null) {
+      if(zipEntry.isDirectory()){
+        continue;
+      }
+      if(zipEntry.getName().contains("lib/" + _cpuType() + "/") &&
+              (zipEntry.getName().contains("weex") || zipEntry.getName().equals(
+                  String.format(Locale.ENGLISH, "lib%s.so", WXEnvironment.CORE_JSC_SO_NAME)))){
+        String[] fileNames = zipEntry.getName().split("/");
+        String fileName = fileNames[fileNames.length - 1];
+        InputStream inputStream = zip.getInputStream(zipEntry);
+        byte[] data = new byte[1024];
+        File zipFile = new File(path + "/" + fileName);
+        if(zipFile.exists()) {
+          zipFile.delete();
+        }
+
+        zipFile.createNewFile();
+
+        FileOutputStream outputStream =new FileOutputStream(zipFile);
+        while (inputStream.read(data) != -1) {
+          outputStream.write(data);
+        }
+        outputStream.close();
+
+      }
+    }
+    zin.closeEntry();
+  }
+
+  public static void copyFile(File oldFile, File newFile) {
+    FileInputStream inputStream = null;
+    FileOutputStream outputStream = null;
+    try {
+      inputStream = new FileInputStream(oldFile);
+      byte[] data = new byte[1024];
+      outputStream = new FileOutputStream(newFile);
+      while (inputStream.read(data) != -1) {
+        outputStream.write(data);
+      }
+      inputStream.close();
+      outputStream.close();
+    } catch (Exception e) {
+      WXLogUtils.e("copyFile " + e.getMessage() + ": " + oldFile.getAbsolutePath() + ": " + newFile.getAbsolutePath());
+      if (inputStream != null) {
+        try {
+          inputStream.close();
+        } catch (IOException e1) {
+          e1.printStackTrace();
+        }
+      }
+
+      if (outputStream != null) {
+        try {
+          outputStream.close();
+        } catch (IOException e1) {
+          e1.printStackTrace();
+        }
+      }
+    }
+  }
+
+  public static void copyFileWithException(File oldFile,File newFile ) throws Exception{
+    FileInputStream inputStream = null;
+    FileOutputStream outputStream = null;
+    try {
+      inputStream = new FileInputStream(oldFile);
+      byte[] data = new byte[1024];
+      outputStream = new FileOutputStream(newFile);
+      while (inputStream.read(data) != -1) {
+        outputStream.write(data);
+      }
+    }catch (Exception e){
+      throw e;
+    }finally {
+      closeIo(inputStream);
+      closeIo(outputStream);
+    }
+  }
+
+  public static void closeIo(Closeable c){
+    if (null == c){
+      return;
+    }
+    try {
+      c.close();
+    }catch (Throwable e){
+      e.printStackTrace();
+    }
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXInterception.java b/android/sdk/src/main/java/org/apache/weex/utils/WXInterception.java
new file mode 100644
index 0000000..04bdcab
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXInterception.java
@@ -0,0 +1,88 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import java.lang.reflect.InvocationHandler;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.lang.reflect.Proxy;
+
+public class WXInterception {
+
+  private WXInterception() {
+  }
+
+  @SuppressWarnings("unchecked")
+  public static <T> T proxy(final Object delegatee, final Class<T> interface_class, final InterceptionHandler<T> handler) throws IllegalArgumentException {
+    if (delegatee instanceof Intercepted) {
+      return (T) delegatee;
+    }
+    handler.setDelegate((T) delegatee);
+    return (T) Proxy.newProxyInstance(WXInterception.class.getClassLoader(), new Class<?>[]{interface_class, Intercepted.class}, handler);
+  }
+
+  @SuppressWarnings("unchecked")
+  public static <T> T proxy(final Object delegatee, final InterceptionHandler<T> handler, final Class<?>... interfaces) throws IllegalArgumentException {
+    //if (Proxy.isProxyClass(delegatee.getClass())) return (T) delegatee;
+    handler.setDelegate((T) delegatee);
+    return (T) Proxy.newProxyInstance(WXInterception.class.getClassLoader(), interfaces, handler);
+  }
+
+  private interface Intercepted {
+
+  }        // A mark to identify our proxy class
+
+  /**
+   * Derive this class and override {@link #invoke(Object, Method, Object[])} to implement an
+   * interception handler.
+   */
+  public abstract static class InterceptionHandler<T> implements InvocationHandler {
+
+    private T mDelegate;
+
+    /**
+     * Derived class should override this method and call <code>super.invoke(...)</code> to delegate the
+     * procedure to original delegate instance if needed.
+     *
+     * @param proxy is ignored, instead the actual delegate instance will be used to invoke this method on.
+     */
+    @Override
+    public Object invoke(final Object proxy, final Method method, final Object[] args) throws Throwable {
+      try {
+        return method.invoke(delegate(), args);
+      } catch (IllegalArgumentException e) {/* Should never happen */
+        WXLogUtils.e("", e);
+        return null;
+      } catch (IllegalAccessException e) {/* Should never happen */
+        WXLogUtils.e("", e);
+        return null;
+      } catch (InvocationTargetException e) {
+        throw e.getTargetException();
+      }
+    }
+
+    protected T delegate() {
+      return mDelegate;
+    }
+
+    void setDelegate(final T delegate) {
+      mDelegate = delegate;
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXJsonUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXJsonUtils.java
new file mode 100644
index 0000000..629879b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXJsonUtils.java
@@ -0,0 +1,93 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+
+import android.support.annotation.NonNull;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONObject;
+import com.alibaba.fastjson.serializer.SerializerFeature;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.common.WXRuntimeException;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+/**
+ * Tool for parse JSON
+ */
+public class WXJsonUtils {
+
+
+  public @NonNull static <T> List<T> getList(String json, Class<T> clazz) {
+    List<T> result = null;
+    try {
+      result = JSONObject.parseArray(json, clazz);
+    } catch (Exception e) {
+      e.printStackTrace();
+      result = new ArrayList<>();
+    }
+    return result;
+  }
+
+  public @NonNull static String fromObjectToJSONString(Object obj, boolean WriteNonStringKeyAsString){
+    try {
+      if(WriteNonStringKeyAsString) {
+        return JSON.toJSONString(obj, SerializerFeature.WriteNonStringKeyAsString);
+      }else {
+        return JSON.toJSONString(obj);
+      }
+    }catch(Exception e){
+      if(WXEnvironment.isApkDebugable()){
+        throw new WXRuntimeException("fromObjectToJSONString parse error!");
+      }
+      WXLogUtils.e("fromObjectToJSONString error:", e);
+      return "{}";
+    }
+  }
+  public @NonNull static String fromObjectToJSONString(Object obj) {
+
+    return fromObjectToJSONString(obj,false);
+  }
+
+  /**
+   * Put the map info in the JSONObject to the container.
+   * This method check for null value in the JSONObject
+   * and won't put the null value in the container.
+   * As {@link ConcurrentHashMap#putAll(Map)} will throws an exception if the key or value to
+   * be put is null, it is necessary to invoke this method as replacement of
+   * {@link Map#putAll(Map)}
+   * @param container container to contain the JSONObject.
+   * @param rawValue jsonObject, contains map info.
+   */
+  public static void putAll(Map<String, Object> container, JSONObject rawValue) {
+    String key;
+    Object value;
+    for (Map.Entry<String, Object> entry : rawValue.entrySet()) {
+      key = entry.getKey();
+      value = entry.getValue();
+      if (key != null && value != null) {
+        container.put(key, value);
+      }
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXLogUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXLogUtils.java
new file mode 100644
index 0000000..6e21f8f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXLogUtils.java
@@ -0,0 +1,338 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.support.annotation.Nullable;
+import android.text.TextUtils;
+import android.util.Log;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.performance.WXStateRecord;
+
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.io.StringWriter;
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+
+public class WXLogUtils {
+
+  public static final String WEEX_TAG = "weex";
+  public static final String WEEX_PERF_TAG = "weex_perf";
+
+  private static final String CLAZZ_NAME_LOG_UTIL = "com.taobao.weex.devtools.common.LogUtil";
+
+  private static StringBuilder builder = new StringBuilder(50);
+  private static HashMap<String, Class> clazzMaps = new HashMap<>(2);
+  private static List<JsLogWatcher> jsLogWatcherList;
+  private static LogWatcher sLogWatcher;
+
+  static {
+    clazzMaps.put(CLAZZ_NAME_LOG_UTIL, loadClass(CLAZZ_NAME_LOG_UTIL));
+    jsLogWatcherList = new ArrayList<>();
+  }
+
+  private static Class loadClass(String clazzName) {
+    Class<?> clazz = null;
+    try {
+      clazz = Class.forName(clazzName);
+      if (clazz != null) {
+        clazzMaps.put(clazzName, clazz);
+      }
+    } catch (ClassNotFoundException e) {
+      // ignore
+    }
+    return clazz;
+  }
+
+  public static void renderPerformanceLog(String type, long time) {
+    if (WXEnvironment.isApkDebugable() || WXEnvironment.isPerf()) {
+//      builder.setLength(0);
+//      builder.append("[render time]").append(type).append(":").append(time);
+//      Log.d(WEEX_PERF_TAG, builder.substring(0));
+//      writeConsoleLog("debug", builder.substring(0));
+    }
+  }
+
+  private static void log(String tag, String msg, LogLevel level){
+    if(TextUtils.isEmpty(msg) || TextUtils.isEmpty(tag) || level == null || TextUtils.isEmpty(level.getName())){
+      return;
+    }
+    if (level == LogLevel.ERROR && !TextUtils.isEmpty(msg) && msg.contains("IPCException")){
+      WXStateRecord.getInstance().recordIPCException("ipc",msg);
+    }
+
+    if(sLogWatcher !=null){
+      sLogWatcher.onLog(level.getName(), tag, msg);
+    }
+
+    if (WXEnvironment.isApkDebugable()) {
+      if(level.getValue() - WXEnvironment.sLogLevel.getValue() >= 0) {
+        Log.println(level.getPriority(), tag, msg);
+        writeConsoleLog(level.getName(), msg);
+      }
+      // if not debug level then print log
+    }else {
+      if(level.getValue() - LogLevel.WARN.getValue() >=0 && level.getValue() - WXEnvironment.sLogLevel.getValue() >= 0){
+        Log.println(level.getPriority(),tag, msg);
+      }
+    }
+  }
+
+  public static void v(String msg) {
+    v(WEEX_TAG,msg);
+  }
+
+  public static void d(String msg) {
+    d(WEEX_TAG,msg);
+  }
+
+  public static void d(String tag, byte[] msg) {
+    d(tag, new String(msg));
+  }
+
+  public static void i(String msg) {
+    i(WEEX_TAG,msg);
+  }
+
+  public static void i(String tag, byte[] msg) {
+    i(tag, new String(msg));
+  }
+
+  public static void info(String msg) {
+    i(WEEX_TAG, msg);
+  }
+
+  public static void w(String msg) {
+    w(WEEX_TAG, msg);
+  }
+
+  public static void w(String tag, byte[] msg) {
+    w(tag, new String(msg));
+  }
+
+  public static void e(String msg) {
+    e(WEEX_TAG,msg);
+  }
+
+  public static void e(String tag, byte[] msg) {
+    e(tag, new String(msg));
+  }
+
+  public static void performance(String instanceId, byte[]msg) {
+//    String s = new String(msg);
+//    if(!TextUtils.isEmpty(instanceId)) {
+//      WXSDKInstance sdkInstance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+//      if(sdkInstance != null) {
+//        int i = s.indexOf(",");
+//        if(i >=0 && i < s.length()) {
+//          String substring = s.substring(s.indexOf(",") + 1);
+//          LogDetail logDetail = JSON.parseObject(substring,LogDetail.class);
+//          sdkInstance.mTimeCalculator.addLog(logDetail);
+//        }
+//      }
+//    }
+//    Log.e(TIMELINE_TAG, "from WeexCore" + s);
+  }
+
+  public static void wtf(String msg){
+    wtf(WEEX_TAG, msg);
+  }
+
+  public static void d(String tag, String msg) {
+
+    if(!TextUtils.isEmpty(tag) && !TextUtils.isEmpty(msg)){
+      log(tag, msg, LogLevel.DEBUG);
+
+      if(WXEnvironment.isApkDebugable()){//sLogLevel in debug mode is "LogLevel.DEBUG"
+        if ("jsLog".equals(tag) && jsLogWatcherList != null && jsLogWatcherList.size() > 0) {
+          for (JsLogWatcher jsLogWatcher : jsLogWatcherList) {
+            if (msg.endsWith("__DEBUG")) {
+              jsLogWatcher.onJsLog(Log.DEBUG, msg.replace("__DEBUG", ""));
+            } else if (msg.endsWith("__INFO")) {
+              jsLogWatcher.onJsLog(Log.DEBUG, msg.replace("__INFO", ""));
+            } else if (msg.endsWith("__WARN")) {
+              jsLogWatcher.onJsLog(Log.DEBUG, msg.replace("__WARN", ""));
+            } else if (msg.endsWith("__ERROR")) {
+              jsLogWatcher.onJsLog(Log.DEBUG, msg.replace("__ERROR", ""));
+            } else {
+              jsLogWatcher.onJsLog(Log.DEBUG, msg);
+            }
+          }
+        }
+      }
+    }
+  }
+
+  private static LogLevel getLogLevel(String level) {
+    switch (level.trim()){
+      case "__ERROR":
+        return LogLevel.ERROR;
+      case "__WARN":
+        return LogLevel.WARN;
+      case "__INFO":
+        return LogLevel.INFO;
+      case "__LOG":
+        return LogLevel.INFO;
+      case "__DEBUG":
+        return LogLevel.DEBUG;
+    }
+    return LogLevel.DEBUG;
+  }
+
+  public static void i(String tag, String msg) {
+    log(tag, msg,LogLevel.INFO);
+  }
+
+  public static void v(String tag, String msg) {
+    log(tag, msg,LogLevel.VERBOSE);
+  }
+
+  public static void w(String tag, String msg) {
+    log(tag, msg,LogLevel.WARN);
+  }
+
+  public static void e(String tag, String msg) {
+    log(tag, msg,LogLevel.ERROR);
+  }
+
+  public static void wtf(String tag, String msg){
+    log(tag, msg, LogLevel.WTF);
+  }
+
+  /**
+   * 'p' for 'Performance', use {@link #WEEX_PERF_TAG}
+   * @param msg
+   */
+  public static void p(String msg) {
+    d(WEEX_PERF_TAG,msg);
+  }
+
+  public static void d(String prefix, Throwable e) {
+    if (WXEnvironment.isApkDebugable()) {
+      d(prefix + getStackTrace(e));
+    }
+  }
+
+  public static void i(String prefix, Throwable e) {
+    if (WXEnvironment.isApkDebugable()) {
+      info(prefix + getStackTrace(e));
+    }
+  }
+
+  public static void v(String prefix, Throwable e) {
+    if (WXEnvironment.isApkDebugable()) {
+      v(prefix + getStackTrace(e));
+    }
+  }
+
+  public static void w(String prefix, Throwable e) {
+    w(prefix + getStackTrace(e));
+
+  }
+
+  public static void e(String prefix, Throwable e) {
+    e(prefix + getStackTrace(e));
+
+  }
+
+  public static void wtf(String prefix, Throwable e){
+    if (WXEnvironment.isApkDebugable()) {
+      wtf(prefix + getStackTrace(e));
+    }
+  }
+
+  /**
+   * 'p' for 'Performance', use {@link #WEEX_PERF_TAG}
+   */
+  public static void p(String prefix, Throwable e) {
+    if (WXEnvironment.isApkDebugable()) {
+      p(prefix + getStackTrace(e));
+    }
+  }
+
+  public static void eTag(String tag, Throwable e) {
+    if (WXEnvironment.isApkDebugable()) {
+      e(tag, getStackTrace(e));
+    }
+  }
+
+  public static String getStackTrace(@Nullable Throwable e) {
+    if (e == null) {
+      return "";
+    }
+    StringWriter sw = null;
+    PrintWriter pw = null;
+    try {
+      sw = new StringWriter();
+      pw = new PrintWriter(sw);
+      e.printStackTrace(pw);
+      pw.flush();
+      sw.flush();
+    } finally {
+      if (sw != null) {
+        try {
+          sw.close();
+        } catch (IOException e1) {
+          e1.printStackTrace();
+        }
+      }
+      if (pw != null) {
+        pw.close();
+      }
+    }
+    return sw.toString();
+  }
+
+
+
+  private static void writeConsoleLog(String level, String message) {
+    if (WXEnvironment.isApkDebugable()) {
+      try {
+        Class<?> clazz = clazzMaps.get(CLAZZ_NAME_LOG_UTIL);
+        if (clazz != null) {
+          Method m = clazz.getMethod("log", String.class, String.class);
+          m.invoke(clazz, level, message);
+        }
+      } catch (Exception e) {
+        Log.d(WEEX_TAG, "LogUtil not found!");
+      }
+    }
+  }
+
+  public static void setJsLogWatcher(JsLogWatcher watcher) {
+    if (!jsLogWatcherList.contains(watcher)) {
+      jsLogWatcherList.add(watcher);
+    }
+  }
+
+  public static void setLogWatcher(LogWatcher watcher) {
+    sLogWatcher = watcher;
+  }
+
+  public interface JsLogWatcher {
+    void onJsLog(int level, String log);
+  }
+
+  public interface LogWatcher {
+    void onLog(String level, String tag, String msg);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXMap.java b/android/sdk/src/main/java/org/apache/weex/utils/WXMap.java
new file mode 100644
index 0000000..00b2f15
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXMap.java
@@ -0,0 +1,29 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import java.io.Serializable;
+import java.util.HashMap;
+
+public class WXMap extends HashMap<String, String> implements Serializable {
+
+  public String put(String key, byte[] value) {
+    return super.put(key, new String(value));
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXReflectionUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXReflectionUtils.java
new file mode 100644
index 0000000..4c9126f
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXReflectionUtils.java
@@ -0,0 +1,142 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.text.TextUtils;
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+
+import java.lang.reflect.Field;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Type;
+import java.math.BigDecimal;
+
+public class WXReflectionUtils {
+
+  public static Object parseArgument(Type paramClazz, Object value) {
+    if(value != null){
+      if(value.getClass() == paramClazz){
+        return  value;
+      }
+      if(paramClazz instanceof  Class){
+        if( ((Class<?>) paramClazz).isAssignableFrom(value.getClass()))   {
+          return value;
+        }
+      }
+    }
+    if (paramClazz == String.class) {
+      return value instanceof String ? value : JSON.toJSONString(value);
+    } else if (paramClazz == int.class) {
+      return value.getClass().isAssignableFrom(int.class) ? value : WXUtils.getInt(value);
+    } else if (paramClazz == long.class) {
+      return value.getClass().isAssignableFrom(long.class) ? value : WXUtils.getLong(value);
+    } else if (paramClazz == double.class) {
+      return value.getClass().isAssignableFrom(double.class) ? value : WXUtils.getDouble(value);
+    } else if (paramClazz == float.class) {
+      return value.getClass().isAssignableFrom(float.class) ? value : WXUtils.getFloat(value);
+    } else if (paramClazz == JSONArray.class && value != null && value.getClass() == JSONArray.class) {
+      return  value;
+    } else if (paramClazz == JSONObject.class && value != null && value.getClass() == JSONObject.class) {
+      return  value;
+    } else {
+      return JSON.parseObject(value instanceof String ? (String) value : JSON.toJSONString(value), paramClazz);
+    }
+  }
+
+
+  public static void setValue(Object obj, String fieldName, Object value) {
+    if (obj == null || TextUtils.isEmpty(fieldName)) {
+      return;
+    }
+
+    try {
+      // Field field = obj.getClass().getDeclaredField(fieldName);
+      Field field = getDeclaredField(obj, fieldName);
+
+      Object realValue = value;
+      if (value instanceof BigDecimal || value instanceof Number || value instanceof String) {
+        if (field.getType() == Float.class || field.getType() == float.class) {
+          realValue = Float.parseFloat(value.toString());
+        } else if (field.getType() == Double.class || field.getType() == double.class) {
+          realValue = Double.parseDouble(value.toString());
+        } else if (field.getType() == Integer.class || field.getType() == int.class) {
+          realValue = (int) Double.parseDouble(value.toString());
+        } else if (field.getType() == Boolean.class || field.getType() == boolean.class) {
+          realValue = Boolean.valueOf(value.toString());
+        }
+      }
+
+      if (field.getType() == boolean.class || field.getType() == Boolean.class) {
+        if (value != null) {
+          realValue = Boolean.valueOf(value.toString());
+        }
+      }
+
+      setProperty(obj, field, realValue);
+    } catch (Exception e) {
+      return;
+    }
+  }
+
+  /**
+   * get field form object and it's parent
+   */
+  public static Field getDeclaredField(Object object, String fieldName) {
+    Field field = null;
+
+    Class<?> clazz = object.getClass();
+
+    for (; clazz != Object.class; clazz = clazz.getSuperclass()) {
+      try {
+        field = clazz.getDeclaredField(fieldName);
+        return field;
+      } catch (Exception e) {
+
+      }
+    }
+
+    return null;
+  }
+
+  /**
+   * Set property(field) of the specified object.
+   * @param bean The object which has the given property
+   * @param field The field to be set
+   * @param value The value to be set to the field
+   * @throws IllegalAccessException
+   * @throws InvocationTargetException
+   * @throws NoSuchMethodException
+   */
+  public static void setProperty(Object bean, Field field, Object value) throws IllegalAccessException,
+          InvocationTargetException,
+          NoSuchMethodException {
+
+    if (bean == null || field == null) {
+      return;
+    }
+
+    try {
+      field.setAccessible(true);
+      field.set(bean, value);
+    } catch (Exception e) {
+    }
+
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXResourceUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXResourceUtils.java
new file mode 100644
index 0000000..d305e3e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXResourceUtils.java
@@ -0,0 +1,451 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.graphics.Color;
+import android.graphics.LinearGradient;
+import android.graphics.Shader;
+import android.support.annotation.NonNull;
+import android.text.TextUtils;
+import android.util.Pair;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Locale;
+import java.util.Map;
+import java.util.StringTokenizer;
+
+/**
+ * Class for parse color
+ */
+public class WXResourceUtils {
+
+  private final static Map<String, Integer> colorMap = new HashMap<>();
+  private final static int RGB_SIZE = 3;
+  private final static int RGBA_SIZE = 4;
+  private final static int HEX = 16;
+  private final static int COLOR_RANGE = 255;
+  private final static String RGB = "rgb";
+  private final static String RGBA = "rgba";
+  private final static SingleFunctionParser.FlatMapper<Integer> FUNCTIONAL_RGB_MAPPER =
+          new SingleFunctionParser.FlatMapper<Integer>() {
+            @Override
+            public Integer map(String raw) {
+              int color = WXUtils.parseUnitOrPercent(raw, COLOR_RANGE);
+              if (color < 0) {
+                color = 0;
+              } else if (color > COLOR_RANGE) {
+                color = COLOR_RANGE;
+              }
+              return color;
+            }
+          };
+
+  private final static SingleFunctionParser.NonUniformMapper<Number> FUNCTIONAL_RGBA_MAPPER =
+          new SingleFunctionParser.NonUniformMapper<Number>() {
+            @Override
+            public List<Number> map(List<String> raw) {
+              List<Number> result = new ArrayList<>(RGBA_SIZE);
+              int i, color;
+              for (i = 0; i < RGB_SIZE; i++) {
+                color = WXUtils.parseUnitOrPercent(raw.get(i), COLOR_RANGE);
+                if (color < 0) {
+                  color = 0;
+                } else if (color > COLOR_RANGE) {
+                  color = COLOR_RANGE;
+                }
+                result.add(color);
+              }
+              result.add(Float.valueOf(raw.get(i)));
+              return result;
+            }
+          };
+
+  static {
+    colorMap.put("aliceblue", 0XFFF0F8FF);
+    colorMap.put("antiquewhite", 0XFFFAEBD7);
+    colorMap.put("aqua", 0XFF00FFFF);
+    colorMap.put("aquamarine", 0XFF7FFFD4);
+    colorMap.put("azure", 0XFFF0FFFF);
+    colorMap.put("beige", 0XFFF5F5DC);
+    colorMap.put("bisque", 0XFFFFE4C4);
+    colorMap.put("black", 0XFF000000);
+    colorMap.put("blanchedalmond", 0XFFFFEBCD);
+    colorMap.put("blue", 0XFF0000FF);
+    colorMap.put("blueviolet", 0XFF8A2BE2);
+    colorMap.put("brown", 0XFFA52A2A);
+    colorMap.put("burlywood", 0XFFDEB887);
+    colorMap.put("cadetblue", 0XFF5F9EA0);
+    colorMap.put("chartreuse", 0XFF7FFF00);
+    colorMap.put("chocolate", 0XFFD2691E);
+    colorMap.put("coral", 0XFFFF7F50);
+    colorMap.put("cornflowerblue", 0XFF6495ED);
+    colorMap.put("cornsilk", 0XFFFFF8DC);
+    colorMap.put("crimson", 0XFFDC143C);
+    colorMap.put("cyan", 0XFF00FFFF);
+    colorMap.put("darkblue", 0XFF00008B);
+    colorMap.put("darkcyan", 0XFF008B8B);
+    colorMap.put("darkgoldenrod", 0XFFB8860B);
+    colorMap.put("darkgray", 0XFFA9A9A9);
+    colorMap.put("darkgreen", 0XFF006400);
+    colorMap.put("darkkhaki", 0XFFBDB76B);
+    colorMap.put("darkmagenta", 0XFF8B008B);
+    colorMap.put("darkolivegreen", 0XFF556B2F);
+    colorMap.put("darkorange", 0XFFFF8C00);
+    colorMap.put("darkorchid", 0XFF9932CC);
+    colorMap.put("darkred", 0XFF8B0000);
+    colorMap.put("darksalmon", 0XFFE9967A);
+    colorMap.put("darkseagreen", 0XFF8FBC8F);
+    colorMap.put("darkslateblue", 0XFF483D8B);
+    colorMap.put("darkslategray", 0XFF2F4F4F);
+    colorMap.put("darkslategrey", 0XFF2F4F4F);
+    colorMap.put("darkturquoise", 0XFF00CED1);
+    colorMap.put("darkviolet", 0XFF9400D3);
+    colorMap.put("deeppink", 0XFFFF1493);
+    colorMap.put("deepskyblue", 0XFF00BFFF);
+    colorMap.put("dimgray", 0XFF696969);
+    colorMap.put("dimgrey", 0XFF696969);
+    colorMap.put("dodgerblue", 0XFF1E90FF);
+    colorMap.put("firebrick", 0XFFB22222);
+    colorMap.put("floralwhite", 0XFFFFFAF0);
+    colorMap.put("forestgreen", 0XFF228B22);
+    colorMap.put("fuchsia", 0XFFFF00FF);
+    colorMap.put("gainsboro", 0XFFDCDCDC);
+    colorMap.put("ghostwhite", 0XFFF8F8FF);
+    colorMap.put("gold", 0XFFFFD700);
+    colorMap.put("goldenrod", 0XFFDAA520);
+    colorMap.put("gray", 0XFF808080);
+    colorMap.put("grey", 0XFF808080);
+    colorMap.put("green", 0XFF008000);
+    colorMap.put("greenyellow", 0XFFADFF2F);
+    colorMap.put("honeydew", 0XFFF0FFF0);
+    colorMap.put("hotpink", 0XFFFF69B4);
+    colorMap.put("indianred", 0XFFCD5C5C);
+    colorMap.put("indigo", 0XFF4B0082);
+    colorMap.put("ivory", 0XFFFFFFF0);
+    colorMap.put("khaki", 0XFFF0E68C);
+    colorMap.put("lavender", 0XFFE6E6FA);
+    colorMap.put("lavenderblush", 0XFFFFF0F5);
+    colorMap.put("lawngreen", 0XFF7CFC00);
+    colorMap.put("lemonchiffon", 0XFFFFFACD);
+    colorMap.put("lightblue", 0XFFADD8E6);
+    colorMap.put("lightcoral", 0XFFF08080);
+    colorMap.put("lightcyan", 0XFFE0FFFF);
+    colorMap.put("lightgoldenrodyellow", 0XFFFAFAD2);
+    colorMap.put("lightgray", 0XFFD3D3D3);
+    colorMap.put("lightgrey", 0XFFD3D3D3);
+    colorMap.put("lightgreen", 0XFF90EE90);
+    colorMap.put("lightpink", 0XFFFFB6C1);
+    colorMap.put("lightsalmon", 0XFFFFA07A);
+    colorMap.put("lightseagreen", 0XFF20B2AA);
+    colorMap.put("lightskyblue", 0XFF87CEFA);
+    colorMap.put("lightslategray", 0XFF778899);
+    colorMap.put("lightslategrey", 0XFF778899);
+    colorMap.put("lightsteelblue", 0XFFB0C4DE);
+    colorMap.put("lightyellow", 0XFFFFFFE0);
+    colorMap.put("lime", 0XFF00FF00);
+    colorMap.put("limegreen", 0XFF32CD32);
+    colorMap.put("linen", 0XFFFAF0E6);
+    colorMap.put("magenta", 0XFFFF00FF);
+    colorMap.put("maroon", 0XFF800000);
+    colorMap.put("mediumaquamarine", 0XFF66CDAA);
+    colorMap.put("mediumblue", 0XFF0000CD);
+    colorMap.put("mediumorchid", 0XFFBA55D3);
+    colorMap.put("mediumpurple", 0XFF9370DB);
+    colorMap.put("mediumseagreen", 0XFF3CB371);
+    colorMap.put("mediumslateblue", 0XFF7B68EE);
+    colorMap.put("mediumspringgreen", 0XFF00FA9A);
+    colorMap.put("mediumturquoise", 0XFF48D1CC);
+    colorMap.put("mediumvioletred", 0XFFC71585);
+    colorMap.put("midnightblue", 0XFF191970);
+    colorMap.put("mintcream", 0XFFF5FFFA);
+    colorMap.put("mistyrose", 0XFFFFE4E1);
+    colorMap.put("moccasin", 0XFFFFE4B5);
+    colorMap.put("navajowhite", 0XFFFFDEAD);
+    colorMap.put("navy", 0XFF000080);
+    colorMap.put("oldlace", 0XFFFDF5E6);
+    colorMap.put("olive", 0XFF808000);
+    colorMap.put("olivedrab", 0XFF6B8E23);
+    colorMap.put("orange", 0XFFFFA500);
+    colorMap.put("orangered", 0XFFFF4500);
+    colorMap.put("orchid", 0XFFDA70D6);
+    colorMap.put("palegoldenrod", 0XFFEEE8AA);
+    colorMap.put("palegreen", 0XFF98FB98);
+    colorMap.put("paleturquoise", 0XFFAFEEEE);
+    colorMap.put("palevioletred", 0XFFDB7093);
+    colorMap.put("papayawhip", 0XFFFFEFD5);
+    colorMap.put("peachpuff", 0XFFFFDAB9);
+    colorMap.put("peru", 0XFFCD853F);
+    colorMap.put("pink", 0XFFFFC0CB);
+    colorMap.put("plum", 0XFFDDA0DD);
+    colorMap.put("powderblue", 0XFFB0E0E6);
+    colorMap.put("purple", 0XFF800080);
+    colorMap.put("rebeccapurple", 0XFF663399);
+    colorMap.put("red", 0XFFFF0000);
+    colorMap.put("rosybrown", 0XFFBC8F8F);
+    colorMap.put("royalblue", 0XFF4169E1);
+    colorMap.put("saddlebrown", 0XFF8B4513);
+    colorMap.put("salmon", 0XFFFA8072);
+    colorMap.put("sandybrown", 0XFFF4A460);
+    colorMap.put("seagreen", 0XFF2E8B57);
+    colorMap.put("seashell", 0XFFFFF5EE);
+    colorMap.put("sienna", 0XFFA0522D);
+    colorMap.put("silver", 0XFFC0C0C0);
+    colorMap.put("skyblue", 0XFF87CEEB);
+    colorMap.put("slateblue", 0XFF6A5ACD);
+    colorMap.put("slategray", 0XFF708090);
+    colorMap.put("slategrey", 0XFF708090);
+    colorMap.put("snow", 0XFFFFFAFA);
+    colorMap.put("springgreen", 0XFF00FF7F);
+    colorMap.put("steelblue", 0XFF4682B4);
+    colorMap.put("tan", 0XFFD2B48C);
+    colorMap.put("teal", 0XFF008080);
+    colorMap.put("thistle", 0XFFD8BFD8);
+    colorMap.put("tomato", 0XFFFF6347);
+    colorMap.put("turquoise", 0XFF40E0D0);
+    colorMap.put("violet", 0XFFEE82EE);
+    colorMap.put("wheat", 0XFFF5DEB3);
+    colorMap.put("white", 0XFFFFFFFF);
+    colorMap.put("whitesmoke", 0XFFF5F5F5);
+    colorMap.put("yellow", 0XFFFFFF00);
+    colorMap.put("yellowgreen", 0XFF9ACD32);
+    colorMap.put("transparent", 0x00000000);
+  }
+
+  public static int getColor(String color) {
+    return getColor(color, Integer.MIN_VALUE);
+  }
+
+  public static int getColor(String color, int defaultColor) {
+    if (TextUtils.isEmpty(color)) {
+      return defaultColor;
+    }
+    color = color.trim(); //remove non visible codes
+
+    Integer cache = WXUtils.sCache.get(color);
+    if(cache!=null){
+      return cache;
+    }
+    else {
+      int resultColor = defaultColor;
+      Pair<Boolean, Integer> result;
+      ColorConvertHandler[] handlers = ColorConvertHandler.values();
+      for (ColorConvertHandler handler : handlers) {
+        try {
+          result = handler.handle(color);
+          if (result.first) {
+            resultColor = result.second;
+            WXUtils.sCache.put(color, resultColor);
+            break;
+          }
+        } catch (RuntimeException e) {
+          WXLogUtils.v("Color_Parser", WXLogUtils.getStackTrace(e));
+        }
+      }
+      return resultColor;
+    }
+  }
+
+  /**
+   * Assembly gradients
+   * @param image gradient values contains direction、colors
+   * @param width component width
+   * @param height component height
+   * @return gradient shader
+   */
+  public static Shader getShader(String image, float width, float height) {
+    List<String> valueList = parseGradientValues(image);
+    if (valueList != null && valueList.size() == 3) {
+      float[] points = parseGradientDirection(valueList.get(0), width, height);
+      Shader shader = new LinearGradient(points[0], points[1],
+              points[2], points[3],
+              getColor(valueList.get(1), Color.WHITE), getColor(valueList.get(2), Color.WHITE),
+              Shader.TileMode.CLAMP);
+      return shader;
+    }
+    return null;
+  }
+
+  /**
+   * parse gradient values contains direction、colors
+   * @param image gradient values
+   * @return split values by comma
+   */
+  @NonNull
+  private static List<String> parseGradientValues(String image) {
+    if (TextUtils.isEmpty(image)) {
+      return null;
+    }
+    image.trim();
+    if(image.startsWith("linear-gradient")){
+      String valueStr = image.substring(image.indexOf("(") + 1, image.lastIndexOf(")"));
+      StringTokenizer tokenizer = new StringTokenizer(valueStr, ",");
+      List<String> values = new ArrayList<>();
+      String temp = null;
+      while (tokenizer.hasMoreTokens()) {
+        String token = tokenizer.nextToken();
+        if (token.contains("(")) {
+          temp = token + ",";
+          continue;
+        }
+        if (token.contains(")")) {
+          temp += token;
+          values.add(temp);
+          temp = null;
+          continue;
+        }
+        if (temp != null) {
+          temp += (token + ",");
+          continue;
+        }
+        values.add(token);
+      }
+      return values;
+    }
+    return null;
+  }
+
+  /**
+   * parse gradient direction
+   * @param direction gradient direction
+   * @param width component width
+   * @param height component height
+   * @return gradient points
+   */
+  private static float[] parseGradientDirection(String direction, float width, float height) {
+    int x1 = 0, y1 = 1, x2 = 2, y2 = 3;
+    float[] points = {0, 0, 0, 0};
+
+    if (!TextUtils.isEmpty(direction)) {
+      direction = direction.replaceAll("\\s*", "").toLowerCase(Locale.ROOT);
+    }
+
+    switch (direction) {
+      //to right
+      case "toright":
+        points[x2] = width;
+        break;
+      //to left
+      case "toleft":
+        points[x1] = width;
+        break;
+      //to bottom
+      case "tobottom":
+        points[y2] = height;
+        break;
+      //to top
+      case "totop":
+        points[y1] = height;
+        break;
+      //to bottom right
+      case "tobottomright":
+        points[x2] = width;
+        points[y2] = height;
+        break;
+      //to top left
+      case "totopleft":
+        points[x1] = width;
+        points[y1] = height;
+        break;
+    }
+    return points;
+  }
+
+  public static boolean isNamedColor(String name) {
+    return colorMap.containsKey(name);
+  }
+
+  enum ColorConvertHandler {
+    NAMED_COLOR_HANDLER {
+      @Override
+      @NonNull Pair<Boolean, Integer> handle(String rawColor) {
+        if (colorMap.containsKey(rawColor)) {
+          return new Pair<>(Boolean.TRUE, colorMap.get(rawColor));
+        } else {
+          return new Pair<>(Boolean.FALSE, Color.TRANSPARENT);
+        }
+      }
+    },
+    RGB_HANDLER {
+      @Override
+      @NonNull Pair<Boolean, Integer> handle(String rawColor) {
+        if (rawColor.length() == 4) {
+          //#eee, #333
+          int r, g, b;
+          r = Integer.parseInt(rawColor.substring(1, 2), HEX);
+          g = Integer.parseInt(rawColor.substring(2, 3), HEX);
+          b = Integer.parseInt(rawColor.substring(3, 4), HEX);
+          return new Pair<>(Boolean.TRUE, Color.rgb(r + (r << 4), g + (g << 4), b + (b << 4)));
+        } else if (rawColor.length() == 7 || rawColor.length() == 9) {
+          //#eeeeee, #333333
+          return new Pair<>(Boolean.TRUE, Color.parseColor(rawColor));
+        } else {
+          return new Pair<>(Boolean.FALSE, Color.TRANSPARENT);
+        }
+      }
+    },
+    FUNCTIONAL_RGB_HANDLER {
+      @Override
+      @NonNull Pair<Boolean, Integer> handle(String rawColor) {
+        SingleFunctionParser<Integer> functionParser = new SingleFunctionParser<>(rawColor, FUNCTIONAL_RGB_MAPPER);
+        List<Integer> rgb = functionParser.parse(RGB);
+        if (null != rgb && rgb.size() == RGB_SIZE) {
+          return new Pair<>(Boolean.TRUE, Color.rgb(rgb.get(0), rgb.get(1), rgb.get(2)));
+        } else {
+          return new Pair<>(Boolean.FALSE, Color.TRANSPARENT);
+        }
+      }
+    },
+
+    FUNCTIONAL_RGBA_HANDLER {
+      @Override
+      @NonNull Pair<Boolean, Integer> handle(String rawColor) {
+        SingleFunctionParser<Number> functionParser = new SingleFunctionParser<>(rawColor, FUNCTIONAL_RGBA_MAPPER);
+        List<Number> rgba = functionParser.parse(RGBA);
+        if (rgba.size() == RGBA_SIZE) {
+          return new Pair<>(Boolean.TRUE, Color.argb(
+                  parseAlpha(rgba.get(3).floatValue()),
+                  rgba.get(0).intValue(),
+                  rgba.get(1).intValue(),
+                  rgba.get(2).intValue()));
+        } else {
+          return new Pair<>(Boolean.FALSE, Color.TRANSPARENT);
+        }
+      }
+    };
+
+    /**
+     * Parse color to #RRGGBB or #AARRGGBB. The parsing algorithm depends on sub-class.
+     *
+     * @param rawColor color, maybe functional RGB(RGBA), #RGB, keywords color or transparent
+     * @return #RRGGBB or #AARRGGBB
+     */
+    @NonNull abstract Pair<Boolean, Integer> handle(String rawColor);
+
+    /**
+     * Parse alpha gradient of color from range 0-1 to range 0-255
+     *
+     * @param alpha the alpha value, in range 0-1
+     * @return the alpha value, in range 0-255
+     */
+    private static int parseAlpha(float alpha) {
+      return (int) (alpha * COLOR_RANGE);
+    }
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXSoInstallMgrSdk.java b/android/sdk/src/main/java/org/apache/weex/utils/WXSoInstallMgrSdk.java
new file mode 100644
index 0000000..a5da705
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXSoInstallMgrSdk.java
@@ -0,0 +1,607 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.annotation.SuppressLint;
+import android.app.Application;
+import android.content.Context;
+import android.content.pm.ApplicationInfo;
+import android.os.Build;
+import android.text.TextUtils;
+import org.apache.weex.IWXStatisticsListener;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.adapter.IWXSoLoaderAdapter;
+import org.apache.weex.adapter.IWXUserTrackAdapter;
+import org.apache.weex.common.WXErrorCode;
+import dalvik.system.PathClassLoader;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.lang.reflect.Field;
+import java.nio.ByteBuffer;
+import java.nio.channels.FileChannel;
+import java.util.Enumeration;
+import java.util.Locale;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipException;
+import java.util.zip.ZipFile;
+
+
+/**
+ * Utility class for managing so library, including load native library and version management.
+ * <ol>
+ *   <li>Load library<br>
+ *     It Will try to use {@link System#loadLibrary(String)} to load native library. If it successes,
+ *     the Android Framework will be responsible for managing library and library version.
+ *     If it fails in case of some ceratin armebi-v7a architecture device, it will try to extract
+ *     native library from apk and copy it the data directory of the app. Then load it using
+ *     {@link System#load(String)}.
+ *     </li>
+ *  <li>
+ *       Version control for extracting native library from apk.
+ *  </li>
+ * </ol>
+ */
+public class WXSoInstallMgrSdk {
+
+  final static String LOGTAG = "INIT_SO";
+  //below is the CPU string types
+  private final static String ARMEABI = "armeabi"; //default
+  private final static String X86 = "x86";
+  private final static String MIPS = "mips";
+  private final static String STARTUPSO = "/libweexjsb.so";
+  private final static String STARTUPSOANDROID15 = "/libweexjst.so";
+
+  static Application mContext = null;
+  private static IWXSoLoaderAdapter mSoLoader = null;
+  private static IWXStatisticsListener mStatisticsListener = null;
+
+  private static String mAbi = null;
+
+  public static void init(Application c,
+                          IWXSoLoaderAdapter loader,
+                          IWXStatisticsListener listener) {
+    mContext = c;
+    mSoLoader = loader;
+    mStatisticsListener = listener;
+  }
+
+  public static boolean isX86(){
+    String cpuType = _cpuType();
+    return cpuType.equalsIgnoreCase(X86);
+  }
+
+  public static boolean isCPUSupport(){
+    String cpuType = _cpuType();
+    return !cpuType.equalsIgnoreCase(MIPS);
+  }
+
+  /**
+   * Load so library.
+   *
+   * If a library loader adapter exists, use this adapter to load library,
+   * otherwise use {@link System#loadLibrary(String)} to load library.
+   * If failed to load library, try to extract the so library and load it
+   * from arembi in the .apk
+   *
+   * @param libName library name, like webp, not necessary to be libwep.so
+   * @param version the version of the so library
+   */
+  public static boolean initSo(String libName, int version, IWXUserTrackAdapter utAdapter) {
+    String cpuType = _cpuType();
+    if (cpuType.equalsIgnoreCase(MIPS) ) {
+      WXExceptionUtils.commitCriticalExceptionRT(null,
+              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
+              "initSo", "[WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT] for android cpuType is MIPS",
+              null);
+      return false;
+    }
+
+    // copy startup so
+    if (WXEnvironment.CORE_SO_NAME.equals(libName)) {
+      copyStartUpSo();
+    }
+
+
+    boolean InitSuc = false;
+      try {
+        // If a library loader adapter exists, use this adapter to load library
+        // instead of System.loadLibrary.
+        if (mSoLoader != null) {
+          mSoLoader.doLoadLibrary("c++_shared");
+        } else {
+          System.loadLibrary("c++_shared");
+        }
+      } catch (Exception | Error e) {
+        WXExceptionUtils.commitCriticalExceptionRT(null,
+                WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
+                "initSo",
+                        "load c++_shared failed Detail Error is: " +e.getMessage(),
+                null);
+
+        if(WXEnvironment.isApkDebugable()) {
+          throw e;
+        }
+      }
+
+      /**
+       * Load library with {@link System#loadLibrary(String)}
+       */
+      try {
+        // If a library loader adapter exists, use this adapter to load library
+        // instead of System.loadLibrary.
+        if (mSoLoader != null) {
+          mSoLoader.doLoadLibrary(libName);
+        } else {
+          System.loadLibrary(libName);
+        }
+
+        InitSuc = true;
+      } catch (Exception | Error e2) {
+        if (cpuType.contains(ARMEABI) || cpuType.contains(X86)) {
+          WXExceptionUtils.commitCriticalExceptionRT(null,
+                  WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
+                  "initSo", libName + "[WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT] for android cpuType is " +cpuType +
+                          "\n Detail Error is: " +e2.getMessage(),
+                  null);
+        }
+
+        if(WXEnvironment.isApkDebugable()) {
+          throw e2;
+        }
+        InitSuc = false;
+      }
+
+//      try {
+
+//        if (!InitSuc) {
+//
+//          //File extracted from apk already exists.
+//          if (isExist(libName, version)) {
+//            boolean res = _loadUnzipSo(libName, version, utAdapter);
+//            if (res) {
+//              return res;
+//            } else {
+//              //Delete the corrupt so library, and extract it again.
+//              removeSoIfExit(libName, version);
+//            }
+//          }
+//
+//          //Fail for loading file from libs, extract so library from so and load it.
+//          if (cpuType.equalsIgnoreCase(MIPS)) {
+//            return false;
+//          } else {
+//            try {
+//              InitSuc = unZipSelectedFiles(libName, version, utAdapter);
+//            } catch (IOException e2) {
+//              e2.printStackTrace();
+//            }
+//          }
+//
+//        }
+//      } catch (Exception | Error e) {
+//        InitSuc = false;
+//        e.printStackTrace();
+//      }
+  //  }
+    return InitSuc;
+  }
+
+  private static File _desSoCopyFile(String soName) {
+    String cpuType = _cpuType();
+    String copyPath = WXEnvironment.copySoDesDir();
+    if (TextUtils.isEmpty(copyPath)) {
+      return null;
+    }
+    File desDir = new File(copyPath, soName + "/" + cpuType);
+    return desDir;
+  }
+
+  /**
+   * copyStartUpSo
+   */
+  @SuppressLint("SdCardPath")
+  public static void copyStartUpSo() {
+    try {
+      // copy libjsb.so to cache/weex/jsb/cputype
+      String pkgName = WXEnvironment.getApplication().getPackageName();
+      String cacheFile = WXEnvironment.getApplication().getApplicationContext().getCacheDir().getPath();
+
+      // cp weexjsb any way
+      // if android api < 16 copy libweexjst.so else copy libweexjsb.so
+      boolean pieSupport = true;
+      File newfile;
+      String startSoName = WXEnvironment.CORE_JSB_SO_NAME;
+      String startSoPath = STARTUPSO;
+      if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
+        pieSupport = false;
+        startSoName = WXEnvironment.CORE_JST_SO_NAME;
+        startSoPath = STARTUPSOANDROID15;
+      }
+
+      final File copyPath = _desSoCopyFile(startSoName);
+      if(!copyPath.exists()) {
+        copyPath.mkdirs();
+      }
+      newfile = new File(copyPath, startSoPath);
+      WXEnvironment.CORE_JSB_SO_PATH = newfile.getAbsolutePath();
+      String jsb = WXEnvironment.getDefaultSettingValue(startSoName, "-1");
+      if(newfile.exists() && TextUtils.equals(WXEnvironment.getAppVersionName(), jsb)) {
+        // no update so skip copy
+        return;
+      }
+
+      String path = "/data/data/" + pkgName + "/lib";
+      if (cacheFile != null && cacheFile.indexOf("/cache") > 0) {
+        path = cacheFile.replace("/cache", "/lib");
+      }
+      File oldfile = null;
+      if (pieSupport) {
+        oldfile = new File(path, STARTUPSO);
+      } else {
+        oldfile = new File(path , STARTUPSOANDROID15);
+      }
+
+
+      if (!oldfile.exists()) {
+        try {
+          String weexjsb = ((PathClassLoader) (WXSoInstallMgrSdk.class.getClassLoader())).findLibrary(startSoName);
+          oldfile = new File(weexjsb);
+        } catch (Throwable throwable) {
+          // do nothing
+        }
+      }
+
+
+      if(!oldfile.exists()) {
+        String extractSoPath = WXEnvironment.extractSo();
+        oldfile = new File(extractSoPath, STARTUPSO);
+      }
+
+      if (oldfile.exists()) {
+        WXFileUtils.copyFile(oldfile, newfile);
+      }
+      WXEnvironment.writeDefaultSettingsValue(startSoName, WXEnvironment.getAppVersionName());
+    } catch (Throwable e) {
+      e.printStackTrace();
+    }
+  }
+
+  public static void copyJssRuntimeSo(){
+    boolean tryUseRunTimeApi = WXUtils.checkGreyConfig("wxapm","use_runtime_api","0");
+    WXLogUtils.e("weex", "tryUseRunTimeApi ? "+ tryUseRunTimeApi);
+    if (!tryUseRunTimeApi){
+      return;
+    }
+    try {
+      WXLogUtils.e("weex", "copyJssRuntimeSo: ");
+      File toPath = _desSoCopyFile(WXEnvironment.CORE_JSS_SO_NAME);
+      if(!toPath.exists()) {
+        toPath.mkdirs();
+      }
+      File targetFile = new File(toPath,"libweexjss.so");
+
+      /** 1. check so and versionCode. if update, then rm old jss.so(runtime) in pkg/libs, and copy new so from apk **/
+      String keyVersionCode = "app_version_code_weex";
+      String defaultSettingValue = WXEnvironment.getDefaultSettingValue(keyVersionCode, "-1");
+
+
+      if (targetFile.exists()){
+        if (!TextUtils.equals(WXEnvironment.getAppVersionName(),defaultSettingValue)){
+          targetFile.delete();
+        }else {
+          WXEnvironment.CORE_JSS_SO_PATH= targetFile.getAbsolutePath();
+          WXEnvironment.sUseRunTimeApi = true;
+          WXLogUtils.e("weex", "copyJssRuntimeSo exist:  return");
+          return;
+        }
+      }
+      /** 2. copy jss(runtime) so **/
+      String fromPath =  ((PathClassLoader) (WXSoInstallMgrSdk.class.getClassLoader())).findLibrary("weexjssr");
+      if (TextUtils.isEmpty(fromPath)){
+        return;
+      }
+      targetFile.createNewFile();
+      WXFileUtils.copyFileWithException(new File(fromPath),targetFile);
+      /**3. update flag **/
+      WXEnvironment.CORE_JSS_SO_PATH= targetFile.getAbsolutePath();
+      WXEnvironment.writeDefaultSettingsValue(keyVersionCode,WXEnvironment.getAppVersionName());
+      WXEnvironment.sUseRunTimeApi = true;
+      WXLogUtils.e("weex", "copyJssRuntimeSo: cp end and return ");
+    }catch (Throwable e){
+      e.printStackTrace();
+      WXEnvironment.sUseRunTimeApi = false;
+      WXLogUtils.e("weex", "copyJssRuntimeSo:  exception" + e);
+    }
+  }
+
+  private static String _getFieldReflectively(Build build, String fieldName) {
+    try {
+      final Field field = Build.class.getField(fieldName);
+      return field.get(build).toString();
+    } catch (Exception ex) {
+      return "Unknown";
+    }
+  }
+
+  public static String _cpuType() {
+    if(TextUtils.isEmpty(mAbi)) {
+      try {
+        mAbi = Build.CPU_ABI;
+      }catch (Throwable e){
+        e.printStackTrace();
+        mAbi = ARMEABI;
+      }
+      if (TextUtils.isEmpty(mAbi)){
+        mAbi = ARMEABI;
+      }
+      mAbi = mAbi.toLowerCase(Locale.ROOT);
+    }
+    return mAbi;
+  }
+
+  /**
+   *
+   * @param libName lib name
+   * @param size  the right size of lib
+   * @return true for valid  ; false for InValid
+   */
+  static boolean checkSoIsValid(String libName, long size) {
+    Context context = mContext;
+    if (null == context) {
+      return false;
+    }
+    try{
+      long start=System.currentTimeMillis();
+      if(WXSoInstallMgrSdk.class.getClassLoader() instanceof PathClassLoader ) {
+
+        String path = ((PathClassLoader) (WXSoInstallMgrSdk.class.getClassLoader())).findLibrary(libName);
+        if(TextUtils.isEmpty(path) ){
+          return false;
+        }
+        File file = new File(path);
+
+        if (!file.exists() || size == file.length()) {
+          WXLogUtils.w("weex so size check path :" + path+"   "+(System.currentTimeMillis() - start));
+          return true;
+        } else {
+          return false;
+        }
+      }
+    }catch(Throwable e ){
+      WXExceptionUtils.commitCriticalExceptionRT(null,
+              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT,
+              "checkSoIsValid", "[WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT] for " +
+                      "weex so size check fail exception :"+e.getMessage(),
+              null);
+      WXLogUtils.e("weex so size check fail exception :"+e.getMessage());
+    }
+
+    return true;
+  }
+
+  /**
+   * Concatenate the path of the so library, including directory.
+   * @param libName the raw name of the lib
+   * @param version the version of the so library
+   * @return the path of the so library
+   */
+  @SuppressLint("SdCardPath")
+  static String _targetSoFile(String libName, int version) {
+    Context context = mContext;
+    if (null == context) {
+      return "";
+    }
+
+    String path = "/data/data/" + context.getPackageName() + "/files";
+
+    File f = context.getFilesDir();
+    if (f != null) {
+      path = f.getPath();
+    }
+    return path + "/lib" + libName + "bk" + version + ".so";
+
+  }
+
+  /**
+   * Remove the so library if it had been extracted.
+   * @param libName
+   * @param version
+   */
+  static void removeSoIfExit(String libName, int version) {
+
+    String file = _targetSoFile(libName, version);
+    File a = new File(file);
+    if (a.exists()) {
+      a.delete();
+    }
+
+  }
+
+  /**
+   * Tell whether the so is extracted.
+   */
+  static boolean isExist(String libName, int version) {
+
+    String file = _targetSoFile(libName, version);
+    File a = new File(file);
+    return a.exists();
+
+  }
+
+
+  /**
+   * Load .so library
+   */
+  @SuppressLint("UnsafeDynamicallyLoadedCode")
+  static boolean _loadUnzipSo(String libName,
+                              int version,
+                              IWXUserTrackAdapter utAdapter) {
+    boolean initSuc = false;
+    try {
+      if (isExist(libName, version)) {
+        // If a library loader adapter exists, use this adapter to load library
+        // instead of System.load.
+        if (mSoLoader != null) {
+          mSoLoader.doLoad(_targetSoFile(libName, version));
+        } else {
+          System.load(_targetSoFile(libName, version));
+        }
+      }
+      initSuc = true;
+    } catch (Throwable e) {
+      initSuc = false;
+      WXExceptionUtils.commitCriticalExceptionRT(null,
+              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT,
+              "_loadUnzipSo", "[WX_KEY_EXCEPTION_SDK_INIT_WX_ERR_COPY_FROM_APK] " +
+                      "\n Detail Msg is : " +  e.getMessage(),
+              null);
+      WXLogUtils.e("", e);
+    }
+    return initSuc;
+  }
+
+  static boolean unZipSelectedFiles(String libName,
+                                    int version,
+                                    IWXUserTrackAdapter utAdapter) throws ZipException, IOException {
+    String sourcePath = "lib/armeabi/lib" + libName + ".so";
+
+    String zipPath = "";
+    Context context = mContext;
+    if (context == null) {
+      return false;
+    }
+
+    ApplicationInfo aInfo = context.getApplicationInfo();
+    if (null != aInfo) {
+      zipPath = aInfo.sourceDir;
+    }
+
+    ZipFile zf;
+    zf = new ZipFile(zipPath);
+    try {
+
+      for (Enumeration<?> entries = zf.entries(); entries.hasMoreElements(); ) {
+        ZipEntry entry = ((ZipEntry) entries.nextElement());
+        if (entry.getName().startsWith(sourcePath)) {
+
+          InputStream in = null;
+          FileOutputStream os = null;
+          FileChannel channel = null;
+          int total = 0;
+          try {
+
+            //Make sure the old library is deleted.
+            removeSoIfExit(libName, version);
+
+            //Copy file
+            in = zf.getInputStream(entry);
+            os = context.openFileOutput("lib" + libName + "bk" + version + ".so",
+                    Context.MODE_PRIVATE);
+            channel = os.getChannel();
+
+            byte[] buffers = new byte[1024];
+            int realLength;
+
+            while ((realLength = in.read(buffers)) > 0) {
+              //os.write(buffers);
+              channel.write(ByteBuffer.wrap(buffers, 0, realLength));
+              total += realLength;
+
+            }
+          } finally {
+            if (in != null) {
+              try {
+                in.close();
+              } catch (Exception e) {
+                e.printStackTrace();
+              }
+            }
+
+            if (channel != null) {
+              try {
+                channel.close();
+              } catch (Exception e) {
+                e.printStackTrace();
+              }
+            }
+
+            if (os != null) {
+              try {
+                os.close();
+              } catch (Exception e) {
+                e.printStackTrace();
+              }
+            }
+
+            if (zf != null) {
+              zf.close();
+              zf = null;
+            }
+          }
+
+          if (total > 0) {
+            return _loadUnzipSo(libName, version, utAdapter);
+          } else {
+            return false;
+          }
+        }
+      }
+    } catch (java.io.IOException e) {
+      e.printStackTrace();
+      WXExceptionUtils.commitCriticalExceptionRT(null,
+              WXErrorCode.WX_KEY_EXCEPTION_SDK_INIT_CPU_NOT_SUPPORT,
+              "unZipSelectedFiles", "[WX_KEY_EXCEPTION_SDK_INIT_unZipSelectedFiles] " +
+                      "\n Detail msg is: " + e.getMessage(),
+              null);
+
+    } finally {
+
+      if (zf != null) {
+        zf.close();
+        zf = null;
+      }
+    }
+    return false;
+  }
+
+  /**
+   * Using {@Code WXExceptionUtils.commitCriticalExceptionRT}  insted
+   */
+//  static void commit(IWXUserTrackAdapter utAdapter, String errCode, String errMsg) {
+//    if (mStatisticsListener != null) {
+//      mStatisticsListener.onException("0", errCode, errMsg);
+//    }
+//
+//    if (utAdapter == null) {
+//      return;
+//    }
+//    if (errCode != null && errMsg != null) {
+//      WXPerformance p = new WXPerformance();
+//      p.errCode = errCode;
+//      p.errMsg = errMsg;
+//      utAdapter.commit(null, null, WXEnvironment.ENVIRONMENT, p, null);
+//    } else {
+//      utAdapter.commit(null, null, WXEnvironment.ENVIRONMENT, null, null);
+//
+//    }
+//  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXUtils.java
new file mode 100644
index 0000000..a06d47e
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXUtils.java
@@ -0,0 +1,597 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.app.ActivityManager;
+import android.content.Context;
+import android.content.res.Configuration;
+import android.os.Looper;
+import android.os.SystemClock;
+import android.support.annotation.Nullable;
+import android.support.v4.util.LruCache;
+import android.text.TextUtils;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.adapter.IWXConfigAdapter;
+import org.apache.weex.common.Constants;
+
+public class WXUtils {
+
+  final static LruCache<String, Integer> sCache = new LruCache<>(64);
+  public static final char PERCENT = '%';
+  private static final int HUNDRED =100;
+  /**
+   * Tell whether current thread is UI(main) thread.
+   * @return true for UI(main) thread
+   */
+  public static boolean isUiThread() {
+    return Thread.currentThread().getId() == Looper.getMainLooper().getThread().getId();
+  }
+
+  public static boolean isUndefined(float value) {
+    return Float.isNaN(value);
+  }
+
+
+  public static float getFloatByViewport(Object value, int viewport) {
+    if (value == null) {
+      return Float.NaN;
+    }
+    String temp = value.toString().trim();
+    if (Constants.Name.AUTO.equals(temp)
+            || Constants.Name.UNDEFINED.equals(temp)
+            || TextUtils.isEmpty(temp)) {
+      WXLogUtils.e("Argument Warning ! value is " + temp + "And default Value:" + Float.NaN);
+      return Float.NaN;
+    }
+
+    if (temp.endsWith("wx")) {
+      try {
+        return transferWx(temp, viewport);
+      } catch (NumberFormatException e) {
+        WXLogUtils.e("Argument format error! value is " + value, e);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    } else if (temp.endsWith("px")) {
+      try {
+        temp = temp.substring(0, temp.indexOf("px"));
+        return Float.parseFloat(temp);
+      } catch (NumberFormatException nfe) {
+        WXLogUtils.e("Argument format error! value is " + value, nfe);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    } else {
+      try {
+        return Float.parseFloat(temp);
+      } catch (NumberFormatException nfe) {
+        WXLogUtils.e("Argument format error! value is " + value, nfe);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }
+    return Float.NaN;
+  }
+
+  public static float getFloat(Object value) {
+    return getFloat(value, Float.NaN);
+  }
+
+  public static Float getFloat(Object value, @Nullable Float df) {
+    if (value == null) {
+      return df;
+    }
+
+    String temp = value.toString().trim();
+    if(Constants.Name.AUTO.equals(temp)
+            || Constants.Name.UNDEFINED.equals(temp)
+            || TextUtils.isEmpty(temp)){
+      WXLogUtils.e("Argument Warning ! value is " + temp + "And default Value:"+Float.NaN);
+      return df;
+    }
+    if (temp.endsWith("wx")) {
+      try {
+        return transferWx(temp, 750);
+      } catch (NumberFormatException e) {
+        WXLogUtils.e("Argument format error! value is " + value, e);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }else if (temp.endsWith("px")) {
+      try {
+        temp = temp.substring(0, temp.indexOf("px"));
+        return Float.parseFloat(temp);
+      } catch (NumberFormatException nfe) {
+        WXLogUtils.e("Argument format error! value is " + value, nfe);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }else {
+      try {
+        return Float.parseFloat(temp);
+      } catch (NumberFormatException nfe) {
+        WXLogUtils.e("Argument format error! value is " + value, nfe);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }
+    return df;
+  }
+
+  private static float transferWx(String stringWithWXPostfix, int viewport) {
+    if(null == stringWithWXPostfix) {
+      return 0;
+    }
+    String temp = stringWithWXPostfix;
+    if(stringWithWXPostfix.endsWith("wx")) {
+      temp = stringWithWXPostfix.substring(0, stringWithWXPostfix.indexOf("wx"));
+    }
+    Float f = Float.parseFloat(temp);
+    float density = WXEnvironment.sApplication.getResources().getDisplayMetrics().density;
+    return density * f * viewport / WXViewUtils.getScreenWidth();
+  }
+
+  public static float fastGetFloat(String raw, int precision){
+    if(!TextUtils.isEmpty(raw)){
+      boolean positive=true;
+      int loc=0;
+      if(raw.charAt(0)=='-'){
+        positive=false;
+        loc++;
+      }
+      else if(raw.charAt(0)=='+'){
+        loc++;
+      }
+
+      char digit;
+      float result=0;
+      while (loc<raw.length() && (digit=raw.charAt(loc))>='0'&&digit<='9'){
+        result=result*10+digit-'0';
+        loc++;
+      }
+
+      if(loc<raw.length()){
+        if(raw.charAt(loc)=='.'){
+          loc++;
+          int remainderLength=10;
+          int counter=0;
+          while(loc<raw.length() &&
+                  counter<precision &&
+                  ((digit=raw.charAt(loc))>='0'&& digit<='9')){
+            result+=(digit-'0')/(float)remainderLength;
+            remainderLength*=10;
+            loc++;
+            counter++;
+          }
+        }
+        else{
+          // throw new NumberFormatException("Illegal separator");
+        }
+      }
+
+      if(!positive)
+        result*=-1;
+      return result;
+    }
+    return 0;
+    // throw new NumberFormatException("NullNumber");
+  }
+
+  /**
+   * Parse string representation of float. This method intend to be faster than
+   * {@link Float#parseFloat(String)}, but less accuracy.
+   * @param raw
+   * @return
+   */
+  public static float fastGetFloat(String raw){
+    return fastGetFloat(raw, Integer.MAX_VALUE);
+  }
+
+  public static int parseInt(String value) {
+    try {
+      if (!TextUtils.isEmpty(value) && !value.contains(".")) {
+        return Integer.parseInt(value);
+      }
+    } catch (NumberFormatException e) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(WXLogUtils.getStackTrace(e));
+      }
+    }
+    return 0;
+  }
+
+  public static int parseInt(Object value) {
+    return parseInt(String.valueOf(value));
+  }
+
+  public static float parseFloat(Object value) {
+    return parseFloat(String.valueOf(value));
+  }
+
+  public static float parseFloat(String value) {
+    try {
+      if (!TextUtils.isEmpty(value) && !TextUtils.equals(value, "null")) {
+        return Float.parseFloat(value);
+      } else {
+        if (WXEnvironment.isApkDebugable()) {
+          WXLogUtils.e("WXUtils parseFloat illegal value is " + value);
+        }
+      }
+    } catch (NumberFormatException e) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.e(WXLogUtils.getStackTrace(e));
+      }
+    }
+    return 0;
+  }
+
+  public static int getInt(Object value) {
+    return getInteger(value, 0);
+  }
+
+  public static @Nullable Integer getInteger(@Nullable Object value, @Nullable Integer df) {
+
+    if (value == null) {
+      return df;
+    }
+
+    String temp = value.toString().trim();
+    String key = temp;
+    Integer cache = sCache.get(key);
+    if (cache != null) {
+      return cache;
+    } else {
+      Integer ret = df;
+      String suffix = "";
+      if (temp.length() >= 2) {
+        suffix = temp.substring(temp.length() - 2, temp.length());
+      }
+
+      if (TextUtils.equals("wx", suffix)) {
+        if (WXEnvironment.isApkDebugable()) {
+          WXLogUtils
+              .w("the value of " + value
+                  + " use wx unit, which will be not supported soon after.");
+        }
+        try {
+          ret = (int)transferWx(temp, 750);
+        } catch (NumberFormatException e) {
+          WXLogUtils.e("Argument format error! value is " + value, e);
+        } catch (Exception e) {
+          WXLogUtils.e("Argument error! value is " + value, e);
+        }
+      } else if (TextUtils.equals("px", suffix)) {
+        try {
+          temp = temp.substring(0, temp.length() - 2);
+          if (!TextUtils.isEmpty(temp) && temp.contains(".")) {
+            ret = (int)WXUtils.parseFloat(temp);
+          } else {
+            ret = Integer.parseInt(temp);
+          }
+        } catch (NumberFormatException nfe) {
+          WXLogUtils.e("Argument format error! value is " + value, nfe);
+        } catch (Exception e) {
+          WXLogUtils.e("Argument error! value is " + value, e);
+        }
+      } else {
+        try {
+          if (!TextUtils.isEmpty(temp)) {
+            if (temp.contains(".")) {
+              ret = (int)WXUtils.parseFloat(temp);
+            } else {
+              ret = Integer.parseInt(temp);
+            }
+          } else {
+            if (WXEnvironment.isApkDebugable()) {
+              WXLogUtils.e("Argument value is null, df is" + df);
+            }
+          }
+        } catch (NumberFormatException nfe) {
+          if (WXEnvironment.isApkDebugable()) {
+            WXLogUtils.w("The parameter format is not supported", nfe);
+          }
+        } catch (Exception e) {
+          WXLogUtils.e("Argument error! value is " + value, e);
+        }
+      }
+      if (ret != null && !ret.equals(df)) {
+        sCache.put(key, ret);
+      }
+      return ret;
+    }
+  }
+
+  /**
+   * Looks like no longer usage exists, Mark deprecate first.
+   * @param value
+   * @return
+   */
+  @Deprecated
+  public static long getLong(Object value) {
+    if (value == null) {
+      return 0;
+    }
+    long result = 0;
+    String temp = value.toString().trim();
+    if (temp.endsWith("wx")) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.w("the value of " + value + " use wx unit, which will be not supported soon after.");
+      }
+      try {
+        return (long)transferWx(temp, 750);
+      } catch (NumberFormatException e) {
+        WXLogUtils.e("Argument format error! value is " + value, e);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }else if (temp.endsWith("px")) {
+      try {
+        temp = temp.substring(0, temp.indexOf("px"));
+        return Long.parseLong(temp);
+      } catch (NumberFormatException nfe) {
+        WXLogUtils.e("Argument format error! value is " + value, nfe);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }else {
+      try {
+        return Long.parseLong(temp);
+      } catch (NumberFormatException nfe) {
+        WXLogUtils.e("Argument format error! value is " + value, nfe);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }
+    return result;
+  }
+
+  /**
+   * Looks like no longer usage exists, Mark deprecate first.
+   * @param value
+   * @return
+   */
+  @Deprecated
+  public static double getDouble(Object value) {
+    if (value == null) {
+      return 0;
+    }
+    double result = 0;
+    String temp = value.toString().trim();
+    if (temp.endsWith("wx")) {
+      if (WXEnvironment.isApkDebugable()) {
+        WXLogUtils.w("the value of " + value + " use wx unit, which will be not supported soon after.");
+      }
+      try {
+        return transferWx(temp, 750);
+      } catch (NumberFormatException e) {
+        WXLogUtils.e("Argument format error! value is " + value, e);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }else if (temp.endsWith("px")) {
+      try {
+        temp = temp.substring(0, temp.indexOf("px"));
+        return Double.parseDouble(temp);
+      } catch (NumberFormatException nfe) {
+        WXLogUtils.e("Argument format error! value is " + value, nfe);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }else {
+      try {
+        return Double.parseDouble(temp);
+      } catch (NumberFormatException nfe) {
+        WXLogUtils.e("Argument format error! value is " + value, nfe);
+      } catch (Exception e) {
+        WXLogUtils.e("Argument error! value is " + value, e);
+      }
+    }
+
+    return result;
+  }
+
+  @Deprecated
+  public static boolean isTabletDevice() {
+    try{
+      return (WXEnvironment.getApplication().getResources().getConfiguration().screenLayout & Configuration.SCREENLAYOUT_SIZE_MASK) >= Configuration.SCREENLAYOUT_SIZE_LARGE;
+    }catch (Exception e){
+      //
+    }
+    return false;
+  }
+
+  public static Boolean getBoolean(@Nullable Object value, @Nullable Boolean df) {
+
+    if (value == null)
+      return df;
+    if (TextUtils.equals("false",value.toString())) {
+      return false;
+    } else if (TextUtils.equals("true",value.toString())) {
+      return true;
+    }
+    return df;
+  }
+
+  public static long getAvailMemory(Context context){
+    ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
+    ActivityManager.MemoryInfo mi = new ActivityManager.MemoryInfo();
+    am.getMemoryInfo(mi);
+    //mi.availMem;
+    //return Formatter.formatFileSize(context, mi.availMem);
+    WXLogUtils.w("app AvailMemory ---->>>"+mi.availMem/(1024*1024));
+    return mi.availMem/(1024*1024);
+  }
+
+  public static String getString(@Nullable Object value,@Nullable String df) {
+
+    if (value == null)
+      return df;
+
+    String originValue;
+    if (value instanceof String) {
+      originValue = (String) value;
+    } else {
+      originValue = value.toString();
+    }
+
+    return originValue;
+  }
+
+  public static int parseUnitOrPercent(String raw, int unit) {
+    int suffix;
+    if ((suffix = raw.lastIndexOf(WXUtils.PERCENT)) != -1) {
+      return parsePercent(raw.substring(0, suffix), unit);
+    }
+    else {
+      return WXUtils.parseInt(raw);
+    }
+  }
+
+  private static int parsePercent(String raw, int unit){
+    return (int)(Float.parseFloat(raw) / HUNDRED * unit);
+  }
+
+  /**
+   * Get a banner data in JSON format from a bundle content.
+   * A bundle banner looks like below:
+   * \/*!count
+   *  * {
+   *  *   version: "0.2.1.20170104-release",
+   *  *   create: "20170207171112",
+   *  *   git: "banner--772c915",
+   *  *   digest: "c709b7f91867e371b24f54d6aeea232a"
+   *  * }
+   *  !*\/
+   *
+   * @param content a bundle content
+   * @return
+   */
+  public static String getBundleBanner(String content) {
+    final String commentBegin = "/*!";
+    final String commentEnd = "!*/";
+    final String asteriskRegex = "\\*";
+    final String replacement = "";
+
+    int offsetCountBegin = content.indexOf(commentBegin);
+    if (offsetCountBegin == -1) {
+      return null;
+    }
+    offsetCountBegin += commentBegin.length();
+    int offsetCountEnd = indexLineBreak(content, offsetCountBegin);
+    if (offsetCountEnd == -1) {
+      return null;
+    }
+    String countStr = content.substring(offsetCountBegin, offsetCountEnd);
+    int count = Integer.parseInt(countStr);
+
+    String commentBody = content.substring(offsetCountEnd + 1, offsetCountEnd + 1 + count);
+    int offsetBodyEnd = commentBody.lastIndexOf(commentEnd);
+    if (offsetBodyEnd == -1) {
+      return null;
+    }
+    commentBody = commentBody.substring(0, offsetBodyEnd);
+
+    StringBuilder commentBodyBuilder = new StringBuilder();
+    String[] items = splitLineBreak(commentBody);
+
+    for (String item : items) {
+      commentBodyBuilder.append(item.replaceFirst(asteriskRegex, replacement));
+    }
+
+    return commentBodyBuilder.toString();
+  }
+
+  private static int indexLineBreak(String str, int fromIndex) {
+    final String lineBreakIos = "\r";
+    final String lineBreakUnix = "\n";
+    final String linebreakWin = "\r\n";
+
+    int index = str.indexOf(lineBreakIos, fromIndex);
+    if (index == -1) {
+      index = str.indexOf(lineBreakUnix, fromIndex);
+    }
+    if (index == -1) {
+      index = str.indexOf(linebreakWin, fromIndex);
+    }
+
+    return index;
+  }
+
+  private static String[] splitLineBreak(String str) {
+    final String lineBreakIos = "\r";
+    final String lineBreakUnix = "\n";
+    final String linebreakWin = "\r\n";
+    String[] items = str.split(lineBreakIos);
+
+    if (items.length == 1) {
+      items = str.split(lineBreakUnix);
+    }
+    if (items.length == 1) {
+      items = str.split(linebreakWin);
+    }
+
+    return items;
+  }
+
+
+  
+  /**
+   * get number
+   * */
+  public static int getNumberInt(Object value, int defaultValue){
+    if(value == null){
+      return  defaultValue;
+    }
+    if(value instanceof  Number){
+      return  ((Number) value).intValue();
+    }
+    try{
+      String number = value.toString();
+      if(number.indexOf('.') >= 0) {
+        return (int) Float.parseFloat(value.toString());
+      }else{
+        return  Integer.parseInt(number);
+      }
+    }catch (Exception e){return  defaultValue;}
+  }
+
+  public static boolean checkGreyConfig(String group,String key,String defaultValue){
+      IWXConfigAdapter configAdapter = WXSDKManager.getInstance().getWxConfigAdapter();
+      if (null == configAdapter) {
+        return false;
+      }
+      double randomValue = Math.random() * 100;
+      double max = 100;
+      try {
+        String configValue = configAdapter.getConfig(group, key, defaultValue);
+        max = Double.valueOf(configValue);
+      } catch (Exception e) {
+        e.printStackTrace();
+      }
+      return randomValue < max;
+  }
+
+  private static final long sInterval = System.currentTimeMillis() - SystemClock.uptimeMillis();
+
+  public static long getFixUnixTime(){
+    return  sInterval + SystemClock.uptimeMillis();
+  }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXViewToImageUtil.java b/android/sdk/src/main/java/org/apache/weex/utils/WXViewToImageUtil.java
new file mode 100755
index 0000000..07b30dd
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXViewToImageUtil.java
@@ -0,0 +1,151 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.content.Context;
+import android.content.Intent;
+import android.graphics.Bitmap;
+import android.graphics.Color;
+import android.net.Uri;
+import android.os.Environment;
+import android.os.Handler;
+import android.os.Looper;
+import android.provider.MediaStore;
+import android.support.annotation.ColorInt;
+import android.view.View;
+
+import org.apache.weex.WXSDKManager;
+
+import java.io.File;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+
+/**
+ * Created by miomin on 7/25/17.
+ */
+public class WXViewToImageUtil {
+
+    public static int mBackgroundColor = Color.TRANSPARENT;
+
+    /**
+     * Generate image and return path via callback
+     */
+    public static void generateImage(final View imageView, final int width,
+                                     @ColorInt final int backgroundColor, final OnImageSavedCallback mOnImageSavedCallback) {
+
+        mBackgroundColor = backgroundColor;
+
+        // Only one save image task occurs at the same time
+        WXSDKManager.getInstance().getWXWorkThreadManager().post(new Thread(new Runnable() {
+            @Override
+            public void run() {
+                // Generate bitmap from ImageView
+                Bitmap bitmap = getBitmapFromImageView(imageView, width);
+
+                if (bitmap == null) {
+                    if (mOnImageSavedCallback != null) {
+                        mOnImageSavedCallback.onSaveFailed("Image is empty");
+                    }
+                    return;
+                }
+
+                // Sava bitmap to gallery
+                final String destPath = saveBitmapToGallery(imageView.getContext(), bitmap, mOnImageSavedCallback);
+
+                new Handler(Looper.getMainLooper()).post(new Runnable() {
+                    @Override
+                    public void run() {
+                        if (mOnImageSavedCallback != null) {
+                            mOnImageSavedCallback.onSaveSucceed(destPath);
+                            imageView.getContext().sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.parse(destPath)));
+                        }
+                    }
+                });
+            }
+        }));
+    }
+
+    /**
+     * Save bitmap to gallery
+     * @return image save path
+     */
+    public static String saveBitmapToGallery(Context context, Bitmap bitmap, final OnImageSavedCallback mOnImageSavedCallback) {
+
+        // Save image
+        File appDir = new File(Environment.getExternalStorageDirectory(), "Weex");
+        if (!appDir.exists()) {
+            appDir.mkdir();
+        }
+
+        String fileName = System.currentTimeMillis() + ".jpg";
+        File file = new File(appDir, fileName);
+
+        try {
+            FileOutputStream fos = new FileOutputStream(file);
+            bitmap.compress(Bitmap.CompressFormat.JPEG, 100, fos);
+            fos.flush();
+            fos.close();
+        } catch (FileNotFoundException e) {
+            if (mOnImageSavedCallback != null)
+                mOnImageSavedCallback.onSaveFailed("Image creation failed due to system reason");
+            e.printStackTrace();
+        } catch (IOException e) {
+            if (mOnImageSavedCallback != null)
+                mOnImageSavedCallback.onSaveFailed("Android IOException");
+            e.printStackTrace();
+        }
+
+        // Insert the image file into the system gallery
+        try {
+            MediaStore.Images.Media.insertImage(context.getContentResolver(),
+                    file.getAbsolutePath(), fileName, null);
+        } catch (FileNotFoundException e) {
+            e.printStackTrace();
+        }
+
+        // Notify the system gallery update
+        context.sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, Uri.parse("file://" + appDir.getAbsolutePath() + "/" + fileName)));
+
+        return file.getAbsolutePath();
+    }
+
+    /**
+     * Save state callback
+     */
+    public interface OnImageSavedCallback {
+        void onSaveSucceed(String path);
+        void onSaveFailed(String errorDesc);
+    }
+
+    /**
+     * Get bitmap from imageview
+     */
+    public static Bitmap getBitmapFromImageView(final View view, int width) {
+        if (view.getWidth() <= 0 || view.getHeight() <= 0) {
+            view.measure(View.MeasureSpec.makeMeasureSpec(width, View.MeasureSpec.EXACTLY),
+                    View.MeasureSpec.makeMeasureSpec(0, View.MeasureSpec.UNSPECIFIED));
+            view.layout(0, 0, view.getMeasuredWidth(), view.getMeasuredHeight());
+        }
+
+        view.setDrawingCacheEnabled(true);
+        Bitmap bitmap = view.getDrawingCache();
+        return bitmap;
+    }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXViewUtils.java b/android/sdk/src/main/java/org/apache/weex/utils/WXViewUtils.java
new file mode 100644
index 0000000..a01176c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXViewUtils.java
@@ -0,0 +1,598 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.annotation.SuppressLint;
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.Paint;
+import android.graphics.Path;
+import android.graphics.PixelFormat;
+import android.graphics.Point;
+import android.graphics.RectF;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.ColorDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.LayerDrawable;
+import android.os.Build;
+import android.os.Build.VERSION_CODES;
+import android.support.annotation.IntDef;
+import android.support.annotation.NonNull;
+import android.support.annotation.Nullable;
+import android.util.DisplayMetrics;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.ViewGroup.LayoutParams;
+import android.view.WindowManager;
+
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+import org.apache.weex.WXSDKManager;
+import org.apache.weex.common.Constants;
+import org.apache.weex.common.WXErrorCode;
+import org.apache.weex.common.WXRuntimeException;
+import org.apache.weex.ui.component.WXComponent;
+import org.apache.weex.ui.flat.widget.Widget;
+import org.apache.weex.ui.flat.widget.WidgetGroup;
+import org.apache.weex.ui.view.border.BorderDrawable;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.util.concurrent.atomic.AtomicInteger;
+
+/**
+ * Utility class for views
+ */
+public class WXViewUtils {
+
+  @IntDef({PixelFormat.TRANSLUCENT, PixelFormat.TRANSPARENT, PixelFormat.OPAQUE})
+  @Retention(RetentionPolicy.SOURCE)
+  public @interface Opacity {}
+
+  /**
+   * Use {@link PixelFormat#TRANSLUCENT} instead
+   */
+  @Deprecated
+  public static final int TRANSLUCENT = PixelFormat.TRANSLUCENT;
+
+  /**
+   * Use {@link PixelFormat#TRANSPARENT} instead.
+   */
+  @Deprecated
+  public static final int TRANSPARENT = PixelFormat.TRANSPARENT;
+
+  /**
+   * Use {@link PixelFormat#OPAQUE} instead
+   */
+  @Deprecated
+  public static final int OPAQUE = PixelFormat.OPAQUE;
+
+  public static final int DIMENSION_UNSET = -1;
+  private static final boolean mUseWebPx = false;
+
+  private static final AtomicInteger sNextGeneratedId = new AtomicInteger(1);
+
+  @SuppressLint("NewApi")
+  public static int generateViewId() {
+
+    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR1) {
+      for (;;) {
+        final int result = sNextGeneratedId.get();
+        // aapt-generated IDs have the high byte nonzero; clamp to the range under that.
+        int newValue = result + 1;
+        if (newValue > 0x00FFFFFF)
+          newValue = 1; // Roll over to 1, not 0.
+        if (sNextGeneratedId.compareAndSet(result, newValue)) {
+          return result;
+        }
+      }
+    } else {
+      return View.generateViewId();
+    }
+  }
+
+  private static int mScreenWidth;
+  private static int mScreenHeight;
+
+
+  public static int getWeexHeight(String instanceId){
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (instance != null) {
+      int weexHeight = instance.getWeexHeight();
+      if (weexHeight >= 0 || weexHeight == -2) {
+        return weexHeight;
+      }
+      else {
+        return getScreenHeight(WXEnvironment.sApplication);
+      }
+    }
+    return -3;
+  }
+
+
+
+  public static int getWeexWidth(String instanceId){
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    if (instance != null) {
+      int weexWidth = instance.getWeexWidth();
+      if (weexWidth >= 0 || weexWidth == -2) {
+        return weexWidth;
+      }
+      else {
+        return getScreenWidth(WXEnvironment.sApplication);
+      }
+    }
+    return -3;
+  }
+
+  @Deprecated
+  public static int getScreenWidth( ) {
+    return getScreenWidth(WXEnvironment.sApplication);
+  }
+
+  @Deprecated
+  public static int setScreenWidth(int screenWidth) {
+    return mScreenWidth = screenWidth;
+  }
+
+  public static float getScreenDensity(Context ctx){
+    if(ctx != null){
+      try{
+        Resources res = ctx.getResources();
+        return res.getDisplayMetrics().density;
+      }catch (Exception e){
+        WXLogUtils.e("getScreenDensityDpi exception:"+e.getMessage());
+      }
+    }
+    return Constants.Value.DENSITY;
+  }
+
+  public static void updateApplicationScreen(Context context){
+    if(context == null || WXEnvironment.sApplication == null){
+        return;
+    }
+    DisplayMetrics metrics = context.getResources().getDisplayMetrics();
+    DisplayMetrics displayMetrics = WXEnvironment.sApplication.getResources().getDisplayMetrics();
+    displayMetrics.heightPixels = metrics.heightPixels;
+    displayMetrics.widthPixels = metrics.widthPixels;
+    displayMetrics.density = metrics.density;
+    displayMetrics.densityDpi = metrics.densityDpi;
+    displayMetrics.scaledDensity = metrics.scaledDensity;
+    displayMetrics.xdpi = metrics.xdpi;
+  }
+
+  public static int getScreenWidth(Context ctx) {
+    if(ctx!=null){
+      Resources res = ctx.getResources();
+      mScreenWidth = res.getDisplayMetrics().widthPixels;
+      if(WXEnvironment.SETTING_FORCE_VERTICAL_SCREEN){
+        mScreenHeight = res
+                .getDisplayMetrics()
+                .heightPixels;
+        mScreenWidth = mScreenHeight > mScreenWidth ? mScreenWidth : mScreenHeight;
+      }
+    } else if(WXEnvironment.isApkDebugable()){
+      throw new WXRuntimeException("Error Context is null When getScreenHeight");
+    }
+    return mScreenWidth;
+  }
+
+
+  public static int getStatusBarHeight(Context context){
+      Resources resources = context.getResources();
+      int resourceId = resources.getIdentifier("status_bar_height", "dimen", "android");
+      if (resourceId > 0) {
+        int statusBarHeight = resources.getDimensionPixelSize(resourceId);
+        return statusBarHeight;
+      }
+      return -1;
+  }
+
+
+  @Deprecated
+  public static int getScreenHeight() {
+    return getScreenHeight(WXEnvironment.sApplication);
+  }
+
+
+  public static int getScreenHeight(String instanceId){
+    WXSDKInstance instance = WXSDKManager.getInstance().getSDKInstance(instanceId);
+    return instance.isFullScreenHeightEnabled()?getFullScreenHeight(WXEnvironment.sApplication):getScreenHeight(WXEnvironment.sApplication);
+  }
+
+//get screen height with status bar on full screen
+  public static int getFullScreenHeight(Context cxt) {
+    if(cxt!=null){
+      WindowManager wm;
+      Resources res = cxt.getResources();
+      if(Build.VERSION.SDK_INT >= 17 && (wm = (WindowManager)cxt.getSystemService(Context.WINDOW_SERVICE)) != null
+              && wm.getDefaultDisplay() != null){
+        Point size = new Point();
+        wm.getDefaultDisplay().getRealSize(size);
+        mScreenHeight = size.y;
+      }
+      else {
+        mScreenHeight = cxt.getResources().getDisplayMetrics().heightPixels;
+      }
+      if(WXEnvironment.SETTING_FORCE_VERTICAL_SCREEN){
+        mScreenWidth = res
+                .getDisplayMetrics()
+                .widthPixels;
+        mScreenHeight = mScreenHeight > mScreenWidth ? mScreenHeight : mScreenWidth;
+      }
+    } else if (WXEnvironment.isApkDebugable()){
+      throw new WXRuntimeException("Error Context is null When getScreenHeight");
+    }
+    return mScreenHeight;
+  }
+//  get screen height without status bar
+  public static int getScreenHeight(Context cxt) {
+    if(cxt!=null){
+      Resources res = cxt.getResources();
+      mScreenHeight = res.getDisplayMetrics().heightPixels;
+      if(WXEnvironment.SETTING_FORCE_VERTICAL_SCREEN){
+        mScreenWidth = res
+                .getDisplayMetrics()
+                .widthPixels;
+        mScreenHeight = mScreenHeight > mScreenWidth ? mScreenHeight : mScreenWidth;
+      }
+    } else if (WXEnvironment.isApkDebugable()){
+      throw new WXRuntimeException("Error Context is null When getScreenHeight");
+    }
+    return mScreenHeight;
+  }
+
+
+  /**
+   * Convert distance from JS,CSS to native. As the JS considers the width of the screen is 750px.
+   * There must be a transform when accessing distance from JS,CSS and use it.
+   * Basically, this method calculates a scale factor(ScreenWidth/750) and use apply this scale
+   * factor to JS,CSS distance.
+   * @param pxValue the raw distance from JS or CSS. The result will be rounded to a closet int.
+   * @return the actual distance in the screen.
+   */
+
+  @Deprecated
+  public static float getRealPxByWidth(float pxValue) {
+    return getRealPxByWidth(pxValue,750);
+  }
+  public static float getRealPxByWidth(float pxValue,int customViewport) {
+    if (Float.isNaN(pxValue)) {
+      return pxValue;
+    }
+    if (mUseWebPx) {
+      return (float) Math.rint(pxValue);
+    } else {
+      float realPx = (pxValue * getScreenWidth() / customViewport);
+      return realPx > 0.005 && realPx < 1 ? 1 : (float) Math.rint(realPx);
+    }
+  }
+
+  @Deprecated
+  public static float getRealSubPxByWidth(float pxValue) {
+    return getRealSubPxByWidth(pxValue,750);
+  }
+
+  public static float getRealSubPxByWidth(float pxValue,int customViewport) {
+    if (Float.isNaN(pxValue)) {
+      return pxValue;
+    }
+    if (mUseWebPx) {
+      return (float) Math.rint(pxValue);
+    } else {
+      float realPx = (pxValue * getScreenWidth() / customViewport);
+      return realPx > 0.005 && realPx < 1 ? 1 : realPx;
+    }
+  }
+
+  /**
+   *  Internal interface that just for debug, you should never call this method because of accuracy loss obviously
+   */
+  @Deprecated
+  public static float getWeexPxByReal(float pxValue) {
+    return getWeexPxByReal(pxValue,750);
+  }
+
+  public static float getWeexPxByReal(float pxValue,int customViewport) {
+    if (Float.isNaN(pxValue)) {
+      return pxValue;
+    }
+    if (mUseWebPx) {
+      return (float) Math.rint(pxValue);
+    } else {
+      return pxValue * customViewport / getScreenWidth();
+    }
+  }
+
+  @Deprecated
+  public static float getRealPxByWidth2(float pxValue) {
+    return getRealPxByWidth2(pxValue,750);
+  }
+  public static int getRealPxByWidth2(float pxValue,int customViewport) {
+    if (mUseWebPx) {
+      return (int) pxValue;
+    } else {
+      float realPx = (pxValue * getScreenWidth() / customViewport);
+      return realPx > 0.005 && realPx < 1 ? 1 : (int) realPx - 1;
+    }
+  }
+
+  /**
+   * Convert distance from native to JS,CSS. As the JS considers the width of the screen is 750px.
+   * There must be a transform when return distance to JS,CSS.
+   * Basically, this method calculates a scale factor(ScreenWidth/750) and use apply this scale
+   * factor to native distance.
+   * @param pxValue the raw distance of native. The result will be rounded to a closet int.
+   * @return the distance in JS,CSS where the screenWidth is 750 px.
+   */
+  @Deprecated
+  public static float getWebPxByWidth(float pxValue) {
+    return getWebPxByWidth(pxValue,750);
+  }
+
+  public static float getWebPxByWidth(float pxValue,int customViewport) {
+    if (pxValue < -1.9999 && pxValue > -2.005) {
+      return Float.NaN;
+    }
+    if (mUseWebPx) {
+      return pxValue;
+    } else {
+      float realPx = (pxValue * customViewport / getScreenWidth());
+      return realPx > 0.005 && realPx < 1 ? 1 : realPx;
+    }
+  }
+
+
+  /**
+   * Convert dp to px
+   * @param dpValue the dp value to be converted
+   * @return the px value
+   */
+  public static int dip2px(float dpValue) {
+    float scale = 2;
+    try {
+      scale = WXEnvironment.getApplication().getResources()
+              .getDisplayMetrics().density;
+    } catch (Exception e) {
+      WXLogUtils.e("[WXViewUtils] dip2px:", e);
+    }
+    float finalPx = (dpValue * scale + 0.5f);
+    return finalPx > 0 && finalPx < 1 ? 1 : (int) finalPx;
+  }
+
+  public static boolean onScreenArea(View view) {
+    if (view == null || view.getVisibility() != View.VISIBLE) {
+      return false;
+    }
+
+    int[] p = new int[2];
+    view.getLocationOnScreen(p);
+    LayoutParams lp = view.getLayoutParams();
+    int viewH = 0;
+    if (lp != null) {
+      viewH = lp.height;
+    } else {
+      viewH = view.getHeight();
+    }
+
+    return (p[1] > 0 && (p[1] - WXViewUtils.getScreenHeight(WXEnvironment.sApplication) < 0))
+            || (viewH + p[1] > 0 && p[1] <= 0);
+  }
+
+  /**
+   * Multiplies the color with the given alpha.
+   *
+   * @param color color to be multiplied
+   * @param alpha value between 0 and 255
+   * @return multiplied color
+   */
+  public static int multiplyColorAlpha(int color, int alpha) {
+    if (alpha == 255) {
+      return color;
+    }
+    if (alpha == 0) {
+      return color & 0x00FFFFFF;
+    }
+    alpha = alpha + (alpha >> 7); // make it 0..256
+    int colorAlpha = color >>> 24;
+    int multipliedAlpha = colorAlpha * alpha >> 8;
+    return (multipliedAlpha << 24) | (color & 0x00FFFFFF);
+  }
+
+  @Opacity
+  public static int getOpacityFromColor(int color) {
+    int colorAlpha = color >>> 24;
+    if (colorAlpha == 255) {
+      return PixelFormat.OPAQUE;
+    } else if (colorAlpha == 0) {
+      return PixelFormat.TRANSPARENT;
+    } else {
+      return PixelFormat.TRANSLUCENT;
+    }
+  }
+
+  @SuppressWarnings("deprecation")
+  public static void setBackGround(View view, Drawable drawable, WXComponent component) {
+    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN){
+      view.setBackgroundDrawable(drawable);
+    }
+    else{
+      try {
+        view.setBackground(drawable);
+      } catch (Exception e) {
+        if (component == null)
+          return;
+        WXExceptionUtils.commitCriticalExceptionRT(component.getInstanceId(),
+                WXErrorCode.WX_RENDER_ERR_TEXTURE_SETBACKGROUND,
+                component.getComponentType() + " setBackGround for android view",
+                WXErrorCode.WX_RENDER_ERR_TEXTURE_SETBACKGROUND.getErrorMsg() + ": TextureView doesn't support displaying a background drawable!",
+                null);
+      }
+    }
+  }
+
+  public static @Nullable
+  BorderDrawable getBorderDrawable(@NonNull View view){
+    Drawable drawable=view.getBackground();
+    if(drawable instanceof BorderDrawable){
+      return (BorderDrawable) drawable;
+    }
+    else if(drawable instanceof LayerDrawable){
+      if(((LayerDrawable) drawable).getNumberOfLayers()>1) {
+        Drawable innerDrawable=((LayerDrawable) drawable).getDrawable(0);
+        if(innerDrawable instanceof BorderDrawable){
+          return (BorderDrawable) innerDrawable;
+        }
+      }
+    }
+    return null;
+  }
+
+  public static void clipCanvasWithinBorderBox(View targetView, Canvas canvas) {
+    Drawable drawable;
+    if (clipCanvasDueToAndroidVersion(canvas) &&
+            clipCanvasIfAnimationExist(targetView) &&
+            ((drawable = targetView.getBackground()) instanceof BorderDrawable)) {
+      BorderDrawable borderDrawable = (BorderDrawable) drawable;
+      if (borderDrawable.isRounded()) {
+        if (clipCanvasIfBackgroundImageExist(targetView, borderDrawable)) {
+          Path path = borderDrawable.getContentPath(
+                  new RectF(0, 0, targetView.getWidth(), targetView.getHeight()));
+          canvas.clipPath(path);
+        }
+      }
+    }
+  }
+
+  public static void clipCanvasWithinBorderBox(Widget widget, Canvas canvas) {
+    BorderDrawable borderDrawable;
+    if (clipCanvasDueToAndroidVersion(canvas) &&
+            clipCanvasIfAnimationExist(null) &&
+            (borderDrawable=widget.getBackgroundAndBorder())!=null ) {
+      if (borderDrawable.isRounded() && clipCanvasIfBackgroundImageExist(widget, borderDrawable)) {
+        Path path = borderDrawable.getContentPath(
+                new RectF(0, 0, widget.getBorderBox().width(), widget.getBorderBox().height()));
+        canvas.clipPath(path);
+      }
+      else {
+        canvas.clipRect(widget.getBorderBox());
+      }
+    }
+  }
+
+  /**
+   * According to https://developer.android.com/guide/topics/graphics/hardware-accel.html#unsupported
+   API 18 or higher supports clipPath to canvas based on hardware acceleration.
+   * @param canvas
+   * @return
+   */
+  private static boolean clipCanvasDueToAndroidVersion(Canvas canvas) {
+    return Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2 ||
+            !canvas.isHardwareAccelerated();
+  }
+
+  /**
+   * According to https://code.google.com/p/android/issues/detail?id=225556&sort=-id&colspec=ID
+   * clipPath doesn't work with rotation nor scale when API level is 24.
+   * As animation will not cause redraw if hardware-acceleration enabled, clipCanvas feature has
+   * to be disabled when API level is 24 without considering the animation property.
+   */
+  private static boolean clipCanvasIfAnimationExist(View targetView) {
+    if (Build.VERSION.SDK_INT != VERSION_CODES.N) {
+      return true;
+    } else {
+      return false;
+    }
+  }
+
+  /**
+   * Due limitation in Android platform, the linear gradient in the following page will not be
+   * rounded if {@link Canvas#clipPath(Path)} of the parent view invoked when API level is lower
+   * than 21.
+   * http://dotwe.org/weex/963c9ade129f86757cecdd85651cd30e
+   * @param targetView
+   * @param borderDrawable
+   * @return
+   */
+  private static boolean clipCanvasIfBackgroundImageExist(@NonNull View targetView,
+                                                          @NonNull BorderDrawable borderDrawable) {
+    if (targetView instanceof ViewGroup) {
+      View child;
+      ViewGroup parent = ((ViewGroup) targetView);
+      int count = parent.getChildCount();
+      for (int i = 0; i < count; i++) {
+        child = parent.getChildAt(i);
+        if (child.getBackground() instanceof BorderDrawable &&
+                ((BorderDrawable) child.getBackground()).hasImage() &&
+                Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
+          return false;
+        }
+      }
+    }
+    return true;
+  }
+
+  private static boolean clipCanvasIfBackgroundImageExist(@NonNull Widget widget,
+                                                          @NonNull BorderDrawable borderDrawable) {
+    if (widget instanceof WidgetGroup) {
+      for (Widget child : ((WidgetGroup) widget).getChildren()) {
+        if (child.getBackgroundAndBorder().hasImage() &&
+                Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
+          return false;
+        }
+      }
+    }
+    return true;
+  }
+
+  public static boolean isViewVisible(View v) {
+    if (null == v){
+      return false;
+    }
+
+    boolean isAttachToWindow = Build.VERSION.SDK_INT >= VERSION_CODES.KITKAT
+        ?v.isAttachedToWindow()
+        :v.getWindowToken() != null;
+
+    if (!isAttachToWindow){
+      return false;
+    }
+    if (v.getVisibility() != View.VISIBLE || v.getAlpha()<=0){
+      return false;
+    }
+
+    Drawable bacDrawable = v.getBackground();
+    if (null == bacDrawable){
+      return true;
+    }
+    if (Build.VERSION.SDK_INT >= VERSION_CODES.KITKAT){
+      return bacDrawable.getAlpha()>0;
+    }
+    //< 4.4
+    if (bacDrawable instanceof ColorDrawable){
+      int alpha = Color.alpha(((ColorDrawable) bacDrawable).getColor());
+      return alpha >0;
+    }else if (bacDrawable instanceof BitmapDrawable){
+      Paint paint = ((BitmapDrawable) bacDrawable).getPaint();
+      return paint.getAlpha() > 0;
+    }
+    return true;
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/WXWsonJSONSwitch.java b/android/sdk/src/main/java/org/apache/weex/utils/WXWsonJSONSwitch.java
new file mode 100644
index 0000000..7676a07
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/WXWsonJSONSwitch.java
@@ -0,0 +1,128 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils;
+
+import android.support.annotation.NonNull;
+
+import com.alibaba.fastjson.JSON;
+import org.apache.weex.bridge.WXJSObject;
+import org.apache.weex.wson.Wson;
+import org.apache.weex.wson.WsonUtils;
+
+/**
+ * Created by furture on 2018/5/17.
+ */
+
+public class WXWsonJSONSwitch {
+
+    private static final String TAG = "WXSwitch";
+
+    /**
+     * switch input data to target according to config, if not use wson return normal data
+     * */
+    public static  final byte[] convertJSONToWsonIfUseWson(byte[] json){
+        if(!USE_WSON){
+            return json;
+        }
+        if(json == null){
+            return null;
+        }
+        String str = new String(json);
+        if(str.startsWith("[")){
+            return WsonUtils.toWson(JSON.parseArray(str));
+        }
+        return WsonUtils.toWson(JSON.parse(str));
+    }
+
+    /**
+     * parse json or wson data by config switch
+     * */
+    public static final Object parseWsonOrJSON(byte[] data){
+        if(data == null){
+            return  null;
+        }
+        try{
+            if(USE_WSON){
+                return  Wson.parse(data);
+            }else{
+                return  JSON.parse(new String(data, "UTF-8"));
+            }
+        }catch (Exception e){
+            WXLogUtils.e(TAG, e);
+            if(USE_WSON){  //fallback
+                return  JSON.parse(new String(data));
+            }else{
+                return Wson.parse(data);
+            }
+        }
+    }
+
+    /**
+     * to wson or wson WXJSObject
+     * */
+    public static final WXJSObject toWsonOrJsonWXJSObject(Object tasks){
+        if(tasks == null){
+            return new WXJSObject(null);
+        }
+        if(tasks.getClass() == WXJSObject.class){
+            return (WXJSObject) tasks;
+        }
+        if(USE_WSON) {
+            return new WXJSObject(WXJSObject.WSON, Wson.toWson(tasks));
+        }else{
+            return new WXJSObject(WXJSObject.JSON, WXJsonUtils.fromObjectToJSONString(tasks));
+        }
+    }
+
+
+    public static  final Object convertWXJSObjectDataToJSON(WXJSObject object){
+        if(object.type == WXJSObject.WSON){
+            return JSON.parse(Wson.parse((byte[]) object.data).toString());
+        }else{
+            return JSON.parse(object.data.toString());
+        }
+    }
+
+
+
+    /**
+     * config whether use json or wson,  you should update this value by updateGlobalConfig(String config)
+     * in WXBridgeManager class  method
+     * */
+    public static  boolean USE_WSON = true;
+
+
+    /**wson off */
+    public static final String WSON_OFF = "wson_off";
+
+
+    public @NonNull
+    static String fromObjectToJSONString(WXJSObject obj) {
+        if(obj != null && obj.type == WXJSObject.WSON){
+            Object data = Wson.parse((byte[]) obj.data);
+            if(data != null){
+                return  data.toString();
+            }
+        }
+        return WXJsonUtils.fromObjectToJSONString(obj,false);
+    }
+
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/batch/BactchExecutor.java b/android/sdk/src/main/java/org/apache/weex/utils/batch/BactchExecutor.java
new file mode 100644
index 0000000..6024dec
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/batch/BactchExecutor.java
@@ -0,0 +1,28 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils.batch;
+
+/**
+ * Created by sospartan on 8/24/16.
+ */
+public interface BactchExecutor {
+  void post(Runnable runnable);
+
+  void setInterceptor(Interceptor interceptor);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/batch/BatchOperationHelper.java b/android/sdk/src/main/java/org/apache/weex/utils/batch/BatchOperationHelper.java
new file mode 100644
index 0000000..b8d75c2
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/batch/BatchOperationHelper.java
@@ -0,0 +1,68 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils.batch;
+
+import java.util.Iterator;
+import java.util.concurrent.CopyOnWriteArrayList;
+
+/**
+ * Created by sospartan on 8/24/16.
+ */
+public class BatchOperationHelper implements Interceptor {
+
+
+  private BactchExecutor mExecutor;
+  private CopyOnWriteArrayList<Runnable> sRegisterTasks = new CopyOnWriteArrayList<>();
+  private boolean isCollecting = false;
+
+  public BatchOperationHelper(BactchExecutor executor){
+    mExecutor = executor;
+    executor.setInterceptor(this);
+    isCollecting = true;
+  }
+
+  @Override
+  public boolean take(Runnable runnable) {
+    if(isCollecting){
+      sRegisterTasks.add(runnable);
+      return true;
+    }
+    return false;
+  }
+
+  /**
+   * Post all tasks to executor. Can only be called once.
+   */
+  public void flush(){
+    isCollecting = false;
+    mExecutor.post(new Runnable() {
+      @Override
+      public void run() {
+        Iterator<Runnable> iterator = sRegisterTasks.iterator();
+        while(iterator.hasNext()){
+          Runnable item = iterator.next();
+          item.run();
+//          iterator.remove();
+          sRegisterTasks.remove(item);
+        }
+      }
+    });
+    mExecutor.setInterceptor(null);
+  }
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/batch/Interceptor.java b/android/sdk/src/main/java/org/apache/weex/utils/batch/Interceptor.java
new file mode 100644
index 0000000..a63142c
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/batch/Interceptor.java
@@ -0,0 +1,26 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+package org.apache.weex.utils.batch;
+
+/**
+ * Created by sospartan on 8/24/16.
+ */
+public interface Interceptor {
+  boolean take(Runnable runnable);
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/cache/RegisterCache.java b/android/sdk/src/main/java/org/apache/weex/utils/cache/RegisterCache.java
new file mode 100644
index 0000000..d55e3ee
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/cache/RegisterCache.java
@@ -0,0 +1,181 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils.cache;
+
+import org.apache.weex.bridge.ModuleFactory;
+import org.apache.weex.bridge.WXModuleManager;
+import org.apache.weex.ui.IFComponentHolder;
+import org.apache.weex.ui.WXComponentRegistry;
+import org.apache.weex.ui.config.AutoScanConfigRegister;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+public class RegisterCache {
+    private static Map<String, ModuleCache> moduleCacheMap = new ConcurrentHashMap<>();
+    private static Map<String, ComponentCache> componentCacheMap = new ConcurrentHashMap<>();
+    private static RegisterCache registerCache;
+
+    private boolean enable = false;
+
+    private boolean enableAutoScan = true;
+
+    public static RegisterCache getInstance() {
+        if (registerCache == null) {
+            synchronized (RegisterCache.class) {
+                if (registerCache == null) {
+                    registerCache = new RegisterCache();
+                }
+            }
+        }
+        return registerCache;
+    }
+
+    private RegisterCache() {
+
+    }
+
+    private volatile boolean finished = false;
+
+    private volatile int doNotCacheSize = Integer.MAX_VALUE;
+
+    public void setEnable(boolean enable) {
+        this.enable = enable;
+    }
+
+    private boolean enableCache() {
+        return enable;
+    }
+
+    private boolean canCache() {
+        return enableCache()
+                && !finished
+                && getDoNotCacheSize() < 1;
+    }
+
+    public boolean enableAutoScan() {
+        return enableAutoScan;
+    }
+
+    public void setEnableAutoScan(boolean enableAutoScan) {
+        if(this.enableAutoScan != enableAutoScan) {
+            if(enableAutoScan) {
+                AutoScanConfigRegister.doScanConfig();
+            }
+            this.enableAutoScan = enableAutoScan;
+        }
+
+    }
+
+    private int getDoNotCacheSize() {
+        return doNotCacheSize--;
+    }
+
+    public void setDoNotCacheSize(int doNotCacheSize) {
+        this.doNotCacheSize = doNotCacheSize;
+    }
+
+    public boolean idle(boolean atCreateInstance) {
+        if (finished)
+            return true;
+
+        String message;
+        if(atCreateInstance) {
+            message = "idle from create instance";
+        } else {
+            message = "idle from external";
+        }
+
+        WXLogUtils.e(message + " cache size is " + (moduleCacheMap.size() + componentCacheMap.size()));
+
+        finished = true;
+        CacheComponentRegister();
+        CacheModuleRegister();
+        return true;
+    }
+
+    public boolean cacheModule(final String moduleName, final ModuleFactory factory, final boolean global) {
+        if (!canCache()) {
+            return false;
+        }
+        try {
+            moduleCacheMap.put(moduleName, new ModuleCache(moduleName, factory, global));
+        } catch (Exception e) {
+            return false;
+        }
+        return true;
+    }
+
+
+    public boolean cacheComponent(final String type, final IFComponentHolder holder, final Map<String, Object> componentInfo) {
+        if (!canCache()) {
+            return false;
+        }
+        try {
+            componentCacheMap.put(type, new ComponentCache(type, holder, componentInfo));
+        } catch (Exception e) {
+            return false;
+        }
+        return true;
+    }
+
+
+    private void CacheComponentRegister() {
+        if (componentCacheMap.isEmpty())
+            return;
+        WXComponentRegistry.registerComponent(componentCacheMap);
+    }
+
+
+    private void CacheModuleRegister() {
+        if (moduleCacheMap.isEmpty())
+            return;
+
+        WXModuleManager.registerModule(moduleCacheMap);
+    }
+
+    public class ModuleCache {
+        public final String name;
+        public final ModuleFactory factory;
+        public final boolean global;
+
+        ModuleCache(String moduleName, ModuleFactory factory, boolean global) {
+            this.name = moduleName;
+            this.factory = factory;
+            this.global = global;
+        }
+    }
+
+
+    public class ComponentCache {
+        public final String type;
+        public final IFComponentHolder holder;
+        public final Map<String, Object> componentInfo;
+
+        ComponentCache(String type, IFComponentHolder holder, Map<String, Object> componentInfo) {
+            this.type = type;
+            this.componentInfo = componentInfo;
+            this.holder = holder;
+        }
+    }
+
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/tools/Info.java b/android/sdk/src/main/java/org/apache/weex/utils/tools/Info.java
new file mode 100644
index 0000000..dd98213
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/tools/Info.java
@@ -0,0 +1,55 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils.tools;
+
+import com.alibaba.fastjson.annotation.JSONField;
+
+public class Info{
+
+	public Info() {
+		taskInfo = new TaskInfo();
+	}
+
+	@JSONField(name="instanceId")
+	public String instanceId;
+
+	@JSONField(name="taskName")
+	public String taskName;
+
+	@JSONField(name="taskInfo")
+	public TaskInfo taskInfo;
+
+	@JSONField(name="platform")
+	public String platform;
+
+	@JSONField(name="taskId")
+	public int taskId;
+
+	@Override
+ 	public String toString(){
+		return 
+			"Info : {" +
+			"instanceId = '" + instanceId + '\'' + 
+			",taskName = '" + taskName + '\'' + 
+			",taskInfo = '" + taskInfo + '\'' + 
+			",platform = '" + platform + '\'' + 
+			",taskId = '" + taskId + '\'' + 
+			"}";
+		}
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/tools/LogDetail.java b/android/sdk/src/main/java/org/apache/weex/utils/tools/LogDetail.java
new file mode 100644
index 0000000..81ff122
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/tools/LogDetail.java
@@ -0,0 +1,86 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils.tools;
+
+import android.text.TextUtils;
+import android.util.Log;
+
+import com.alibaba.fastjson.annotation.JSONField;
+import org.apache.weex.WXEnvironment;
+import java.util.Locale;
+
+public class LogDetail {
+    public static final String KeyWrod_Init = "Weex_Init";
+    public static final String KeyWords_Render = "Weex_Render";
+
+    public LogDetail() {
+        time = new Time();
+        info = new Info();
+    }
+
+    @JSONField(name = "time")
+    public Time time;
+
+    @JSONField(name = "Info")
+    public Info info;
+
+    @Override
+    public String toString() {
+        return
+                "taskName : " + info.taskName + " - LogDetail : {" +
+                        "time = '" + time + '\'' +
+                        ", info = '" + info + '\'' +
+                        "}";
+    }
+
+
+    public String keyWords = KeyWords_Render;
+
+    public void println() {
+        if(WXEnvironment.isPerf())
+        Log.e(TimeCalculator.TIMELINE_TAG," timeline " + this.keyWords + " java LogDetail: " + this.toString());
+    }
+
+    public void name(String name) {
+        time.constructor();
+        info.taskName = name;
+        if(!TextUtils.isEmpty(name)) {
+            String s = name.toLowerCase(Locale.ROOT);
+            if(s.contains("module")
+            || s.contains("component")
+                    || s.contains("framework")) {
+                this.keyWords = KeyWrod_Init;
+            }
+        }
+    }
+
+    public void keyWorkds(String keyWords) {
+        this.keyWords = keyWords;
+    }
+
+    public void taskStart() {
+        time.taskStart();
+    }
+
+    public void taskEnd() {
+        time.taskEnd();
+        println();
+    }
+
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/tools/LogSwitch.java b/android/sdk/src/main/java/org/apache/weex/utils/tools/LogSwitch.java
new file mode 100644
index 0000000..bc5c12a
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/tools/LogSwitch.java
@@ -0,0 +1,54 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils.tools;
+
+public class LogSwitch {
+
+    private int low_level = 4;
+    private int medium_level = 2;
+    private int high_level = 1;
+    private int log_switch = 0;
+    private boolean showLowLevelLog = false;
+    private boolean showMediumLevelLog = false;
+    private boolean showHighLevelLog = true;
+
+
+    public void setLog_switch() {
+        // Todo
+        // read prop
+
+        if (showLowLevelLog)
+            log_switch |= low_level;
+
+        if (showMediumLevelLog) {
+            log_switch |= medium_level;
+        }
+
+        if (showHighLevelLog) {
+            log_switch |= high_level;
+        }
+    }
+
+
+    public int getLog_switch() {
+        return log_switch;
+    }
+
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/tools/TaskInfo.java b/android/sdk/src/main/java/org/apache/weex/utils/tools/TaskInfo.java
new file mode 100644
index 0000000..34abfcf
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/tools/TaskInfo.java
@@ -0,0 +1,39 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils.tools;
+
+import com.alibaba.fastjson.annotation.JSONField;
+
+public class TaskInfo{
+
+	@JSONField(name="args")
+	public String args;
+
+	@JSONField(name="relateTaskId")
+	public int relateTaskId;
+
+	@Override
+ 	public String toString(){
+		return 
+			"TaskInfo{" + 
+			"args = '" + args + '\'' + 
+			",relateTaskId = '" + relateTaskId + '\'' + 
+			"}";
+		}
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/tools/Time.java b/android/sdk/src/main/java/org/apache/weex/utils/tools/Time.java
new file mode 100644
index 0000000..eb5a6c7
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/tools/Time.java
@@ -0,0 +1,83 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils.tools;
+
+import com.alibaba.fastjson.annotation.JSONField;
+
+public class Time {
+
+    @JSONField(name = "taskStart")
+    public long taskStart;
+
+    @JSONField(name = "execTime")
+    public long execTime;
+
+    @JSONField(name = "constructor")
+    public long constructor;
+
+    @JSONField(name = "destructor")
+    public long destructor;
+
+    @JSONField(name = "taskEnd")
+    public long taskEnd;
+
+    @JSONField(name = "waitTime")
+    public long waitTime;
+
+    @Override
+    public String toString() {
+        return
+                "time : {" +
+                        "constructor = '" + constructor + '\'' +
+                        ",taskStart = '" + taskStart + '\'' +
+                        ",execTime = '" + execTime + '\'' +
+                        ",waitTime = '" + waitTime + '\'' +
+                        ",destructor = '" + destructor + '\'' +
+                        ",taskEnd = '" + taskEnd + '\'' +
+                        "}";
+    }
+
+
+    protected void constructor() {
+        constructor = System.currentTimeMillis();
+    }
+
+    public void execTime() {
+        execTime = taskEnd - taskStart;
+    }
+
+    public void taskStart() {
+        taskStart = System.currentTimeMillis();
+    }
+
+    public void taskEnd() {
+        taskEnd = System.currentTimeMillis();
+        execTime();
+        destructor();
+    }
+
+    private void destructor() {
+        waitTime();
+        destructor = System.currentTimeMillis();
+    }
+
+    public void waitTime() {
+        waitTime = taskStart - constructor;
+    }
+}
\ No newline at end of file
diff --git a/android/sdk/src/main/java/org/apache/weex/utils/tools/TimeCalculator.java b/android/sdk/src/main/java/org/apache/weex/utils/tools/TimeCalculator.java
new file mode 100644
index 0000000..deb4809
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/utils/tools/TimeCalculator.java
@@ -0,0 +1,67 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.utils.tools;
+
+import android.util.Log;
+
+import com.alibaba.fastjson.JSON;
+import org.apache.weex.WXEnvironment;
+import org.apache.weex.WXSDKInstance;
+
+import java.util.concurrent.CopyOnWriteArrayList;
+
+public class TimeCalculator {
+
+    public static final String TIMELINE_TAG = "timeline";
+
+    public static final String PLATFORM_ANDROID = "Android";
+
+    private CopyOnWriteArrayList<LogDetail> logRecorder;
+    public TimeCalculator(WXSDKInstance instance) {
+        logRecorder = new CopyOnWriteArrayList<LogDetail>();
+    }
+
+    public void addLog(LogDetail logDetail) {
+        if(!WXEnvironment.isPerf()) {
+            return;
+        }
+        logRecorder.add(logDetail);
+    }
+
+    public LogDetail createLogDetail(String name) {
+        LogDetail logDetail = new LogDetail();
+        logDetail.name(name);
+        addLog(logDetail);
+        return logDetail;
+    }
+
+    public void println() {
+        if(!WXEnvironment.isPerf()) {
+            return;
+        }
+
+        for (LogDetail l: logRecorder) {
+            Log.e(TIMELINE_TAG, JSON.toJSONString(l));
+        }
+
+    }
+
+
+    private String test = "{\"time\":{\"execTime\":0,\"constructor\":0,\"destructor\":0,\"taskStart\":0,\"taskEnd\":0,\"waitTime\":0},\"Info\":{\"taskInfo\":{\"relateTaskId\":0,\"args\":\"stringReplace\"},\"taskName\":\"stringReplace\",\"instanceId\":\"1\",\"platform\":\"stringReplace\",\"taskId\":0}}";
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/wson/Wson.java b/android/sdk/src/main/java/org/apache/weex/wson/Wson.java
new file mode 100644
index 0000000..4d1098b
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/wson/Wson.java
@@ -0,0 +1,820 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.wson;
+
+
+import android.support.v4.util.LruCache;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.alibaba.fastjson.annotation.JSONField;
+import org.apache.weex.utils.WXLogUtils;
+
+import java.lang.reflect.Array;
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
+import java.lang.reflect.Modifier;
+import java.math.BigDecimal;
+import java.math.BigInteger;
+import java.nio.ByteOrder;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Calendar;
+import java.util.Collection;
+import java.util.Date;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * fast binary json format for parse map and serialize map
+ * Created by efurture on 2017/8/16.
+ */
+public class Wson {
+
+    /**
+     * skip map null values
+     * */
+    public static final boolean WriteMapNullValue = false;
+    /**
+     * wson data type
+     * */
+    private static final byte NULL_TYPE = '0';
+
+    private static final byte STRING_TYPE = 's';
+
+    private static final byte BOOLEAN_TYPE_TRUE = 't';
+
+    private static final byte BOOLEAN_TYPE_FALSE = 'f';
+
+    private static final byte NUMBER_INT_TYPE = 'i';
+
+    private static final byte NUMBER_LONG_TYPE = 'l';
+
+    private static final byte NUMBER_BIG_INTEGER_TYPE = 'g';
+
+    private static final byte NUMBER_BIG_DECIMAL_TYPE = 'e';
+
+    private static final byte NUMBER_DOUBLE_TYPE = 'd';
+
+    private static final byte NUMBER_FLOAT_TYPE = 'F';
+
+    private static final byte ARRAY_TYPE = '[';
+
+    private static final byte MAP_TYPE = '{';
+
+    /**
+     * StringUTF-16, byte order with native byte order
+     * */
+    private static final boolean IS_NATIVE_LITTLE_ENDIAN = (ByteOrder.nativeOrder() == ByteOrder.LITTLE_ENDIAN);
+
+
+    /**
+     * parse wson data  to object, please use WXJsonUtils.parseWson
+     * @param  data  byte array
+     * */
+    public static final Object parse(byte[] data){
+        if(data == null){
+            return  null;
+        }
+        try{
+            Parser parser =  new Parser(data);
+            Object object = parser.parse();
+            parser.close();
+            return object;
+        }catch (Exception e){
+            WXLogUtils.e("parseWson", e);
+            return  null;
+        }
+    }
+
+
+    /**
+     * serialize object to wson data, please use WXJsonUtils.toWsonOrJsonWXJSObject
+     * */
+    public static final byte[] toWson(Object object){
+        if(object == null){
+            return  null;
+        }
+        Builder builder = new Builder();
+        byte[]  bts  = builder.toWson(object);
+        builder.close();
+        return bts;
+    }
+
+
+    /**
+     * wson data parser
+     * */
+    private static final class Parser {
+
+        private int position = 0;
+        private byte[] buffer;
+        private char[]  charsBuffer;
+
+        private Parser(byte[] buffer) {
+            this.buffer = buffer;
+            charsBuffer = localCharsBufferCache.get();
+            if(charsBuffer != null){
+                localCharsBufferCache.set(null);
+            }else{
+                charsBuffer = new char[512];
+            }
+        }
+
+
+        private   final Object parse(){
+            return  readObject();
+        }
+
+        private final void close(){
+            position = 0;
+            buffer = null;
+            if(charsBuffer != null){
+                localCharsBufferCache.set(charsBuffer);
+            }
+            charsBuffer = null;
+        }
+
+        private final Object readObject(){
+            byte type  = readType();
+            switch (type){
+                case STRING_TYPE:
+                    return readUTF16String();
+                case NUMBER_INT_TYPE :
+                    return  readVarInt();
+                case NUMBER_FLOAT_TYPE :
+                    return  readFloat();
+                case MAP_TYPE:
+                    return readMap();
+                case ARRAY_TYPE:
+                    return readArray();
+                case NUMBER_DOUBLE_TYPE :
+                    return readDouble();
+                case NUMBER_LONG_TYPE :
+                    return  readLong();
+                case NUMBER_BIG_INTEGER_TYPE :
+                    return  new BigInteger(readUTF16String());
+                case NUMBER_BIG_DECIMAL_TYPE :
+                    return  new BigDecimal(readUTF16String());
+                case BOOLEAN_TYPE_FALSE:
+                    return  Boolean.FALSE;
+                case BOOLEAN_TYPE_TRUE:
+                    return  Boolean.TRUE;
+                case NULL_TYPE:
+                    return  null;
+                default:
+                    throw new RuntimeException("wson unhandled type " + type + " " +
+                            position  +  " length " + buffer.length);
+            }
+        }
+
+
+
+        private final Object readMap(){
+            int size = readUInt();
+            Map<String, Object> object = new JSONObject();;
+            for(int i=0; i<size; i++){
+                String key = readMapKeyUTF16();
+                Object value = readObject();
+                object.put(key, value);
+            }
+            return object;
+        }
+
+        private final Object readArray(){
+            int length = readUInt();
+            List<Object> array = new JSONArray(length);
+            for(int i=0; i<length; i++){
+                array.add(readObject());
+            }
+            return  array;
+        }
+
+        private  final byte readType(){
+            byte type = buffer[position];
+            position ++;
+            return  type;
+        }
+
+
+        private final String readMapKeyUTF16() {
+            int length = readUInt();
+            length = length/2;
+            if(charsBuffer.length < length){
+                charsBuffer = new char[length];
+            }
+            int hash = 5381;
+            if(IS_NATIVE_LITTLE_ENDIAN){
+                for(int i=0; i<length; i++){
+                    char ch = (char) ((buffer[position] & 0xFF) +
+                            (buffer[position + 1] << 8));
+                    charsBuffer[i] = (ch);
+                    hash = ((hash << 5) + hash)  + ch;
+                    position+=2;
+                }
+            }else{
+                for(int i=0; i<length; i++){
+                    char ch = (char) ((buffer[position + 1] & 0xFF) +
+                            (buffer[position] << 8));
+                    charsBuffer[i] = (ch);
+                    hash = ((hash << 5) + hash)  + ch;
+                    position+=2;
+                }
+            }
+            int globalIndex = (globalStringBytesCache.length - 1)&hash;
+            String cache = globalStringBytesCache[globalIndex];
+            if(cache != null
+                    && cache.length() == length){
+                boolean isStringEqual  = true;
+                for(int i=0; i<length; i++){
+                    if(charsBuffer[i] != cache.charAt(i)){
+                        isStringEqual = false;
+                        break;
+                    }
+                }
+                if(isStringEqual) {
+                    return cache;
+                }
+            }
+            cache = new String(charsBuffer, 0, length);
+            if(length < 64) {
+                globalStringBytesCache[globalIndex] = cache;
+            }
+            return  cache;
+        }
+
+        private final String readUTF16String(){
+            int length = readUInt()/2;
+            if(charsBuffer.length < length){
+                charsBuffer = new char[length];
+            }
+            if(IS_NATIVE_LITTLE_ENDIAN){
+                for(int i=0; i<length; i++){
+                    char ch = (char) ((buffer[position] & 0xFF) +
+                            (buffer[position + 1] << 8));
+                    charsBuffer[i] = (ch);
+                    position+=2;
+                }
+            }else{
+                for(int i=0; i<length; i++){
+                    char ch = (char) ((buffer[position + 1] & 0xFF) +
+                            (buffer[position] << 8));
+                    charsBuffer[i] = (ch);
+                    position+=2;
+                }
+            }
+            return  new String(charsBuffer, 0, length);
+        }
+
+
+
+
+
+        private   final int readVarInt(){
+            int raw = readUInt();
+            // This undoes the trick in putVarInt()
+            int num = (((raw << 31) >> 31) ^ raw) >> 1;
+            // This extra step lets us deal with the largest signed values by treating
+            // negative results from read unsigned methods as like unsigned values.
+            // Must re-flip the top bit if the original read value had it set.
+            return num ^ (raw & (1 << 31));
+        }
+
+        private final  int readUInt(){
+            int value = 0;
+            int i = 0;
+            int b;
+            while (((b = buffer[position]) & 0x80) != 0) {
+                value |= (b & 0x7F) << i;
+                i += 7;
+                position+=1;
+                if (i > 35) {
+                    throw new IllegalArgumentException("Variable length quantity is too long");
+                }
+            }
+            position+=1;
+            return value | (b << i);
+        }
+
+        private final long readLong(){
+            long number = (((buffer[position + 7] & 0xFFL)      ) +
+                    ((buffer[position + 6] & 0xFFL) <<  8) +
+                    ((buffer[position + 5] & 0xFFL) << 16) +
+                    ((buffer[position + 4] & 0xFFL) << 24) +
+                    ((buffer[position + 3] & 0xFFL) << 32) +
+                    ((buffer[position + 2] & 0xFFL) << 40) +
+                    ((buffer[position + 1] & 0xFFL) << 48) +
+                    (((long) buffer[position])      << 56));
+            position += 8;
+            return  number;
+        }
+
+        private  final Object readDouble(){
+            double number = Double.longBitsToDouble(readLong());
+            if(number > Integer.MAX_VALUE){
+                long numberLong = (long) number;
+                double doubleLong = (numberLong);
+                if(number - doubleLong < Double.MIN_NORMAL){
+                    return numberLong;
+                }
+            }
+            return  number;
+        }
+
+        private Object readFloat() {
+            int number = (((buffer[position + 3] & 0xFF)      ) +
+                    ((buffer[position + 2] & 0xFF) <<  8) +
+                    ((buffer[position + 1] & 0xFF) << 16) +
+                    ((buffer[position  ] & 0xFF) << 24));
+            position +=4;
+            return  Float.intBitsToFloat(number);
+        }
+    }
+
+    /**
+     * wson builder
+     * */
+    private static final class Builder {
+
+        private byte[] buffer;
+        private int position;
+        private ArrayList refs;
+        private final static ThreadLocal<byte[]> bufLocal = new ThreadLocal<byte[]>();
+        private final static ThreadLocal<ArrayList> refsLocal = new ThreadLocal<ArrayList>();
+
+
+
+        private Builder(){
+            buffer =  bufLocal.get();
+            if(buffer != null) {
+                bufLocal.set(null);
+            }else{
+                buffer = new byte[1024];
+            }
+            refs = refsLocal.get();
+            if(refs != null){
+                refsLocal.set(null);
+            }else{
+                refs = new ArrayList<>(16);
+            }
+        }
+
+
+        private final byte[] toWson(Object object){
+            writeObject(object);
+            byte[] bts = new byte[position];
+            System.arraycopy(buffer, 0, bts, 0, position);
+            return  bts;
+        }
+
+        private final void close(){
+            if(buffer.length <= 1024*16){
+                bufLocal.set(buffer);
+            }
+            if(refs.isEmpty()){
+                refsLocal.set(refs);
+            }else{
+                refs.clear();
+            }
+            refs = null;
+            buffer = null;
+            position = 0;
+        }
+
+        private final void writeObject(Object object) {
+            if(object instanceof  CharSequence){
+                ensureCapacity(2);
+                writeByte(STRING_TYPE);
+                writeUTF16String((CharSequence) object);
+                return;
+            }else if (object instanceof Map){
+                if(refs.contains(object)){
+                    ensureCapacity(2);
+                    writeByte(NULL_TYPE);
+                    return;
+                }
+                refs.add(object);
+                Map map = (Map) object;
+                writeMap(map);
+                refs.remove(refs.size()-1);
+                return;
+            }else if (object instanceof List){
+                if(refs.contains(object)){
+                    ensureCapacity(2);
+                    writeByte(NULL_TYPE);
+                    return;
+                }
+                refs.add(object);
+                ensureCapacity(8);
+                List list = (List) object;
+                writeByte(ARRAY_TYPE);
+                writeUInt(list.size());
+                for(Object value : list){
+                    writeObject(value);
+                }
+                refs.remove(refs.size()-1);
+                return;
+            }else if (object instanceof Number){
+                Number number = (Number) object;
+                writeNumber(number);
+                return;
+            }else if (object instanceof  Boolean){
+                ensureCapacity(2);
+                Boolean value  = (Boolean) object;
+                if(value){
+                    writeByte(BOOLEAN_TYPE_TRUE);
+                }else{
+                    writeByte(BOOLEAN_TYPE_FALSE);
+                }
+                return;
+            }else if(object == null){
+                ensureCapacity(2);
+                writeByte(NULL_TYPE);
+                return;
+            }else if (object.getClass().isArray()){
+                if(refs.contains(object)){
+                    ensureCapacity(2);
+                    writeByte(NULL_TYPE);
+                    return;
+                }
+                refs.add(object);
+                ensureCapacity(8);
+                int length = Array.getLength(object);
+                writeByte(ARRAY_TYPE);
+                writeUInt(length);
+                for(int i=0; i<length; i++){
+                    Object value = Array.get(object, i);
+                    writeObject(value);
+                }
+                refs.remove(refs.size()-1);
+                return;
+            }else  if(object instanceof  Date){
+                ensureCapacity(10);
+                double date = ((Date)object).getTime();
+                writeByte(NUMBER_DOUBLE_TYPE);
+                writeDouble(date);
+            }else  if(object instanceof  Calendar){
+                ensureCapacity(10);
+                double date = ((Calendar)object).getTime().getTime();
+                writeByte(NUMBER_DOUBLE_TYPE);
+                writeDouble(date);
+            }else  if(object instanceof  Collection){
+                if(refs.contains(object)){
+                    ensureCapacity(2);
+                    writeByte(NULL_TYPE);
+                    return;
+                }
+                refs.add(object);
+                ensureCapacity(8);
+                Collection list = (Collection) object;
+                writeByte(ARRAY_TYPE);
+                writeUInt(list.size());
+                for(Object value : list){
+                    writeObject(value);
+                }
+                refs.remove(refs.size()-1);
+            }else{
+                if(refs.contains(object)){
+                    ensureCapacity(2);
+                    writeByte(NULL_TYPE);
+                }else {
+                    refs.add(object);
+                    if(object.getClass().isEnum()){
+                        writeObject(JSON.toJSONString(object));
+                    }else{
+                        writeAdapterObject(object);
+                    }
+                    refs.remove(refs.size()-1);
+                }
+                return;
+            }
+        }
+
+        private final void writeNumber(Number number) {
+            ensureCapacity(12);
+            if(number instanceof  Integer){
+                writeByte(NUMBER_INT_TYPE);
+                writeVarInt(number.intValue());
+                return;
+            }
+
+            if(number instanceof Float){
+                writeByte(NUMBER_FLOAT_TYPE);
+                writeFloat(number.floatValue());
+                return;
+            }
+            if(number instanceof  Double){
+                writeByte(NUMBER_DOUBLE_TYPE);
+                writeDouble(number.doubleValue());
+                return;
+            }
+
+            if(number instanceof  Long){
+                writeByte(NUMBER_LONG_TYPE);
+                writeLong(number.longValue());
+                return;
+            }
+
+            if(number instanceof  Short
+                    || number instanceof  Byte){
+                writeByte(NUMBER_INT_TYPE);
+                writeVarInt(number.intValue());
+                return;
+            }
+
+            if(number instanceof BigInteger){
+                writeByte(NUMBER_BIG_INTEGER_TYPE);
+                writeUTF16String(number.toString());
+                return;
+            }
+
+            if(number instanceof BigDecimal){
+                String value = number.toString();
+                double doubleValue = number.doubleValue();
+                if(value.equals(Double.toString(doubleValue))){
+                    writeByte(NUMBER_DOUBLE_TYPE);
+                    writeDouble(doubleValue);
+                }else {
+                    writeByte(NUMBER_BIG_DECIMAL_TYPE);
+                    writeUTF16String(value);
+                }
+                return;
+            }
+            writeByte(STRING_TYPE);
+            writeUTF16String(number.toString());
+
+        }
+
+        private final  void writeMap(Map map) {
+            if(WriteMapNullValue){
+                ensureCapacity(8);
+                writeByte(MAP_TYPE);
+                writeUInt(map.size());
+                Set<Map.Entry<Object,Object>>  entries = map.entrySet();
+                for(Map.Entry<Object,Object> entry : entries){
+                    writeMapKeyUTF16(entry.getKey().toString());
+                    writeObject(entry.getValue());
+                }
+            }else{
+                Set<Map.Entry<Object,Object>>  entries = map.entrySet();
+                int nullValueSize = 0;
+                for(Map.Entry<Object,Object> entry : entries){
+                    if(entry.getValue() == null){
+                        nullValueSize++;
+                    }
+                }
+
+                ensureCapacity(8);
+                writeByte(MAP_TYPE);
+                writeUInt(map.size()-nullValueSize);
+                for(Map.Entry<Object,Object> entry : entries){
+                    if(entry.getValue() == null){
+                        continue;
+                    }
+                    writeMapKeyUTF16(entry.getKey().toString());
+                    writeObject(entry.getValue());
+                }
+            }
+        }
+
+
+        private final void writeByte(byte type){
+            buffer[position] = type;
+            position++;
+        }
+
+        private final void writeAdapterObject(Object object){
+            if(specialClass.get(object.getClass().getName()) != null){
+                writeObject(JSON.toJSON(object));
+                return;
+            }
+            try{
+                writeMap(toMap(object));
+            }catch (Exception e){
+                specialClass.put(object.getClass().getName(), true);
+                writeObject(JSON.toJSON(object));
+            }
+        }
+
+        private  final Map  toMap(Object object){
+            Map map = new JSONObject();
+            try {
+                Class<?> targetClass = object.getClass();
+                String key = targetClass.getName();
+                List<Method> methods = getBeanMethod(key, targetClass);
+                for (Method method : methods) {
+                    String methodName = method.getName();
+                    if (methodName.startsWith(METHOD_PREFIX_GET)) {
+                        Object value = method.invoke(object);
+                        if(value != null){
+                            StringBuilder builder = new StringBuilder(method.getName().substring(3));
+                            builder.setCharAt(0, Character.toLowerCase(builder.charAt(0)));
+                            map.put(builder.toString(), (Object) value);
+                        }
+                    }else if(methodName.startsWith(METHOD_PREFIX_IS)){
+                        Object value = method.invoke(object);
+                        if(value != null){
+                            StringBuilder builder = new StringBuilder(method.getName().substring(2));
+                            builder.setCharAt(0, Character.toLowerCase(builder.charAt(0)));
+                            map.put(builder.toString(), value);
+                        }
+                    }
+                }
+                List<Field> fields = getBeanFields(key, targetClass);
+                for(Field field : fields){
+                    String fieldName = field.getName();
+                    if(map.containsKey(fieldName)){
+                        continue;
+                    }
+                    Object value  = field.get(object);
+                    if(value == null){
+                        continue;
+                    }
+                    map.put(fieldName, value);
+                }
+            }catch (Exception e){
+                if(e instanceof  RuntimeException){
+                    throw  (RuntimeException)e;
+                }else{
+                    throw  new RuntimeException(e);
+                }
+            }
+            return  map;
+        }
+
+        private  final void writeMapKeyUTF16(String value){
+            writeUTF16String(value);
+        }
+
+
+
+
+        /**
+         * writeString UTF-16
+         * */
+        private  final void writeUTF16String(CharSequence value){
+            int length = value.length();
+            ensureCapacity(length*2 + 8);
+            writeUInt(length*2);
+            if(IS_NATIVE_LITTLE_ENDIAN){
+                for(int i=0; i<length; i++){
+                    char ch = value.charAt(i);
+                    buffer[position] = (byte) (ch);
+                    buffer[position+1] = (byte) (ch >>> 8);
+                    position+=2;
+                }
+            }else{
+                for(int i=0; i<length; i++){
+                    char ch = value.charAt(i);
+                    buffer[position + 1] = (byte) (ch      );
+                    buffer[position] = (byte) (ch >>> 8);
+                    position+=2;
+                }
+            }
+        }
+
+
+        private final void writeDouble(double value){
+            writeLong(Double.doubleToLongBits(value));
+        }
+
+        private final void writeFloat(float value){
+            int val = Float.floatToIntBits(value);
+            buffer[position + 3] = (byte) (val       );
+            buffer[position + 2] = (byte) (val >>>  8);
+            buffer[position + 1] = (byte) (val >>> 16);
+            buffer[position ] = (byte) (val >>> 24);
+            position += 4;
+        }
+
+        private final void writeLong(long val){
+            buffer[position + 7] = (byte) (val       );
+            buffer[position + 6] = (byte) (val >>>  8);
+            buffer[position + 5] = (byte) (val >>> 16);
+            buffer[position + 4] = (byte) (val >>> 24);
+            buffer[position + 3] = (byte) (val >>> 32);
+            buffer[position + 2] = (byte) (val >>> 40);
+            buffer[position + 1] = (byte) (val >>> 48);
+            buffer[position    ] = (byte) (val >>> 56);
+            position += 8;
+        }
+
+        private final void writeVarInt(int value){
+            writeUInt((value << 1) ^ (value >> 31));
+        }
+
+        private final void  writeUInt(int value){
+            while ((value & 0xFFFFFF80) != 0) {
+                buffer[position] = (byte)((value & 0x7F) | 0x80);
+                position++;
+                value >>>= 7;
+            }
+            buffer[position] = (byte)(value & 0x7F);
+            position++;
+        }
+
+
+        private final void ensureCapacity(int minCapacity) {
+            minCapacity += position;
+            // overflow-conscious code
+            if (minCapacity - buffer.length > 0){
+                int oldCapacity = buffer.length;
+                int newCapacity = oldCapacity << 1;
+                if(newCapacity < 1024*16){
+                    newCapacity = 1024*16;
+                }
+                if (newCapacity - minCapacity < 0) {
+                    newCapacity = minCapacity;
+                }
+                buffer = Arrays.copyOf(buffer, newCapacity);
+            }
+        }
+    }
+
+
+    /**
+     * cache json property key, most of them all same
+     * */
+    private static final int GLOBAL_STRING_CACHE_SIZE = 2*1024;
+    private static final ThreadLocal<char[]> localCharsBufferCache = new ThreadLocal<>();
+    private static final String[] globalStringBytesCache = new String[GLOBAL_STRING_CACHE_SIZE];
+
+
+
+
+    /**
+     * lru cache, to map helper
+     * */
+    private static final String METHOD_PREFIX_GET = "get";
+    private static final String METHOD_PREFIX_IS = "is";
+    private static LruCache<String, List<Method>> methodsCache = new LruCache<>(128);
+    private static LruCache<String, List<Field>> fieldsCache = new LruCache<>(128);
+    private static LruCache<String, Boolean> specialClass = new LruCache<>(16);
+
+
+    private static final List<Method> getBeanMethod(String key, Class targetClass){
+        List<Method> methods = methodsCache.get(key);
+        if(methods == null){
+            methods = new ArrayList<>();
+            Method[]  allMethods = targetClass.getMethods();
+            for(Method method : allMethods){
+                if(method.getDeclaringClass() == Object.class){
+                    continue;
+                }
+                if( (method.getModifiers() & Modifier.STATIC) != 0){
+                    continue;
+                }
+                String methodName = method.getName();
+                if(methodName.startsWith(METHOD_PREFIX_GET)
+                        || methodName.startsWith(METHOD_PREFIX_IS)) {
+                    if(method.getAnnotation(JSONField.class) != null){
+                        throw new UnsupportedOperationException("getBeanMethod JSONField Annotation Not Handled, Use toJSON");
+                    }
+                    methods.add(method);
+                }
+            }
+            methodsCache.put(key, methods);
+        }
+        return methods;
+    }
+
+
+
+    private static  final List<Field> getBeanFields(String key, Class targetClass){
+        List<Field> fieldList = fieldsCache.get(key);
+        if(fieldList == null) {
+            Field[] fields = targetClass.getFields();
+            fieldList = new ArrayList<>(fields.length);
+            for(Field field : fields){
+                if((field.getModifiers() & Modifier.STATIC) != 0){
+                    continue;
+                }
+                if(field.getAnnotation(JSONField.class) != null){
+                    throw new UnsupportedOperationException("getBeanMethod JSONField Annotation Not Handled, Use toJSON");
+                }
+                fieldList.add(field);
+            }
+            fieldsCache.put(key, fieldList);
+        }
+        return  fieldList;
+    }
+
+}
diff --git a/android/sdk/src/main/java/org/apache/weex/wson/WsonUtils.java b/android/sdk/src/main/java/org/apache/weex/wson/WsonUtils.java
new file mode 100644
index 0000000..edd1a15
--- /dev/null
+++ b/android/sdk/src/main/java/org/apache/weex/wson/WsonUtils.java
@@ -0,0 +1,54 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+package org.apache.weex.wson;
+
+import org.apache.weex.utils.WXLogUtils;
+
+/**
+ * Created by furture on 2018/5/17.
+ */
+
+public class WsonUtils {
+    /**
+     * total entry, with wson support, always parse json
+     * */
+    public static final Object parseWson(byte[] data){
+        if(data == null){
+            return  null;
+        }
+        try{
+            return  Wson.parse(data);
+        }catch (Exception e){
+            WXLogUtils.e("weex wson parse error ", e);
+            return  null;
+        }
+    }
+
+    public static final byte[] toWson(Object data){
+        if(data == null){
+            return  null;
+        }
+        try{
+            return  Wson.toWson(data);
+        }catch (Exception e){
+            WXLogUtils.e("weex wson to wson error ", e);
+            return  null;
+        }
+    }
+}
diff --git a/android/sdk/src/test/java/com/taobao/weex/TestActivity.java b/android/sdk/src/test/java/com/taobao/weex/TestActivity.java
deleted file mode 100644
index 66b305e..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/TestActivity.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import android.app.Activity;
-/**
- * Created by sospartan on 7/27/16.
- */
-public   class TestActivity extends Activity {
-  public  void test(){
-    //
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/TestApplication.java b/android/sdk/src/test/java/com/taobao/weex/TestApplication.java
deleted file mode 100644
index 9ca09d9..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/TestApplication.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import android.app.Application;
-
-/**
- * Created by sospartan on 7/21/16.
- */
-public class TestApplication extends Application {
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/WXSDKEngineTest.java b/android/sdk/src/test/java/com/taobao/weex/WXSDKEngineTest.java
deleted file mode 100644
index 0864653..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/WXSDKEngineTest.java
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import com.taobao.weex.bridge.WXBridgeManagerTest;
-import com.taobao.weex.common.TestModule;
-import com.taobao.weex.common.TestModuleFactory;
-import com.taobao.weex.ui.component.TestComponent;
-import com.taobao.weex.ui.component.WXComponent;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 7/20/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(manifest = Config.NONE)
-@PrepareForTest({})
-public class WXSDKEngineTest {
-
-  @Before
-  public void setUp() throws Exception {
-
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    WXBridgeManagerTest.getLooper().idle();
-  }
-
-  @Test
-  public void testInit() throws Exception {
-    assertFalse(WXSDKEngine.isInitialized());
-    WXSDKEngine.initialize(RuntimeEnvironment.application,null);
-
-    new Thread(){
-      public void run(){
-        try {
-          Thread.sleep(60000);
-          assertTrue(WXSDKEngine.isInitialized());
-        } catch (InterruptedException e) { }
-      }
-    }.start();
-
-
-    //keep compatible
-    WXSDKEngine.init(RuntimeEnvironment.application);
-    WXSDKEngine.init(RuntimeEnvironment.application,null);
-    WXSDKEngine.init(RuntimeEnvironment.application,null,null);
-    WXSDKEngine.init(RuntimeEnvironment.application,null,null,null,null);
-  }
-
-  @Test
-  public void testRegisterComponent() throws Exception {
-    assertFalse(WXSDKEngine.registerComponent(null,(Class<? extends WXComponent>) null,true));
-    assertTrue(WXSDKEngine.registerComponent("test", TestComponent.class,true));
-    assertTrue(WXSDKEngine.registerComponent("test1",TestComponent.class));
-    assertTrue(WXSDKEngine.registerComponent(TestComponent.class,false,"testA","testB","testC"));
-    Map<String,Object> compInfo = new HashMap<>();
-    assertFalse(WXSDKEngine.registerComponent(compInfo,TestComponent.class));
-  }
-
-  @Test
-  public void testRegisterModule() throws Exception {
-    assertTrue(WXSDKEngine.registerModule("test", TestModule.class));
-    assertFalse(WXSDKEngine.registerModule(null,TestModule.class));
-    assertFalse(WXSDKEngine.registerModule("test",null));
-
-    assertFalse(WXSDKEngine.registerModuleWithFactory(null,new TestModuleFactory(TestModule.class),true));
-    assertTrue(WXSDKEngine.registerModuleWithFactory("test1",new TestModuleFactory(TestModule.class),true));
-  }
-
-
-  @Test
-  public void testRegisterDomObject() throws Exception {
-    assertFalse(WXSDKEngine.registerDomObject("test",null));
-    assertFalse(WXSDKEngine.registerDomObject("", TestDomObject.class));
-    assertTrue(WXSDKEngine.registerDomObject("test",TestDomObject.class));
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/WXSDKInstanceTest.java b/android/sdk/src/test/java/com/taobao/weex/WXSDKInstanceTest.java
deleted file mode 100644
index 6be97ae..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/WXSDKInstanceTest.java
+++ /dev/null
@@ -1,198 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import static org.junit.Assert.assertEquals;
-import static org.powermock.api.mockito.PowerMockito.mock;
-import static org.powermock.api.mockito.PowerMockito.mockStatic;
-import static org.powermock.api.mockito.PowerMockito.when;
-
-import android.view.View;
-import android.widget.FrameLayout;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.bridge.WXBridgeManagerTest;
-import com.taobao.weex.common.WXPerformance;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.dom.WXDomManagerTest;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXComponentFactory;
-import com.taobao.weex.ui.component.WXDivTest;
-import com.taobao.weex.ui.component.WXVContainer;
-import com.taobao.weex.utils.WXFileUtils;
-import com.taobao.weex.utils.WXSoInstallMgrSdk;
-import java.util.HashMap;
-import java.util.Map;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.Robolectric;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-import org.robolectric.shadows.ShadowLooper;
-
-
-/**
- * Created by sospartan on 7/27/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19,manifest = Config.NONE)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-@PrepareForTest({WXFileUtils.class,WXSoInstallMgrSdk.class})
-public class WXSDKInstanceTest {
-  @Rule
-  public PowerMockRule rule = new PowerMockRule();
-
-  public static WXSDKInstance createInstance(){
-    WXSDKInstance instance =  new WXSDKInstance(Robolectric.setupActivity(TestActivity.class),"1");
-    final FrameLayout container = new FrameLayout(instance.getContext());
-    instance.registerRenderListener(new IWXRenderListener() {
-      @Override
-      public void onViewCreated(WXSDKInstance instance, View view) {
-        container.addView(view);
-      }
-
-      @Override
-      public void onRenderSuccess(WXSDKInstance instance, int width, int height) {
-
-      }
-
-      @Override
-      public void onRefreshSuccess(WXSDKInstance instance, int width, int height) {
-
-      }
-
-      @Override
-      public void onException(WXSDKInstance instance, String errCode, String msg) {
-
-      }
-    });
-    instance.mContext = Robolectric.setupActivity(TestActivity.class);
-
-    return instance;
-  }
-
-  public static void setupRoot(WXSDKInstance instance){
-
-    WXDomObject domObject = new WXDomObject();
-    WXVContainer comp = (WXVContainer) WXComponentFactory.newInstance(instance, domObject, null);
-
-    WXComponent root = WXDivTest.create(comp);
-    comp.addChild(root);
-    comp.createView();
-
-    instance.onCreateFinish();
-    ShadowLooper.idleMainLooper();
-  }
-
-  WXSDKInstance mInstance;
-
-  @Before
-  public void setup() throws Exception {
-    mockStatic(WXSoInstallMgrSdk.class);
-    when(WXSoInstallMgrSdk.initSo("weexv8", 1, null)).thenReturn(true);
-    WXSDKEngine.initialize(RuntimeEnvironment.application,new InitConfig.Builder().build());
-    mInstance = createInstance();
-    WXBridgeManagerTest.getLooper().idle();
-
-    mockStatic(WXFileUtils.class);
-    when(WXFileUtils.loadAsset(null,null)).thenReturn("{}");
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    WXBridgeManagerTest.getLooper().idle();
-    WXDomManagerTest.getLooper().idle();
-    mInstance.destroy();
-  }
-
-
-  @Test
-  public void testRender() throws Exception {
-    assertEquals(WXFileUtils.loadAsset(null,null),"{}");
-
-    mInstance.render("{}",null,null,null);
-
-  }
-
-  @Test
-  public void testSetSize() throws Exception {
-    setupRoot(mInstance);
-    mInstance.setSize(10,10);
-  }
-
-  @Test
-  public void testRenderEvent() throws Exception {
-    mInstance.onRenderError("test","test");
-    mInstance.onRenderSuccess(10,10);
-  }
-
-  @Test
-  public void testRenderByUrl() throws Exception {
-    mInstance.renderByUrl(WXPerformance.DEFAULT,"file:///test",null,null,100,100, WXRenderStrategy.APPEND_ASYNC);
-    mInstance.renderByUrl(WXPerformance.DEFAULT,"http://taobao.com",null,null,100,100, WXRenderStrategy.APPEND_ASYNC);
-  }
-
-  @Test
-  public void testGlobalEvent() throws Exception {
-    mInstance.addEventListener(null,null);
-    mInstance.addEventListener(null,"");
-    mInstance.addEventListener("",null);
-
-    mInstance.addEventListener("test","123");
-    mInstance.fireGlobalEventCallback("test",null);
-    mInstance.removeEventListener("test");
-    mInstance.removeEventListener("test","123");
-  }
-
-  @Test
-  public void testFireEvent() throws Exception {
-    mInstance.fireEvent("1","test");
-    Map<String,Object> params = new HashMap<>();
-    params.put("arg1",null);
-    params.put("arg2",123);
-    mInstance.fireEvent("1","test",params);
-
-    Map<String,Object> domChange = new HashMap<>();
-    domChange.put("attr1","123");
-    mInstance.fireEvent("1","test",params,domChange);
-  }
-
-
-  @Test
-  public void testOnActivityLifecycle() throws Exception {
-    mInstance.registerActivityStateListener(mock(IWXActivityStateListener.class));
-    mInstance.onActivityCreate();
-    mInstance.onActivityStart();
-    mInstance.onActivityResume();
-    mInstance.onActivityPause();
-    mInstance.onActivityStop();
-  }
-
-  @Test
-  public void testOnJSException() throws Exception {
-    mInstance.onJSException(null,null,null);
-    mInstance.onJSException("100","test","some error");
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/WXSDKManagerTest.java b/android/sdk/src/test/java/com/taobao/weex/WXSDKManagerTest.java
deleted file mode 100644
index ae6442d..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/WXSDKManagerTest.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex;
-
-import com.taobao.weex.ui.WXRenderManager;
-import org.junit.After;
-import org.junit.Before;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 8/30/16.
- */
-public class WXSDKManagerTest {
-
-  public static void setRenderManager(WXRenderManager rm){
-    WXSDKManager.initInstance(rm);
-  }
-
-  public static void setInstance(WXSDKManager m){
-    WXSDKManager.setInstance(m);
-  }
-
-  @Before
-  public void setUp() throws Exception {
-
-  }
-
-  @After
-  public void tearDown() throws Exception {
-
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/adapter/DefaultUriAdapterTest.java b/android/sdk/src/test/java/com/taobao/weex/adapter/DefaultUriAdapterTest.java
deleted file mode 100644
index 3c4d84b..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/adapter/DefaultUriAdapterTest.java
+++ /dev/null
@@ -1,116 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.adapter;
-
-import android.net.Uri;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.WXSDKManagerTest;
-import com.taobao.weex.common.WXRenderStrategy;
-import com.taobao.weex.common.WXRequest;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.mockito.internal.util.MockUtil;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.assertEquals;
-
-
-/**
- * Created by sospartan on 21/11/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({"org.mockito.*", "org.robolectric.*", "android.*"})
-public class DefaultUriAdapterTest {
-  URIAdapter adapter;
-  WXSDKInstance instance;
-
-  @Before
-  public void setup() {
-    WXEnvironment.sApplication = RuntimeEnvironment.application;
-    WXSDKManager wxsdkManager = WXSDKManager.getInstance();
-    if (!new MockUtil().isSpy(wxsdkManager)) {
-      WXSDKManager spy = Mockito.spy(wxsdkManager);
-      WXSDKManagerTest.setInstance(spy);
-      Mockito.when(spy.getIWXHttpAdapter()).thenReturn(new IWXHttpAdapter() {
-        @Override
-        public void sendRequest(WXRequest request, OnHttpListener listener) {
-          //do nothing.
-        }
-      });
-    }
-
-    adapter = new DefaultUriAdapter();
-    instance = WXSDKInstanceTest.createInstance();
-  }
-
-  @Test
-  public void testRewrite() throws Exception {
-
-    final String host = "http://127.0.0.1";
-    final String base = host + "/test/123/";
-    final String bundleWithSlash = base + "?arg=value";
-    final String bundle = base + "bundle.js?arg=value";
-
-
-    instance.renderByUrl("", bundle, null, null, 0, 0, WXRenderStrategy.APPEND_ONCE);
-    testRelative(host, base, bundle);
-    instance.renderByUrl("", bundleWithSlash, null, null, 0, 0, WXRenderStrategy.APPEND_ONCE);
-    testRelative(host, base, bundleWithSlash);
-  }
-
-  private void testRelative(String host, String baseWithSlash, String bundleUrl) {
-    Uri uri = adapter.rewrite(instance, URIAdapter.IMAGE, Uri.parse("./456"));
-    assertEquals(Uri.parse(baseWithSlash + "./456"), uri);
-
-    uri = adapter.rewrite(instance, URIAdapter.IMAGE, Uri.parse("../456"));
-    assertEquals(Uri.parse(baseWithSlash + "../456"), uri);
-
-
-    uri = adapter.rewrite(instance, URIAdapter.IMAGE, Uri.parse("./456?k=v"));
-    assertEquals(Uri.parse(baseWithSlash + "./456?k=v"), uri);
-
-    uri = adapter.rewrite(instance, URIAdapter.IMAGE, Uri.parse("./456?k=v&k2=v2"));
-    assertEquals(Uri.parse(baseWithSlash + "./456?k=v&k2=v2"), uri);
-
-    uri = adapter.rewrite(instance, URIAdapter.IMAGE, Uri.parse("./456?k=v#flagment"));
-    assertEquals(Uri.parse(baseWithSlash + "./456?k=v#flagment"), uri);
-
-    uri = adapter.rewrite(instance, URIAdapter.IMAGE, Uri.parse("//test.com/test/test2"));
-    assertEquals(Uri.parse("http://test.com/test/test2"), uri);
-
-    uri = adapter.rewrite(instance, URIAdapter.IMAGE, Uri.parse("/test2"));
-    assertEquals(Uri.parse(host + "/test2"), uri);
-
-    uri = adapter.rewrite(instance, URIAdapter.IMAGE, Uri.parse(""));
-    assertEquals(Uri.parse(bundleUrl), uri);
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/appfram/clipboard/WXClipboardModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/appfram/clipboard/WXClipboardModuleTest.java
deleted file mode 100644
index 4f2de36..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/appfram/clipboard/WXClipboardModuleTest.java
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.clipboard;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.bridge.JSCallback;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 27/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXClipboardModuleTest {
-
-  WXClipboardModule module;
-
-  @Before
-  public void setUp() throws Exception {
-    module = new WXClipboardModule();
-    module.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-  }
-
-  @After
-  public void tearDown() throws Exception {
-
-  }
-
-  @Test
-  public void testSetString() throws Exception {
-    module.setString("test");
-  }
-
-  @Test
-  public void testGetString() throws Exception {
-
-    JSCallback mock = Mockito.mock(JSCallback.class);
-    module.getString(mock);
-    Mockito.verify(mock,Mockito.times(1)).invoke(Mockito.anyObject());
-
-    testSetString();
-
-    mock = Mockito.mock(JSCallback.class);
-    module.getString(mock);
-    Mockito.verify(mock,Mockito.times(1)).invoke(Mockito.anyObject());
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/appfram/navigator/WXNavigatorModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/appfram/navigator/WXNavigatorModuleTest.java
deleted file mode 100644
index 9084adc..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/appfram/navigator/WXNavigatorModuleTest.java
+++ /dev/null
@@ -1,174 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.navigator;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.WXBridgeManager;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-import static org.junit.Assert.*;
-import static org.mockito.Mockito.when;
-import static org.powermock.api.mockito.PowerMockito.*;
-import static org.mockito.Mockito.*;
-
-/**
- * Created by sospartan on 7/28/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*","org.json.*" })
-@PrepareForTest(WXSDKEngine.class)
-public class WXNavigatorModuleTest {
-
-  WXNavigatorModule module;
-  JSCallback callback;
-
-  @Rule
-  public PowerMockRule rule = new PowerMockRule();
-
-  @Before
-  public void setUp() throws Exception {
-    mockStatic(WXSDKEngine.class);
-    callback = Mockito.mock(JSCallback.class);
-
-
-    module = new WXNavigatorModule();
-    module.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-  }
-
-  private void mockSetter(){
-    when(WXSDKEngine.getActivityNavBarSetter()).thenReturn(new IActivityNavBarSetter() {
-      @Override
-      public boolean push(String param) {
-        return true;
-      }
-
-      @Override
-      public boolean pop(String param) {
-        return true;
-      }
-
-      @Override
-      public boolean setNavBarRightItem(String param) {
-        return true;
-      }
-
-      @Override
-      public boolean clearNavBarRightItem(String param) {
-        return true;
-      }
-
-      @Override
-      public boolean setNavBarLeftItem(String param) {
-        return true;
-      }
-
-      @Override
-      public boolean clearNavBarLeftItem(String param) {
-        return true;
-      }
-
-      @Override
-      public boolean setNavBarMoreItem(String param) {
-        return true;
-      }
-
-      @Override
-      public boolean clearNavBarMoreItem(String param) {
-        return true;
-      }
-
-      @Override
-      public boolean setNavBarTitle(String param) {
-        return true;
-      }
-    });
-  }
-
-  @Test
-  public void testPush() throws Exception {
-    module.push("{}",callback);
-    module.push("{'url':'kdkdkdkdkd'}",callback);
-    mockSetter();
-    module.push("{}",callback);
-  }
-
-
-  @Test
-  public void testPop() throws Exception {
-    mockSetter();
-    module.pop("{}",callback);
-  }
-
-  @Test
-  public void testSetNavBarRightItem() throws Exception {
-    mockSetter();
-    module.setNavBarRightItem("{}",callback);
-  }
-
-  @Test
-  public void testClearNavBarRightItem() throws Exception {
-    mockSetter();
-    module.clearNavBarRightItem("{}",callback);
-  }
-
-  @Test
-  public void testSetNavBarLeftItem() throws Exception {
-    mockSetter();
-    module.setNavBarLeftItem("{}",callback);
-  }
-
-  @Test
-  public void testClearNavBarLeftItem() throws Exception {
-    mockSetter();
-    module.clearNavBarLeftItem("{}",callback);
-  }
-
-  @Test
-  public void testSetNavBarMoreItem() throws Exception {
-    mockSetter();
-    module.setNavBarMoreItem("{}",callback);
-  }
-
-  @Test
-  public void testClearNavBarMoreItem() throws Exception {
-    mockSetter();
-    module.clearNavBarMoreItem("{}",callback);
-  }
-
-  @Test
-  public void testSetNavBarTitle() throws Exception {
-    mockSetter();
-    module.setNavBarTitle("{}",callback);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/appfram/storage/DefaultWXStorageTest.java b/android/sdk/src/test/java/com/taobao/weex/appfram/storage/DefaultWXStorageTest.java
deleted file mode 100644
index fae69b8..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/appfram/storage/DefaultWXStorageTest.java
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.storage;
-
-import static org.mockito.Mockito.anyMapOf;
-import static org.mockito.Mockito.timeout;
-import static org.mockito.Mockito.verify;
-import static org.powermock.api.mockito.PowerMockito.mockStatic;
-import static org.powermock.api.mockito.PowerMockito.whenNew;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mock;
-import org.mockito.MockitoAnnotations;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 7/28/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-public class DefaultWXStorageTest {
-
-  @Mock
-  WXSQLiteOpenHelper supplier;
-  @Mock
-  IWXStorageAdapter.OnResultReceivedListener listener;
-  DefaultWXStorage storage;
-
-  @Rule
-  public PowerMockRule rule = new PowerMockRule();
-
-  @Before
-  public void setup() throws Exception{
-    MockitoAnnotations.initMocks(this);
-    storage = new DefaultWXStorage(RuntimeEnvironment.application);
-    mockStatic(WXSQLiteOpenHelper.class);
-    whenNew(WXSQLiteOpenHelper.class)
-            .withArguments(RuntimeEnvironment.application)
-            .thenReturn(supplier);
-  }
-
-
-  @Test
-  public void testSetItem() throws Exception {
-    storage.setItem("","",listener);
-
-    verify(listener,timeout(3000).times(1)).onReceived(anyMapOf(String.class,Object.class));
-    storage.close();
-  }
-
-  @Test
-  public void testGetItem() throws Exception {
-    storage.getItem("",listener);
-
-    verify(listener,timeout(3000).times(1)).onReceived(anyMapOf(String.class,Object.class));
-    storage.close();
-  }
-
-  @Test
-  public void testRemoveItem() throws Exception {
-    storage.removeItem("",listener);
-
-    verify(listener,timeout(3000).times(1)).onReceived(anyMapOf(String.class,Object.class));
-    storage.close();
-  }
-
-  @Test
-  public void testLength() throws Exception {
-    storage.length(listener);
-
-    verify(listener,timeout(3000).times(1)).onReceived(anyMapOf(String.class,Object.class));
-    storage.close();
-  }
-
-  @Test
-  public void testGetAllKeys() throws Exception {
-    storage.getAllKeys(listener);
-
-    verify(listener,timeout(3000).times(1)).onReceived(anyMapOf(String.class,Object.class));
-    storage.close();
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/appfram/storage/WXStorageModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/appfram/storage/WXStorageModuleTest.java
deleted file mode 100644
index 1ff7c89..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/appfram/storage/WXStorageModuleTest.java
+++ /dev/null
@@ -1,130 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.appfram.storage;
-
-import static org.mockito.Mockito.any;
-import static org.mockito.Mockito.times;
-import static org.mockito.Mockito.verify;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.WXBridgeManager;
-import java.util.Map;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 7/28/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-@PrepareForTest(WXBridgeManager.class)
-public class WXStorageModuleTest {
-
-
-  WXStorageModule module;
-  JSCallback callback;
-
-  @Before
-  public void setUp() throws Exception {
-    module = new WXStorageModule();
-    module.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-    module.mStorageAdapter = new IWXStorageAdapter() {
-      @Override
-      public void setItem(String key, String value, OnResultReceivedListener listener) {
-        Map<String, Object> data = StorageResultHandler.setItemResult(true);
-        listener.onReceived(data);
-      }
-
-      @Override
-      public void getItem(String key, OnResultReceivedListener listener) {
-        Map<String, Object> data = StorageResultHandler.setItemResult(true);
-        listener.onReceived(data);
-      }
-
-      @Override
-      public void removeItem(String key, OnResultReceivedListener listener) {
-        Map<String, Object> data = StorageResultHandler.setItemResult(true);
-        listener.onReceived(data);
-      }
-
-      @Override
-      public void length(OnResultReceivedListener listener) {
-        Map<String, Object> data = StorageResultHandler.setItemResult(true);
-        listener.onReceived(data);
-      }
-
-      @Override
-      public void getAllKeys(OnResultReceivedListener listener) {
-        Map<String, Object> data = StorageResultHandler.setItemResult(true);
-        listener.onReceived(data);
-      }
-
-      @Override
-      public void setItemPersistent(String key, String value, OnResultReceivedListener listener) {
-
-      }
-
-      @Override
-      public void close() {
-
-      }
-    };
-    callback = Mockito.mock(JSCallback.class);
-  }
-
-  @Test
-  public void testSetItem() throws Exception {
-    module.setItem("","",callback);
-    verify(callback,times(1)).invoke(any());
-
-  }
-
-  @Test
-  public void testGetItem() throws Exception {
-    module.getItem("",callback);
-    verify(callback,times(1)).invoke(any());
-  }
-
-  @Test
-  public void testRemoveItem() throws Exception {
-    module.removeItem("",callback);
-    verify(callback,times(1)).invoke(any());
-  }
-
-  @Test
-  public void testLength() throws Exception {
-    module.length(callback);
-    verify(callback,times(1)).invoke(any());
-  }
-
-  @Test
-  public void testGetAllKeys() throws Exception {
-    module.getAllKeys(callback);
-    verify(callback,times(1)).invoke(any());
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/bridge/WXBridgeManagerTest.java b/android/sdk/src/test/java/com/taobao/weex/bridge/WXBridgeManagerTest.java
deleted file mode 100644
index 61a3f14..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/bridge/WXBridgeManagerTest.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import static junit.framework.Assert.assertNotNull;
-
-import android.os.Handler;
-import android.os.Message;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.InitConfig;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.WXSDKManagerTest;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXJSBridgeMsgType;
-import com.taobao.weex.ui.WXRenderManager;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.Shadows;
-import org.robolectric.annotation.Config;
-import org.robolectric.shadows.ShadowLooper;
-
-
-/**
- * Created by lixinke on 16/2/24.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-@PrepareForTest(WXModuleManager.class)
-public class WXBridgeManagerTest {
-
-  WXSDKInstance instance;
-
-  public static ShadowLooper getLooper() {
-    WXBridgeManager bridgeManager = WXBridgeManager.getInstance();
-    Handler handler = bridgeManager.mJSHandler;
-    return Shadows.shadowOf(handler.getLooper());
-  }
-
-  public static void setBridgeManager(WXBridgeManager bridge) {
-    WXBridgeManager.mBridgeManager = bridge;
-  }
-
-  private WXBridgeManager getInstance() {
-    return WXBridgeManager.getInstance();
-  }
-
-  @Before
-  public void setUp() throws Exception {
-    WXSDKEngine.initialize(RuntimeEnvironment.application,new InitConfig.Builder().build());
-    instance = WXSDKInstanceTest.createInstance();
-    WXRenderManager rednerManager = new WXRenderManager();
-    rednerManager.registerInstance(instance);//
-    WXSDKManagerTest.setRenderManager(rednerManager);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    getLooper().idle();
-    getInstance().destroy();
-  }
-
-  @Test
-  public void testGetInstance() throws Exception {
-    WXBridgeManager instance = WXBridgeManager.getInstance();
-    assertNotNull(instance);
-  }
-
-  @Test
-  public void testRestart() throws Exception {
-    getInstance().restart();
-  }
-
-  @Test
-  public void testSetStackTopInstance() throws Exception {
-    getInstance().setStackTopInstance("");
-  }
-
-  @Test
-  public void testCallNative() throws Exception {
-    getInstance()
-        .callNative(instance.getInstanceId(),
-            "[{\"module\":\"testModule\",\"method\":\"test\"}]",
-            null);
-
-    getInstance()
-        .callNative(instance.getInstanceId(),
-            "[{\"module\":\""+WXDomModule.WXDOM+"\",\"method\":\"test\"}]",
-            null);
-
-  }
-
-  @Test
-  public void testInitScriptsFramework() throws Exception {
-    getInstance().initScriptsFramework("");
-  }
-
-  @Test
-  public void testFireEvent() throws Exception {
-    getInstance().fireEvent(instance.getInstanceId(),"100", Constants.Event.CLICK,null,null);
-  }
-
-  @Test
-  public void testCallback() throws Exception {
-    getInstance().callbackJavascript(instance.getInstanceId(),"test",null,false);
-  }
-
-  @Test
-  public void testRefreshInstance() throws Exception {
-    getInstance().refreshInstance(instance.getInstanceId(),null);
-  }
-
-  @Test
-  public void testCreateInstance() throws Exception {
-    getInstance().createInstance(instance.getInstanceId(),"",null,null);
-  }
-
-  @Test
-  public void testDestroyInstance() throws Exception {
-    getInstance().destroyInstance(instance.getInstanceId());
-  }
-
-  @Test
-  public void testHandleMessage() throws Exception {
-    int[] msgs = {
-        WXJSBridgeMsgType.INIT_FRAMEWORK,
-        WXJSBridgeMsgType.CALL_JS_BATCH,
-        WXJSBridgeMsgType.SET_TIMEOUT,
-        WXJSBridgeMsgType.MODULE_INTERVAL,
-        WXJSBridgeMsgType.MODULE_TIMEOUT
-    };
-    Message msg = new Message();
-    for(int w:msgs) {
-      msg.what = w;
-      getInstance().handleMessage(msg);
-    }
-  }
-
-  @Test
-  public void testReportJSException() throws Exception {
-    getInstance().reportJSException(instance.getInstanceId(),"test","test exception");
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/bridge/WXBridgeTest.java b/android/sdk/src/test/java/com/taobao/weex/bridge/WXBridgeTest.java
deleted file mode 100644
index 13feaf6..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/bridge/WXBridgeTest.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 27/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXBridgeTest {
-
-  WXBridge bridge;
-
-  @Before
-  public void setUp() throws Exception {
-    bridge = new WXBridge();
-  }
-
-  @Test
-  public void testCallNative() throws Exception {
-    bridge.callNative("1","{}","100");
-  }
-
-  @Test
-  public void testCallAddElement() throws Exception {
-    bridge.callAddElement("1","1","{}","0","100");
-  }
-
-
-  @After
-  public void tearDown() throws Exception {
-
-  }
-
-  @Test
-  public void testReportJSException() throws Exception {
-    bridge.reportJSException("1","test","some exception");
-  }
-
-  @Test
-  public void testSetTimeoutNative() throws Exception {
-    bridge.setTimeoutNative("100","1024");
-  }
-
-  @Test
-  public void testSetJSFrmVersion() throws Exception {
-    bridge.setJSFrmVersion("v0.1");
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/bridge/WXHashMapTest.java b/android/sdk/src/test/java/com/taobao/weex/bridge/WXHashMapTest.java
deleted file mode 100644
index 71638ae..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/bridge/WXHashMapTest.java
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.Stack;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class,manifest = Config.NONE)
-public class WXHashMapTest {
-	private WXHashMap<String, String> mWXHashMap = new WXHashMap<>();
-
-	@Before
-	public void setUp() throws Exception {
-		mWXHashMap.clear();
-	}
-
-	@Test
-	public void testPutKV() {
-		mWXHashMap.put("one", "1");
-		assertEquals("1", mWXHashMap.get("one"));
-	}
-
-	@Test
-	public void testRemoveObject() {
-		mWXHashMap.put("one", "1");
-		mWXHashMap.remove("one");
-		assertEquals(0, mWXHashMap.size());
-	}
-
-	@Test
-	public void testRemoveFromMapAndStack() {
-		mWXHashMap.put("one","1");
-		mWXHashMap.removeFromMapAndStack("one");
-		assertEquals(true,mWXHashMap.getInstanceStack().empty());
-	}
-
-	@Test
-	public void testGetStackTopInstanceId() {
-		mWXHashMap.setStackTopInstance("123456");
-		mWXHashMap.setStackTopInstance("654321");
-		String id=mWXHashMap.getStackTopInstanceId();
-		assertEquals("654321",id);
-	}
-
-	@Test
-	public void testSetStackTopInstance() {
-		mWXHashMap.setStackTopInstance("123456");
-		int size=mWXHashMap.getInstanceStack().size();
-		assertEquals(1,size);
-	}
-
-	@Test
-	public void testGetInstanceStack() {
-		Stack<String> instance= mWXHashMap.getInstanceStack();
-		assertNotNull(instance);
-	}
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/bridge/WXModuleManagerTest.java b/android/sdk/src/test/java/com/taobao/weex/bridge/WXModuleManagerTest.java
deleted file mode 100644
index c4c92d8..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/bridge/WXModuleManagerTest.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.bridge;
-
-import com.alibaba.fastjson.JSONArray;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.InitConfig;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.common.TestModule;
-import com.taobao.weex.common.TypeModuleFactory;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.modules.junit4.PowerMockRunner;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 8/31/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class)
-public class WXModuleManagerTest {
-
-  WXSDKInstance instance;
-
-  @Before
-  public void setUp() throws Exception {
-    WXSDKEngine.initialize(RuntimeEnvironment.application,new InitConfig.Builder().build());
-    instance = WXSDKInstanceTest.createInstance();
-    WXModuleManager.registerModule("test",null,false);
-    WXModuleManager.registerModule("test1",new TypeModuleFactory<>(TestModule.class),true);
-    WXModuleManager.registerModule("test2",new TypeModuleFactory<>(TestModule.class),false);
-    WXBridgeManagerTest.getLooper().idle();
-  }
-
-  @After
-  public void tearDown() throws Exception {
-
-  }
-
-  @Test
-  public void testCallModuleMethod() throws Exception {
-    WXModuleManager.callModuleMethod(instance.getInstanceId(),"test1","testMethod",null);
-    WXModuleManager.callModuleMethod(instance.getInstanceId(),"test2","testMethod",null);
-  }
-
-  @Test
-  public void testCallModuleMethod2() throws Exception {
-    JSONArray args = new JSONArray();
-    args.add("testarg");
-    WXModuleManager.callModuleMethod(instance.getInstanceId(),"test1","testMethod",args);
-  }
-
-  @Test
-  public void testCallModuleMethod3() throws Exception {
-    JSONArray args = new JSONArray();
-    args.add("testarg");
-    args.add(null);
-    WXModuleManager.callModuleMethod(instance.getInstanceId(),"test1","testCallbackMethod",args);
-  }
-
-  @Test
-  public void testCallModuleMethod4() throws Exception {
-    JSONArray args = new JSONArray();
-    args.add("testarg");
-    args.add("testcallbackId");
-    WXModuleManager.callModuleMethod(instance.getInstanceId(),"test1","testCallbackMethod",args);
-  }
-
-  @Test
-  public void testDestroyInstanceModules() throws Exception {
-    testCallModuleMethod();//module instance is lazy create.
-    WXModuleManager.destroyInstanceModules(instance.getInstanceId());
-  }
-
-  @Test
-  public void testReload() throws Exception {
-    WXModuleManager.reload();
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/common/TestModule.java b/android/sdk/src/test/java/com/taobao/weex/common/TestModule.java
deleted file mode 100644
index b1158d4..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/common/TestModule.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.annotation.JSMethod;
-import com.taobao.weex.bridge.JSCallback;
-
-/**
- * Created by sospartan on 7/27/16.
- */
-public class TestModule extends WXSDKEngine.DestroyableModule {
-
-  @JSMethod
-  public void testMethod(String arg){
-
-  }
-
-  @JSMethod(uiThread=true)
-  public void testCallbackMethod(String arg, JSCallback callback){
-
-  }
-
-  @Override
-  public void destroy() {
-
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/common/TestModuleFactory.java b/android/sdk/src/test/java/com/taobao/weex/common/TestModuleFactory.java
deleted file mode 100644
index ae9fc65..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/common/TestModuleFactory.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.bridge.ModuleFactory;
-
-import java.util.ArrayList;
-import java.util.Map;
-
-/**
- * Created by sospartan on 7/27/16.
- */
-public class TestModuleFactory extends WXSDKEngine.DestroyableModuleFactory<TestModule> {
-
-
-  public TestModuleFactory(Class<TestModule> clz) {
-    super(clz);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/common/WXModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/common/WXModuleTest.java
deleted file mode 100644
index 5860720..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/common/WXModuleTest.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.common;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 7/27/16.
- */
-public class WXModuleTest {
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/dom/WXAttrTest.java b/android/sdk/src/test/java/com/taobao/weex/dom/WXAttrTest.java
deleted file mode 100644
index c122418..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/dom/WXAttrTest.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import static com.taobao.weex.common.Constants.Name.IMAGE_QUALITY;
-import static com.taobao.weex.common.Constants.Name.SRC;
-import static com.taobao.weex.common.Constants.Name.VALUE;
-import static com.taobao.weex.common.Constants.Value.HIGH;
-import static org.hamcrest.CoreMatchers.is;
-import static org.hamcrest.MatcherAssert.assertThat;
-import static org.junit.Assert.assertEquals;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXImageSharpen;
-import com.taobao.weex.utils.WXViewUtils;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class)
-public class WXAttrTest {
-
-  WXAttr attr;
-
-  @Before
-  public void setUp() throws Exception {
-    attr = new WXAttr();
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    attr.clear();
-  }
-
-  @Test
-  public void testGetValue() throws Exception {
-    assertEquals(null,WXAttr.getValue(attr));
-
-    attr.put(VALUE,"test");
-
-    assertEquals("test",WXAttr.getValue(attr));
-  }
-
-  @Test
-  public void testGetImageQuality() throws Exception {
-    assertEquals(WXImageQuality.AUTO,attr.getImageQuality());
-
-    attr.put(IMAGE_QUALITY,HIGH);
-    assertEquals(WXImageQuality.HIGH,attr.getImageQuality());
-  }
-
-  @Test
-  public void testGetImageSharpen() throws Exception {
-    assertEquals(WXImageSharpen.UNSHARPEN,attr.getImageSharpen());
-
-  }
-
-  @Test
-  public void testGetImageSrc() throws Exception {
-    assertEquals(null,attr.getImageSrc());
-
-    attr.put(SRC,"test");
-    assertEquals("test",attr.getImageSrc());
-  }
-
-  @Test
-  public void testShowIndicators() throws Exception {
-    assertEquals(true,attr.showIndicators());
-  }
-
-  @Test
-  public void testAutoPlay() throws Exception {
-    assertEquals(false,attr.autoPlay());
-  }
-
-  @Test
-  public void testGetScope() throws Exception {
-    assertEquals(null,attr.getScope());
-  }
-
-  @Test
-  public void testGetLoadMoreRetry() throws Exception {
-    assertEquals(null,attr.getLoadMoreRetry());
-  }
-
-  @Test
-  public void testGetLoadMoreOffset() throws Exception {
-    assertEquals(null,attr.getLoadMoreOffset());
-  }
-
-  @Test
-  public void testGetIsRecycleImage() throws Exception {
-    assertEquals(true,attr.getIsRecycleImage());
-  }
-
-  @Test
-  public void testGetScrollDirection() throws Exception {
-    assertEquals("vertical",attr.getScrollDirection());
-  }
-
-  @Test
-  public void testGetElevation() {
-    int elevation = 100, viewPortW = 750;
-
-    attr.put(Constants.Name.ELEVATION, elevation);
-    assertThat(attr.getElevation(viewPortW),
-               is(WXViewUtils.getRealSubPxByWidth(elevation, viewPortW)));
-
-    attr.put(Constants.Name.ELEVATION, "");
-    assertThat(attr.getElevation(viewPortW), is(0f));
-
-    attr.put(Constants.Name.ELEVATION, "give me a NAN");
-    assertThat(attr.getElevation(viewPortW), is(Float.NaN));
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/dom/WXDomManagerTest.java b/android/sdk/src/test/java/com/taobao/weex/dom/WXDomManagerTest.java
deleted file mode 100644
index 261b5b7..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/dom/WXDomManagerTest.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.ui.WXRenderManager;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.Shadows;
-import org.robolectric.shadows.ShadowLooper;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 8/31/16.
- */
-@RunWith(RobolectricTestRunner.class)
-public class WXDomManagerTest {
-
-  public static ShadowLooper getLooper() {
-    return Shadows.shadowOf(WXSDKManager.getInstance().getWXDomManager().mDomHandler.getLooper());
-  }
-
-  WXDomManager dm;
-  WXSDKInstance instance;
-
-  @Before
-  public void setUp() throws Exception {
-    WXRenderManager rm = new WXRenderManager();
-    instance =   WXSDKInstanceTest.createInstance();
-    rm.registerInstance(instance);
-    dm = new WXDomManager(rm);
-  }
-
-  @Test
-  public void testRemoveDomStatement() throws Exception {
-      dm.removeDomStatement(instance.getInstanceId());
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    getLooper().idle();
-    dm.destroy();
-  }
-
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/dom/WXDomStatementTest.java b/android/sdk/src/test/java/com/taobao/weex/dom/WXDomStatementTest.java
deleted file mode 100644
index 4bdd77a..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/dom/WXDomStatementTest.java
+++ /dev/null
@@ -1,292 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.InitConfig;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.WXSDKManager;
-import com.taobao.weex.WXSDKManagerTest;
-import com.taobao.weex.bridge.WXBridgeManagerTest;
-import com.taobao.weex.ui.WXRenderManager;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-import org.robolectric.shadows.ShadowLooper;
-
-/**
- * Created by sospartan on 8/29/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXDomStatementTest {
-
-  DOMActionContextImpl stmt;
-  WXRenderManager rednerManager;
-  WXSDKInstance instance;
-
-  @Before
-  public void setUp() throws Exception {
-    WXSDKEngine.initialize(RuntimeEnvironment.application,new InitConfig.Builder().build());
-    ShadowLooper looper = WXBridgeManagerTest.getLooper();
-    looper.idle();
-    ShadowLooper.runUiThreadTasksIncludingDelayedTasks();
-    instance = WXSDKInstanceTest.createInstance();
-    rednerManager = new WXRenderManager();
-    rednerManager.registerInstance(instance);//
-    WXSDKManagerTest.setRenderManager(rednerManager);
-    stmt = new DOMActionContextImpl(instance.getInstanceId(),rednerManager );
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    stmt.destroy();
-  }
-
-  void createBody(){
-    JSONObject body = new JSONObject();
-    body.put("type","div");
-    body.put("ref",WXDomObject.ROOT);
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(), TestActions.body(body),true);
-  }
-
-  void addDom(JSONObject obj,String parentRef,int index){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.addDom(obj,parentRef,index),false);
-  }
-
-  void removeDom(String ref){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.remove(ref),false);
-  }
-
-  void updateAttrs(String ref,JSONObject data){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.updateAttr(ref,data),false);
-  }
-
-  void updateStyle(String ref,JSONObject data,boolean byPesudo){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.updateStyle(ref,data,byPesudo),false);
-  }
-
-  void moveDom(String ref,String parent,int index){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.moveDom(ref,parent,index),false);
-  }
-
-  private void scrollToDom(String s, JSONObject o) {
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.scrollTo(s,o),false);
-  }
-
-  private void addEvent(String ref,String event){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.addEvent(ref,event),false);
-  }
-
-  private void removeEvent(String ref,String event){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.removeEvent(ref,event),false);
-  }
-
-  private void updateFinish(){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.updateFinish(),false);
-  }
-
-  private void createFinish(){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.createFinish(),false);
-  }
-
-  private void refreshFinish(){
-    WXSDKManager.getInstance().getWXDomManager().executeAction(instance.getInstanceId(),TestActions.refreshFinish(),false);
-  }
-
-  @Test
-  public void testCustomDomObject() throws Exception {
-    WXDomObject root = new TestDomObject();
-    root.add(new WXListDomObject(),0);
-    root.add(new WXScrollerDomObject(),0);
-    root.add(new WXTextDomObject(),0);
-    root.add(new WXSwitchDomObject(),0);
-    root.add(new TextAreaEditTextDomObject(),0);
-    stmt.layout(root);
-    root.traverseTree(ApplyStyleConsumer.getInstance());
-  }
-
-  @Test
-  public void testCreateBody() throws Exception {
-    createBody();
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testAddDom() throws Exception {
-    createBody();
-
-    JSONObject obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","100");
-
-    addDom(obj,WXDomObject.ROOT,0);
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testMoveDom() throws Exception {
-    createBody();
-    JSONObject obj;
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","100");
-    addDom(obj,WXDomObject.ROOT,0);
-
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","101");
-    addDom(obj,WXDomObject.ROOT,0);
-
-    moveDom("100",WXDomObject.ROOT,1);
-    stmt.batch();
-  }
-
-  @Test
-  public void testRemoveDom() throws Exception {
-    createBody();
-    JSONObject obj;
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","100");
-    addDom(obj,WXDomObject.ROOT,0);
-
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","101");
-    addDom(obj,WXDomObject.ROOT,0);
-
-    removeDom("101");
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testUpdateAttrs() throws Exception {
-    createBody();
-    JSONObject obj;
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","100");
-    addDom(obj,WXDomObject.ROOT,0);
-
-
-    updateAttrs("100",new JSONObject());
-    updateAttrs("100",null);
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testUpdateStyle() throws Exception {
-    createBody();
-    JSONObject obj;
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","100");
-    addDom(obj,WXDomObject.ROOT,0);
-
-    updateStyle("100",new JSONObject(),false);
-    updateStyle("100",null,false);
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testAddEvent() throws Exception {
-    createBody();
-    JSONObject obj;
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","100");
-    addDom(obj,WXDomObject.ROOT,0);
-
-    addEvent("100","click");
-    addEvent("100",null);
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testRemoveEvent() throws Exception {
-    createBody();
-    JSONObject obj;
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","100");
-    addDom(obj,WXDomObject.ROOT,0);
-
-    removeEvent("100",null);
-    addEvent("100","click");
-    removeEvent("100","click");
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testScrollToDom() throws Exception {
-    createBody();
-    JSONObject obj;
-    obj = new JSONObject();
-    obj.put("type","div");
-    obj.put("ref","100");
-    addDom(obj,WXDomObject.ROOT,0);
-
-    scrollToDom("100",null);
-    stmt.batch();
-  }
-
-
-
-  @Test
-  public void testCreateFinish() throws Exception {
-    createBody();
-    createFinish();
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testRefreshFinish() throws Exception {
-    createBody();
-    refreshFinish();
-
-    stmt.batch();
-  }
-
-  @Test
-  public void testUpdateFinish() throws Exception {
-    createBody();
-
-    updateFinish();
-    stmt.batch();
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/dom/WXStyleTest.java b/android/sdk/src/test/java/com/taobao/weex/dom/WXStyleTest.java
deleted file mode 100644
index f6641d4..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/dom/WXStyleTest.java
+++ /dev/null
@@ -1,138 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import android.graphics.Typeface;
-
-import com.taobao.weex.common.Constants;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertThat;
-import static org.hamcrest.CoreMatchers.*;
-
-
-/**
- * Description:
- *
- * Created by rowandjj(chuyi)<br/>
- */
-
-public class WXStyleTest {
-    WXStyle style;
-
-    @Before
-    public void setUp() throws Exception {
-        style = new WXStyle();
-    }
-
-
-    @Test
-    public void testBlur() {
-        assertEquals(0,style.size());
-        assertEquals(null,style.getBlur());
-        style.put(Constants.Name.FILTER,"blur(5px)");
-        assertEquals("blur(5px)",style.getBlur());
-
-    }
-
-    @Test
-    public void testFontWeight(){
-        WXStyle none = new WXStyle();
-        assertThat(WXStyle.getFontWeight(none), is(Typeface.NORMAL));
-
-        WXStyle normal = new WXStyle();
-        normal.put(Constants.Name.FONT_WEIGHT, Constants.Value.NORMAL);
-        assertThat(WXStyle.getFontWeight(normal), is(Typeface.NORMAL));
-
-        WXStyle bold = new WXStyle();
-        bold.put(Constants.Name.FONT_WEIGHT, Constants.Value.BOLD);
-        assertThat(WXStyle.getFontWeight(bold), is(Typeface.BOLD));
-
-        WXStyle illegal = new WXStyle();
-        illegal.put(Constants.Name.FONT_WEIGHT, "f");
-        assertThat(WXStyle.getFontWeight(illegal), is(Typeface.NORMAL));
-
-        WXStyle number100 = new WXStyle();
-        number100.put(Constants.Name.FONT_WEIGHT, "100");
-        assertThat(WXStyle.getFontWeight(number100), is(Typeface.NORMAL));
-
-        WXStyle number200 = new WXStyle();
-        number200.put(Constants.Name.FONT_WEIGHT, "200");
-        assertThat(WXStyle.getFontWeight(number200), is(Typeface.NORMAL));
-
-        WXStyle number300 = new WXStyle();
-        number300.put(Constants.Name.FONT_WEIGHT, "300");
-        assertThat(WXStyle.getFontWeight(number300), is(Typeface.NORMAL));
-
-        WXStyle number400 = new WXStyle();
-        number400.put(Constants.Name.FONT_WEIGHT, "400");
-        assertThat(WXStyle.getFontWeight(number400), is(Typeface.NORMAL));
-
-        WXStyle number500 = new WXStyle();
-        number500.put(Constants.Name.FONT_WEIGHT, "500");
-        assertThat(WXStyle.getFontWeight(number500), is(Typeface.NORMAL));
-
-        WXStyle number600 = new WXStyle();
-        number600.put(Constants.Name.FONT_WEIGHT, "600");
-        assertThat(WXStyle.getFontWeight(number600), is(Typeface.BOLD));
-
-        WXStyle number700 = new WXStyle();
-        number700.put(Constants.Name.FONT_WEIGHT, "700");
-        assertThat(WXStyle.getFontWeight(number700), is(Typeface.BOLD));
-
-        WXStyle number800 = new WXStyle();
-        number800.put(Constants.Name.FONT_WEIGHT, "800");
-        assertThat(WXStyle.getFontWeight(number800), is(Typeface.BOLD));
-
-        WXStyle number900 = new WXStyle();
-        number900.put(Constants.Name.FONT_WEIGHT, "900");
-        assertThat(WXStyle.getFontWeight(number900), is(Typeface.BOLD));
-    }
-
-    @After
-    public void tearDown() throws Exception {
-        style.clear();
-    }
-
-    @Test
-    public void testPesudoParsing() throws Exception {
-        Map<String,Object> styles = new HashMap<>();
-        styles.put("color","#FF0000");
-        styles.put("color:active","#008000");
-        styles.put("fontSize:active:some_clz",20);
-        styles.put("color:active:enabled",15);
-        styles.put("color:active:disabled","#008000");
-        styles.put("fontSize:active:disabled",30);
-
-        WXStyle style = new WXStyle();
-        style.putAll(styles,false);
-
-        assertEquals(style.getPesudoStyles().get(":active").keySet().size(),1);
-        assertEquals(style.getPesudoStyles().get(":active:some_clz").get("fontSize"),20);
-        assertEquals(style.getPesudoStyles().get(":active:disabled").get("fontSize"),30);
-        assertEquals(style.getPesudoStyles().get(":active:disabled").keySet().size(),2);
-    }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/dom/WXTextDomObjectTest.java b/android/sdk/src/test/java/com/taobao/weex/dom/WXTextDomObjectTest.java
deleted file mode 100644
index c01259a..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/dom/WXTextDomObjectTest.java
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.dom;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-
-import static com.taobao.weex.common.Constants.Name.*;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.api.mockito.PowerMockito;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 26/09/2016.
- */
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-public class WXTextDomObjectTest {
-
-  WXTextDomObject dom;
-
-  @Before
-  public void setUp() throws Exception {
-    dom = new WXTextDomObject();
-    WXStyle styles = dom.getStyles();
-    styles.put(LINES,10);
-    styles.put(FONT_SIZE,10);
-
-    dom.getAttrs().put(VALUE,"test");
-  }
-
-  @Test
-  public void testLayoutBefore() throws Exception {
-    dom.layoutBefore();
-  }
-
-  @Test
-  public void testMeasure() throws Exception {
-    testLayoutBefore();
-    MeasureOutput output = new MeasureOutput();
-    WXTextDomObject mock = PowerMockito.spy(dom);
-    PowerMockito.when(mock,"getTextWidth",dom.getTextPaint(),100f,false).thenReturn(10f);
-    WXTextDomObject.TEXT_MEASURE_FUNCTION.measure(mock,100,output);
-
-    assertEquals(output.width,10f,0.1f);
-  }
-
-  @Test
-  public void testLayoutAfter() throws Exception {
-    dom.layoutAfter();
-  }
-
-  @Test
-  public void testClone() throws Exception {
-    WXTextDomObject cloneDom = dom.clone();
-
-    assertFalse(cloneDom == dom);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/http/WXStreamModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/http/WXStreamModuleTest.java
deleted file mode 100644
index e0a2aa3..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/http/WXStreamModuleTest.java
+++ /dev/null
@@ -1,188 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.http;
-
-import android.os.Looper;
-import android.telecom.Call;
-
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.adapter.DefaultWXHttpAdapter;
-import com.taobao.weex.adapter.IWXHttpAdapter;
-import com.taobao.weex.bridge.JSCallback;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.common.WXRequest;
-import com.taobao.weex.common.WXResponse;
-import com.taobao.weex.common.WXThread;
-import junit.framework.Assert;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.ArgumentCaptor;
-import org.mockito.invocation.InvocationOnMock;
-import org.mockito.stubbing.Answer;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.*;
-import java.util.logging.Level;
-import java.util.logging.Logger;
-
-import static org.mockito.Mockito.*;
-import static junit.framework.Assert.*;
-
-
-/**
- * Created by sospartan on 5/24/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@PrepareForTest({WXStreamModule.class, IWXHttpAdapter.class})
-@Config(manifest= Config.NONE)
-public class WXStreamModuleTest {
-
-  @Before
-  public void setup() throws Exception{
-
-  }
-
-  private WXResponse successResponse(){
-    WXResponse resp = new WXResponse();
-    resp.data = "data";
-    resp.statusCode = "200";
-    return resp;
-  }
-
-  static class Callback implements JSCallback{
-     Map<String, Object> mData;
-
-    @Override
-    public void invoke(Object data) {
-      mData = (Map<String,Object>)data;
-    }
-
-    @Override
-    public void invokeAndKeepAlive(Object data) {
-      mData = (Map<String,Object>)data;
-    }
-  }
-
-
-  @Test
-  public void testFetchInvaildOptions() throws Exception{
-    IWXHttpAdapter adapter = new IWXHttpAdapter() {
-      @Override
-      public void sendRequest(WXRequest request, OnHttpListener listener) {
-        listener.onHttpFinish(successResponse());
-      }
-    };
-
-    WXStreamModule streamModule = new WXStreamModule(adapter);
-    Callback cb = new Callback();
-    streamModule.fetch("",cb,null);
-
-    assert   !(boolean)cb.mData.get("ok");
-  }
-
-  private WXStreamModule createModule(IWXHttpAdapter adapter){
-    WXStreamModule m = new WXStreamModule(adapter);
-    m.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-    return m;
-  }
-
-  @Test
-  public void testFetchSuccessFinish() throws Exception{
-    IWXHttpAdapter adapter = new IWXHttpAdapter() {
-      @Override
-      public void sendRequest(WXRequest request, OnHttpListener listener) {
-        listener.onHttpFinish(successResponse());
-      }
-    };
-
-    WXStreamModule streamModule = createModule(adapter);
-    Callback cb = new Callback();
-    streamModule.fetch("{'url':'http://www.taobao.com'}",cb,null);
-
-    assert   (boolean)cb.mData.get("ok");
-  }
-
-
-  @Test
-  public void testFetchHeaderReceived() throws Exception{
-    IWXHttpAdapter adapter = new IWXHttpAdapter() {
-      @Override
-      public void sendRequest(WXRequest request, OnHttpListener listener) {
-        Map<String,List<String>> headers = new HashMap<>();
-        headers.put("key", Arrays.asList("someval"));
-        listener.onHeadersReceived(200,headers);
-      }
-    };
-
-    WXStreamModule streamModule = createModule(adapter);
-    Callback cb = new Callback();
-    streamModule.fetch("{'url':'http://www.taobao.com'}",null,cb);
-
-    assert   ((Map<String,String>)cb.mData.get("headers")).get("key").equals("someval");
-  }
-
-  @Test
-  public void testFetchRequestHttpbinCallback() throws Exception{
-    WXStreamModule streamModule = createModule(new DefaultWXHttpAdapter());
-    JSCallback progress = mock(JSCallback.class);
-    JSCallback finish = mock(JSCallback.class);
-    System.out.print("request start "+System.currentTimeMillis());
-    streamModule.fetch("{method: 'POST',url: 'http://httpbin.org/post',type:'json'}",finish,progress);
-    verify(progress,timeout(10*1000).atLeastOnce()).invokeAndKeepAlive(anyMapOf(String.class, Object.class));
-    verify(finish,timeout(10*1000).times(1)).invoke(anyMapOf(String.class, Object.class));
-    System.out.print("\nrequest finish"+System.currentTimeMillis());
-  }
-
-
-  @Test
-  public void testFetchStatus() throws Exception{
-    WXStreamModule streamModule = createModule(new IWXHttpAdapter() {
-      @Override
-      public void sendRequest(WXRequest request, OnHttpListener listener) {
-        WXResponse response = new WXResponse();
-        response.statusCode = "-1";
-        listener.onHttpFinish(response);
-      }
-    });
-    Callback finish = new Callback();
-
-    streamModule.fetch("",finish,null);
-    assertEquals(finish.mData.get(WXStreamModule.STATUS_TEXT),Status.ERR_INVALID_REQUEST);
-
-    streamModule.fetch("{method: 'POST',url: 'http://httpbin.org/post',type:'json'}",finish,null);
-    assertEquals(finish.mData.get(WXStreamModule.STATUS_TEXT),Status.ERR_CONNECT_FAILED);
-
-    streamModule = createModule(new IWXHttpAdapter() {
-      @Override
-      public void sendRequest(WXRequest request, OnHttpListener listener) {
-        WXResponse response = new WXResponse();
-        response.statusCode = "302";
-        listener.onHttpFinish(response);
-      }
-    });
-    streamModule.fetch("{method: 'POST',url: 'http://httpbin.org/post',type:'json'}",finish,null);
-    assertEquals(finish.mData.get(WXStreamModule.STATUS),302);
-    assertEquals(finish.mData.get(WXStreamModule.STATUS).getClass(),Integer.class);
-    assertEquals(finish.mData.get(WXStreamModule.STATUS_TEXT),Status.getStatusText("302"));
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/ComponentHolderTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/ComponentHolderTest.java
deleted file mode 100644
index 1ddb122..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/ComponentHolderTest.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.bridge.Invoker;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXVContainer;
-
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Created by sospartan on 8/4/16.
- */
-public class ComponentHolderTest {
-    public static class TestComponentHolder implements IFComponentHolder{
-
-      WXComponent mComponent;
-      TestComponentHolder(WXComponent comp){
-        mComponent = comp;
-      }
-
-      @Override
-      public void loadIfNonLazy() {
-
-      }
-
-      @Override
-      public Invoker getPropertyInvoker(String name) {
-        return null;
-      }
-
-      @Override
-      public Invoker getMethodInvoker(String name) {
-        return null;
-      }
-
-      @Override
-      public String[] getMethods() {
-        return new String[0];
-      }
-
-      @Override
-      public WXComponent createInstance(WXSDKInstance instance, WXDomObject node, WXVContainer parent) throws IllegalAccessException, InvocationTargetException, InstantiationException {
-        mComponent.bindHolder(this);
-        return mComponent;
-      }
-    }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/WXRenderStatementTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/WXRenderStatementTest.java
deleted file mode 100644
index 1c4fef9..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/WXRenderStatementTest.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui;
-
-import android.text.TextUtils;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.ui.component.WXComponentFactory;
-import com.taobao.weex.utils.WXSoInstallMgrSdk;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.powermock.api.mockito.PowerMockito;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.PowerMockRunner;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by lixinke on 16/3/2.
- */
-@RunWith(PowerMockRunner.class)
-@Config(constants = BuildConfig.class)
-@PrepareForTest({WXSoInstallMgrSdk.class, TextUtils.class,WXComponentFactory.class})
-public class WXRenderStatementTest {
-
-    RenderContextImpl mWXRenderStatement;
-
-    @Before
-    public void setUp() throws Exception {
-        PowerMockito.mockStatic(WXSoInstallMgrSdk.class);
-        PowerMockito.mockStatic(TextUtils.class);
-        PowerMockito.mockStatic(WXComponentFactory.class);
-        PowerMockito.when(TextUtils.isEmpty("124")).thenReturn(true);
-        PowerMockito.when(WXSoInstallMgrSdk.initSo(null, 1, null)).thenReturn(true);
-        WXSDKInstance instance = Mockito.mock(WXSDKInstance.class);
-        mWXRenderStatement = new RenderContextImpl(instance);
-    }
-
-    public void testCreateBody() throws Exception {
-
-    }
-
-    @Test
-    public void testCreateBodyOnDomThread() throws Exception {
-
-    }
-
-    public void testSetPadding() throws Exception {
-
-    }
-
-    public void testSetLayout() throws Exception {
-
-    }
-
-    public void testSetExtra() throws Exception {
-
-    }
-
-    public void testAddComponent() throws Exception {
-
-    }
-
-    @Test
-    public void testCreateComponentOnDomThread() throws Exception {
-
-
-//        PowerMockito.mockStatic(TextUtils.class);
-//        PowerMockito.mockStatic(WXComponentFactory.class);
-//        PowerMockito.when(TextUtils.isEmpty("1234")).thenReturn(true);
-//        PowerMockito.when(WXComponentFactory.newInstance(null, null, null, null)).thenReturn(PowerMockito.mock(WXDiv.class));
-//
-//        WXDomObject object = PowerMockito.mock(WXDomObject.class);
-//        WXComponent wxComponent = mWXRenderStatement.createBodyOnDomThread(object);
-//        assertNotNull(wxComponent);
-
-    }
-
-    public void testAddComponent1() throws Exception {
-
-    }
-
-    public void testRemoveComponent() throws Exception {
-
-    }
-
-    public void testMove() throws Exception {
-
-    }
-
-    public void testAddEvent() throws Exception {
-
-    }
-
-    public void testRemoveEvent() throws Exception {
-
-    }
-
-    public void testUpdateAttrs() throws Exception {
-
-    }
-
-    public void testUpdateStyle() throws Exception {
-
-    }
-
-    public void testScrollTo() throws Exception {
-
-    }
-
-    public void testCreateFinish() throws Exception {
-
-    }
-
-    public void testRefreshFinish() throws Exception {
-
-    }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/animation/WXAnimationModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/animation/WXAnimationModuleTest.java
deleted file mode 100644
index 7dd4858..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/animation/WXAnimationModuleTest.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.animation;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 7/29/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*","org.json.*" })
-@PrepareForTest()
-public class WXAnimationModuleTest {
-
-
-  WXAnimationModule module;
-  @Before
-  public void setUp() throws Exception {
-    module = new WXAnimationModule();
-    module.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-
-
-  }
-
-  @Test
-  public void testTransition() throws Exception {
-    module.transition("","","");
-    module.transition("test","test","");
-  }
-
-  @Test
-  public void testCreateAnimatorListener() throws Exception {
-
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/ComponentTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/ComponentTest.java
deleted file mode 100644
index bcafc2a..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/ComponentTest.java
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.view.View;
-
-import com.taobao.weex.WXSDKInstance;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by sospartan on 8/3/16.
- */
-public class ComponentTest {
-  public static void create(WXComponent comp){
-    create(comp,null);
-  }
-  public static void create(WXComponent comp,View view){
-    TestDomObject domObject = new TestDomObject();
-    WXVContainer parent;
-
-    if((parent = comp.getParent())!=null){
-      if(view != null) {
-        comp.mHost = view;
-      }else{
-        comp.createView();
-      }
-    }else{
-      parent = WXDivTest.create();
-      parent.addChild(comp);
-      parent.createChildViewAt(-1);
-    }
-
-    comp.setSafeLayout(comp);
-
-//    domObject = new TestDomObject();
-//    comp.updateDom(domObject);
-    comp.applyLayoutAndEvent(comp);
-
-    addEvent(comp);
-  }
-
-
-  public static void setProperty(WXComponent comp,String[] propNames,Object[][] valueGroups){
-    Map<String, Object> props = new HashMap<>();
-    int len = propNames.length;
-
-    if(propNames.length != valueGroups.length){
-      throw new RuntimeException("Property name and value group length not match");
-    }
-    for (int i=0;i<len;i++){
-      for (Object obj:valueGroups[i]){
-        props.put(propNames[i],obj);
-        comp.updateProperties(props);
-      }
-
-    }
-  }
-
-  public static void addEvent(WXComponent comp){
-    for (String event :
-        TestConstants.Events) {
-      comp.addEvent(event);
-    }
-  }
-
-  public static void destory(WXComponent comp){
-    comp.destroy();
-  }
-
-  public static <T> T createComponent(WXDomObject dom, WXVContainer parent, Class<T> type) throws NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {
-     return type
-         .getConstructor(WXSDKInstance.class,WXDomObject.class,WXVContainer.class)
-        .newInstance(parent.getInstance(),dom,parent);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/EditComponentTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/EditComponentTest.java
deleted file mode 100644
index 8a40791..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/EditComponentTest.java
+++ /dev/null
@@ -1,136 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import com.taobao.weex.ui.view.WXEditText;
-
-import junit.framework.Assert;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-
-import static com.taobao.weex.common.Constants.Name.*;
-import static com.taobao.weex.common.Constants.Value.*;
-
-/**
- * Created by sospartan on 8/3/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-@PrepareForTest
-public class EditComponentTest {
-  static final String[] PROPS = {
-      TEXT_ALIGN,
-      FONT_SIZE,
-      COLOR,
-      TYPE,
-      VALUE,
-      PLACE_HOLDER,
-      PLACEHOLDER_COLOR,
-      AUTOFOCUS,
-      LINES,
-      SINGLELINE,
-      MAX_LENGTH,
-      ROWS};
-  static final Object[][] TEST_VALUES = {
-      {null,CENTER, Constants.Name.LEFT, Constants.Name.RIGHT,"kdkdkdk"},
-      {null,12,Integer.MAX_VALUE,0,-2},
-      {"red","#000","#ffffff","rgb(12,23,45)"},
-      {"DKDK",
-          TEXT,
-          PASSWORD,
-          TEL,
-          EMAIL,
-          URL,
-          DATE,
-          TIME,
-          DATETIME},
-      {null,123,"dkdkdkdk"},
-      {null,123,"dkdkdkdk"},
-      {"red","#000","#ffffff","rgb(12,23,45)"},
-      {null,true,"true","false",false,"test"},
-      {null,34,Integer.MAX_VALUE,-1,"test"},
-      {null,true,"true","false",false,"test"},
-      {null,34,Integer.MAX_VALUE,-1,"test"},
-      {null,34,Integer.MAX_VALUE,-1,"test"},
-      };
-
-  AbstractEditComponent component;
-
-  public static WXInput create() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXInput) new SimpleComponentHolder(WXInput.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  public static Textarea createTextarea() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (Textarea) new SimpleComponentHolder(Textarea.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-
-  @Before
-  public void setUp() throws Exception {
-    component = create();
-    ComponentTest.create(component);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    ComponentTest.destory(component);
-  }
-
-  @Test
-  public void testEvent() throws Exception {
-    WXEditText view = component.getHostView();
-    view.performClick();
-    view.setText("");
-    view.requestFocus();
-    view.setText("hello");
-    view.clearFocus();
-    view.setText(null);
-  }
-
-  @Test
-  public void testSetProperty() throws Exception {
-
-    ComponentTest.setProperty(component,PROPS,TEST_VALUES);
-  }
-
-  @Test
-  public void testFocus() throws Exception {
-    component.getParent().mHost = component.getParent().initComponentHostView(component.getContext());
-    component.getParent().interceptFocus();
-    component.getHostView().clearFocus();
-    component.focus();
-    Assert.assertEquals(component.getHostView().hasFocus(), true);
-  }
-
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/TestComponent.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/TestComponent.java
deleted file mode 100644
index 1ac43e6..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/TestComponent.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weex.WXSDKInstance;
-
-/**
- * Created by sospartan on 7/27/16.
- */
-public class TestComponent extends WXDiv{
-  public TestComponent(WXSDKInstance instance, WXDomObject dom, WXVContainer parent, String instanceId, boolean isLazy) {
-    super(instance, dom, parent, instanceId, isLazy);
-  }
-
-  public TestComponent(WXSDKInstance instance, WXDomObject dom, WXVContainer parent) {
-    super(instance, dom, parent);
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/TestConstants.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/TestConstants.java
deleted file mode 100644
index f0d060b..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/TestConstants.java
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weex.common.Constants;
-
-/**
- * Created by sospartan on 8/9/16.
- */
-public class TestConstants {
-  public static final String Events[] = {"", null,
-      Constants.Event.INPUT,
-      Constants.Event.APPEAR,
-      Constants.Event.BLUR,
-      Constants.Event.CLICK,
-      Constants.Event.CHANGE,
-      Constants.Event.FOCUS,
-      Constants.Event.DISAPPEAR,
-  };
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/TextareaTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/TextareaTest.java
deleted file mode 100644
index 33fe97d..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/TextareaTest.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 8/9/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class TextareaTest  {
-
-  Textarea component;
-
-  @Before
-  public void setUp() throws Exception {
-    component = EditComponentTest.createTextarea();
-    ComponentTest.create(component);
-  }
-
-  @Test
-  public void testSetProperty() throws Exception {
-    Map<String, Object> props = new HashMap<>();
-    int len = EditComponentTest.PROPS.length;
-
-    for (int i = 0; i < len; i++) {
-      for (Object obj : EditComponentTest.TEST_VALUES[i]) {
-        props.put(EditComponentTest.PROPS[i], obj);
-        component.updateProperties(props);
-      }
-
-    }
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    ComponentTest.destory(component);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXComponentTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXComponentTest.java
deleted file mode 100644
index 8ea91f1..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXComponentTest.java
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.common.Constants;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 7/27/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXComponentTest {
-
-  WXComponent component;
-
-  @Before
-  public void setUp() throws Exception {
-    WXVContainer root = WXDivTest.create();
-    ComponentTest.create(root);
-    component = WXDivTest.create(root);
-    ComponentTest.create(component);
-  }
-
-  @Test
-  public void testSetProperty() throws Exception {
-
-    assertTrue(component.setProperty(Constants.Name.VISIBILITY,null));
-    assertTrue(component.setProperty(Constants.Name.VISIBILITY, Constants.Value.VISIBLE));
-
-    assertTrue(component.setProperty(Constants.Name.DISABLED,true));
-    assertTrue(component.setProperty(Constants.Name.POSITION, Constants.Value.FIXED));
-    assertTrue(component.setProperty(Constants.Name.BACKGROUND_COLOR, "#ffffff"));
-    assertTrue(component.setProperty(Constants.Name.OPACITY, 0.5f));
-    assertTrue(component.setProperty(Constants.Name.BORDER_RADIUS,0.5f));
-    assertTrue(component.setProperty(Constants.Name.BORDER_RADIUS,null));
-    assertTrue(component.setProperty(Constants.Name.BORDER_WIDTH,null));
-    assertTrue(component.setProperty(Constants.Name.BORDER_WIDTH,10));
-    assertTrue(component.setProperty(Constants.Name.BORDER_STYLE,null));
-    assertTrue(component.setProperty(Constants.Name.BORDER_STYLE, "SOLID"));
-    assertTrue(component.setProperty(Constants.Name.BORDER_COLOR,null));
-    assertTrue(component.setProperty(Constants.Name.BORDER_COLOR, "#ff0000"));
-
-    assertTrue(component.setProperty(Constants.Name.BORDER_TOP_LEFT_RADIUS, 1));
-    assertTrue(component.setProperty(Constants.Name.BORDER_TOP_RIGHT_RADIUS, 1));
-    assertTrue(component.setProperty(Constants.Name.BORDER_BOTTOM_LEFT_RADIUS, 1));
-    assertTrue(component.setProperty(Constants.Name.BORDER_BOTTOM_RIGHT_RADIUS, 1));
-    assertTrue(component.setProperty(Constants.Name.BORDER_TOP_WIDTH, 1));
-    assertTrue(component.setProperty(Constants.Name.BORDER_LEFT_WIDTH, 1));
-    assertTrue(component.setProperty(Constants.Name.BORDER_BOTTOM_WIDTH, 1));
-    assertTrue(component.setProperty(Constants.Name.BORDER_RIGHT_WIDTH,1));
-
-    assertTrue(component.setProperty(Constants.Name.BORDER_TOP_COLOR, "#ff0000"));
-    assertTrue(component.setProperty(Constants.Name.BORDER_BOTTOM_COLOR, "#ff0000"));
-    assertTrue(component.setProperty(Constants.Name.BORDER_LEFT_COLOR, "#ff0000"));
-    assertTrue(component.setProperty(Constants.Name.BORDER_RIGHT_COLOR, "#ff0000"));
-
-    assertTrue(component.setProperty(Constants.Name.WIDTH, null));
-    assertTrue(component.setProperty(Constants.Name.MIN_WIDTH, null));
-    assertTrue(component.setProperty(Constants.Name.MAX_WIDTH, null));
-    assertTrue(component.setProperty(Constants.Name.HEIGHT, null));
-    assertTrue(component.setProperty(Constants.Name.MIN_HEIGHT, null));
-    assertTrue(component.setProperty(Constants.Name.MAX_HEIGHT, null));
-    assertTrue(component.setProperty(Constants.Name.ALIGN_ITEMS, null));
-    assertTrue(component.setProperty(Constants.Name.ALIGN_SELF, null));
-    assertTrue(component.setProperty(Constants.Name.FLEX, null));
-    assertTrue(component.setProperty(Constants.Name.FLEX_DIRECTION, null));
-    assertTrue(component.setProperty(Constants.Name.JUSTIFY_CONTENT, null));
-    assertTrue(component.setProperty(Constants.Name.FLEX_WRAP, null));
-    assertTrue(component.setProperty(Constants.Name.MARGIN, null));
-    assertTrue(component.setProperty(Constants.Name.MARGIN_TOP, null));
-    assertTrue(component.setProperty(Constants.Name.MARGIN_LEFT, null));
-    assertTrue(component.setProperty(Constants.Name.MARGIN_RIGHT, null));
-    assertTrue(component.setProperty(Constants.Name.MARGIN_BOTTOM, null));
-    assertTrue(component.setProperty(Constants.Name.PADDING, null));
-    assertTrue(component.setProperty(Constants.Name.PADDING_TOP, null));
-    assertTrue(component.setProperty(Constants.Name.PADDING_LEFT, null));
-    assertTrue(component.setProperty(Constants.Name.PADDING_RIGHT, null));
-    assertTrue(component.setProperty(Constants.Name.PADDING_BOTTOM, null));
-
-  }
-
-
-  @Test
-  public void testAddEvent() throws Exception {
-    component.addEvent(Constants.Event.FOCUS);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXDivTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXDivTest.java
deleted file mode 100644
index 310af8e..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXDivTest.java
+++ /dev/null
@@ -1,120 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.dom.WXEvent;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by gulin on 16/2/24.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-public class WXDivTest {
-
-    private WXDiv mWXDiv;
-    private WXText child2;
-
-
-    public static WXDiv create(){
-        return create(null);
-    }
-
-    public static WXDiv create(WXVContainer parent){
-        WXDiv div = new WXDiv(WXSDKInstanceTest.createInstance(),new TestDomObject(),parent);
-        return div;
-    }
-
-
-    @Before
-    public void setUp() throws Exception {
-        WXSDKInstance instance = Mockito.mock(WXSDKInstance.class);
-        Mockito.when(instance.getContext()).thenReturn(RuntimeEnvironment.application);
-
-        WXDomObject divDom = new WXDomObject();
-        WXDomObject spy = Mockito.spy(divDom);
-        Mockito.when(spy.getPadding()).thenReturn(new Spacing());
-        Mockito.when(spy.getEvents()).thenReturn(new WXEvent());
-        Mockito.when(spy.clone()).thenReturn(divDom);
-        TestDomObject.setRef(divDom,"1");
-        mWXDiv = new WXDiv(instance, divDom, null);
-        mWXDiv.initView();
-    }
-
-    @Test
-    public void testAddChild(){
-        WXSDKInstance instance = Mockito.mock(WXSDKInstance.class);
-        Mockito.when(instance.getContext()).thenReturn(RuntimeEnvironment.application);
-
-        WXDomObject testDom = Mockito.mock(WXDomObject.class);
-        Mockito.when(testDom.getPadding()).thenReturn(new Spacing());
-        Mockito.when(testDom.clone()).thenReturn(testDom);
-        TestDomObject.setRef(testDom,"2");
-        WXText child1 = new WXText(instance, testDom, mWXDiv);
-        child1.initView();
-
-        mWXDiv.addChild(child1, 0);
-
-        assertEquals(1, mWXDiv.childCount());
-
-        WXDomObject testDom2 = Mockito.spy(new WXDomObject());
-        Mockito.when(testDom2.getPadding()).thenReturn(new Spacing());
-        Mockito.when(testDom2.clone()).thenReturn(testDom2);
-        TestDomObject.setRef(testDom2,"3");
-        child2 = new WXText(instance, testDom2, mWXDiv);
-        child2.initView();
-
-        mWXDiv.addChild(child2, -1);
-
-        assertEquals(2, mWXDiv.childCount());
-        assertEquals(child2, mWXDiv.getChild(1));
-
-        WXDomObject testDom3 = Mockito.mock(WXDomObject.class);
-        Mockito.when(testDom3.getPadding()).thenReturn(new Spacing());
-        Mockito.when(testDom3.clone()).thenReturn(testDom3);
-        TestDomObject.setRef(testDom3,"4");
-        WXText child3 = new WXText(instance, testDom3, mWXDiv);
-        child3.initView();
-
-        mWXDiv.addChild(child3, 1);
-
-        assertEquals(3, mWXDiv.childCount());
-        assertEquals(child3, mWXDiv.getChild(1));
-    }
-
-    @Test
-    public void testRemove(){
-        testAddChild();
-        mWXDiv.remove(child2,true);
-
-        assertEquals(2, mWXDiv.childCount());
-    }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXEmbedTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXEmbedTest.java
deleted file mode 100644
index 752b425..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXEmbedTest.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.common.Constants;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 26/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-public class WXEmbedTest {
-
-  WXEmbed component;
-
-  @Before
-  public void setUp() throws Exception {
-
-    WXEnvironment.sApplication = RuntimeEnvironment.application;
-    WXDiv div = WXDivTest.create();
-    ComponentTest.create(div);
-    component = new WXEmbed(div.getInstance(),new TestDomObject(),div);
-    ComponentTest.create(component);
-    component.getDomObject().getStyles().put(Constants.Name.VISIBILITY, Constants.Value.VISIBLE);
-  }
-
-  @Test
-  public void testSetProperty() throws Exception {
-    component.setProperty(Constants.Name.SRC,"http://www.taobao.com");
-  }
-
-  @Test
-  public void testSetVisibility() throws Exception {
-    component.setProperty(Constants.Name.VISIBILITY,Constants.Value.HIDDEN);
-    component.setProperty(Constants.Name.SRC,"http://www.taobao.com");
-    component.setProperty(Constants.Name.VISIBILITY,Constants.Value.VISIBLE);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    component.destroy();
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXHeaderTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXHeaderTest.java
deleted file mode 100644
index 740f7c4..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXHeaderTest.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.ui.SimpleComponentHolder;
-
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Created by sospartan on 8/29/16.
- */
-public class WXHeaderTest {
-
-  public static WXHeader create(WXVContainer parent) throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXHeader) new SimpleComponentHolder(WXHeader.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), parent);
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXImageTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXImageTest.java
deleted file mode 100644
index 9999f71..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXImageTest.java
+++ /dev/null
@@ -1,155 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import static junit.framework.Assert.assertEquals;
-import static junit.framework.Assert.assertNotNull;
-import static junit.framework.Assert.assertNull;
-
-import android.graphics.Bitmap;
-import android.graphics.drawable.Drawable;
-import android.view.ViewGroup;
-import android.widget.ImageView;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.TestActivity;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.common.WXImageSharpen;
-import com.taobao.weex.dom.WXAttr;
-import com.taobao.weex.ui.view.WXImageView;
-import com.taobao.weex.ui.view.border.BorderDrawable;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.powermock.api.mockito.PowerMockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.Robolectric;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXImageTest {
-
-  @Rule
-  public PowerMockRule rule = new PowerMockRule();
-
-  WXImage mWXImage;
-  WXSDKInstance mInstance;
-  WXDiv mWXDiv;
-  WXDomObject mDomObject;
-
-  @Before
-  public void setUp() throws Exception {
-
-    mInstance = WXSDKInstanceTest.createInstance();
-    mDomObject = new TestDomObject();
-    PowerMockito.when(Mockito.spy(mDomObject).clone()).thenReturn(mDomObject);
-    mWXDiv = PowerMockito.mock(WXDiv.class);
-    mWXImage = new WXImage(mInstance, mDomObject, mWXDiv);
-
-  }
-
-
-  @Test
-  @PrepareForTest(WXImageView.class)
-  public void testInitComponentHostView() throws Exception {
-
-    ImageView imageView = mWXImage.initComponentHostView(Robolectric.setupActivity(TestActivity.class));
-    assertEquals(imageView.getClass(), WXImageView.class);
-
-  }
-
-  @Test
-  @PrepareForTest(WXImageView.class)
-  public void testSetBackgroundColor() throws Exception {
-
-    ImageView imageView = mWXImage.initComponentHostView(Robolectric.setupActivity(TestActivity.class));
-    mWXImage.mHost = imageView;
-
-    mWXImage.setBackgroundColor("#FFFFFF");
-
-    Drawable drawable = mWXImage.getHostView().getBackground();
-    assertEquals(drawable instanceof BorderDrawable, true);
-  }
-
-
-  @Test
-  public void testSetProperty() throws Exception {
-
-    ImageView imageView = mWXImage.initComponentHostView(Robolectric.setupActivity(TestActivity.class));
-    mWXImage.mHost = imageView;
-
-    mWXImage.setProperty(Constants.Name.RESIZE_MODE, "cover");
-    ImageView.ScaleType scaleType = mWXImage.getHostView().getScaleType();
-    assertEquals(scaleType, ImageView.ScaleType.CENTER_CROP);
-
-
-  }
-
-
-  @Test
-  public void testSetResizeMode() throws Exception {
-
-    ImageView imageView = mWXImage.initComponentHostView(Robolectric.setupActivity(TestActivity.class));
-    mWXImage.mHost = imageView;
-
-    mWXImage.setResizeMode("cover");
-    ImageView.ScaleType scaleType = mWXImage.getHostView().getScaleType();
-    assertEquals(scaleType, ImageView.ScaleType.CENTER_CROP);
-
-  }
-
-  @Test
-  public void testSetResize() throws Exception {
-    ImageView imageView = mWXImage.initComponentHostView(Robolectric.setupActivity(TestActivity.class));
-    mWXImage.mHost = imageView;
-
-    mWXImage.setResize("cover");
-    ImageView.ScaleType scaleType = mWXImage.getHostView().getScaleType();
-    assertEquals(scaleType, ImageView.ScaleType.CENTER_CROP);
-  }
-
-  @Test
-  public void testSetSrc() throws Exception {
-    TestDomObject.setAttribute((WXDomObject)mWXImage.getDomObject(),PowerMockito.mock(WXAttr.class));
-    PowerMockito.when(mWXImage.getDomObject().getAttrs().getImageSharpen()).thenReturn(WXImageSharpen.SHARPEN);
-    mWXImage.setSrc("");
-
-  }
-
-  @Test
-  public void testSetImageBitmap(){
-    ImageView imageView = mWXImage.initComponentHostView(Robolectric.setupActivity(TestActivity.class));
-    imageView.setLayoutParams(new ViewGroup.LayoutParams(
-        ViewGroup.LayoutParams.WRAP_CONTENT,
-        ViewGroup.LayoutParams.WRAP_CONTENT));
-    imageView.setImageBitmap(null);
-    assertNull(imageView.getDrawable());
-
-    imageView.setImageBitmap(Bitmap.createBitmap(100, 100, Bitmap.Config.RGB_565));
-    assertNotNull(imageView.getDrawable());
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXLoadingTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXLoadingTest.java
deleted file mode 100644
index 59d803e..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXLoadingTest.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Created by sospartan on 28/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXLoadingTest {
-
-  public static WXLoading create() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXLoading) new SimpleComponentHolder(WXLoading.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  WXLoading component;
-
-  @Before
-  public void setUp() throws Exception {
-    component = create();
-    ComponentTest.create(component);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    component.destroy();
-  }
-
-  @Test
-  public void testOnLoading() throws Exception {
-    component.onLoading();
-  }
-
-
-  @Test
-  public void testSetProperty() throws Exception {
-    component.setProperty(Constants.Name.DISPLAY,WXLoading.HIDE);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXRefreshTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXRefreshTest.java
deleted file mode 100644
index 99ca151..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXRefreshTest.java
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Created by sospartan on 28/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXRefreshTest {
-
-  public static WXRefresh create() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXRefresh) new SimpleComponentHolder(WXRefresh.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  WXRefresh component;
-
-  @Before
-  public void setUp() throws Exception {
-    component = create();
-    ComponentTest.create(component);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    component.destroy();
-  }
-
-  @Test
-  public void testOnRefresh() throws Exception {
-    component.onRefresh();
-  }
-
-  @Test
-  public void testOnPullingDown() throws Exception {
-    component.onPullingDown(10,100,100);
-  }
-
-  @Test
-  public void testSetProperty() throws Exception {
-    component.setProperty(Constants.Name.DISPLAY,WXRefresh.HIDE);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXScrollerTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXScrollerTest.java
deleted file mode 100644
index 185ab2e..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXScrollerTest.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.ui.view.WXScrollView;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 8/25/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXScrollerTest {
-
-  public static WXScroller create(){
-    WXDiv div = WXDivTest.create();
-    ComponentTest.create(div);
-    WXScroller component = new WXScroller(WXSDKInstanceTest.createInstance(),new WXScrollerDomObject(),div);
-    div.addChild(component);
-    return component;
-  }
-
-
-  WXScroller component;
-
-  @Before
-  public void setUp() throws Exception {
-    component = create();
-    ComponentTest.create(component);
-  }
-
-  @Test
-  public void testAddChild() throws Exception{
-    WXDiv div = WXDivTest.create(component);
-    component.addChild(div);
-    ComponentTest.create(div);
-
-  }
-
-  @Test
-  public void testScroll() throws Exception {
-    WXScroller comp = create();
-    WXDiv div = WXDivTest.create(comp);
-    ComponentTest.create(div);
-    comp.addChild(div);
-    ComponentTest.create(comp);
-    WXScrollView view = (WXScrollView) comp.getInnerView();
-    view.scrollTo(100,100);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    component.destroy();
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSliderNeighborTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSliderNeighborTest.java
deleted file mode 100644
index 0f18fa5..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSliderNeighborTest.java
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 27/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXSliderNeighborTest {
-
-  public static WXSliderNeighbor create() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXSliderNeighbor) new SimpleComponentHolder(WXSliderNeighbor.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  WXSliderNeighbor component;
-
-  @Before
-  public void setUp() throws Exception {
-    component = create();
-    ComponentTest.create(component);
-  }
-
-  @Test
-  public void testPages() throws Exception {
-    component = create();
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-
-    WXIndicator indicator = new WXIndicator(component.getInstance(),new TestDomObject(),component,false);
-    ComponentTest.create(indicator);
-    component.addChild(indicator);
-    ComponentTest.create(component);
-
-    assertEquals(5,component.mViewPager.getCirclePageAdapter().getRealCount());
-    assertEquals(6,component.getChildCount());
-
-    component.mViewPager.setCurrentItem(0);
-  }
-
-  @Test
-  public void testSetProperties() throws Exception {
-    component.setProperty(WXSliderNeighbor.NEIGHBOR_ALPHA,0.4f);
-    component.setProperty(WXSliderNeighbor.NEIGHBOR_SCALE,0.9f);
-  }
-
-  @Test
-  public void testZoomTransformer() throws Exception {
-    component = create();
-    TestComponent page = ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class);
-    TestComponent pageChild = ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class);
-    page.addChild(pageChild);
-    component.addChild(page);
-
-    ComponentTest.create(component);
-//    ComponentTest.create(pageChild);
-//    ComponentTest.create(page);
-    WXSliderNeighbor.ZoomTransformer transformer = component.createTransformer();
-    transformer.transformPage(page.getHostView(),0.2f);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    component.destroy();
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSliderTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSliderTest.java
deleted file mode 100644
index 697d3b4..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSliderTest.java
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.ui.SimpleComponentHolder;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-
-import static com.taobao.weex.common.Constants.Name;
-import static org.junit.Assert.assertEquals;
-
-/**
- * Created by sospartan on 8/9/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXSliderTest {
-
-  WXSlider component;
-
-  static final String[] PROPS = {
-      Name.AUTO_PLAY,
-      Name.VALUE,
-      "unknown",
-      Name.INTERVAL,
-      Name.INDEX,
-      Name.SHOW_INDICATORS
-  };
-
-  static final Object[][] VALUES = {
-      {"","true","false",true,false,null},
-      {"","1","0",1,-1,null},
-      {null,"","test"},
-      {"","100","0",100,-1,null},
-      {"","1","0",1,2,3,-1,null},
-      {"","true","false",true,false,null}
-  };
-
-  public static WXSlider create() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXSlider) new SimpleComponentHolder(WXSlider.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  public static WXIndicator createIndicator() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXIndicator) new SimpleComponentHolder(WXIndicator.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  public static WXIndicator createIndicator(WXVContainer container) throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXIndicator) new SimpleComponentHolder(WXIndicator.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), container);
-  }
-
-  @Before
-  public void setup() throws Exception {
-    component = create();
-    ComponentTest.create(component);
-  }
-
-  @Test
-  public void testSetProperties() throws Exception {
-    ComponentTest.setProperty(component,PROPS,VALUES);
-  }
-
-  @Test
-  public void testPages() throws Exception {
-    component = create();
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-    component.addChild(ComponentTest.createComponent(new TestDomObject(),component,TestComponent.class));
-
-    WXIndicator indicator = new WXIndicator(component.getInstance(),new TestDomObject(),component,false);
-    ComponentTest.create(indicator);
-    component.addChild(indicator);
-    ComponentTest.create(component);
-
-    assertEquals(5,component.mViewPager.getCirclePageAdapter().getRealCount());
-    assertEquals(6,component.getChildCount());
-
-    component.mViewPager.setCurrentItem(0);
-  }
-
-  static final String[] IPROPS = {
-      Name.ITEM_SIZE,
-      Name.ITEM_SELECTED_COLOR,
-      Name.ITEM_COLOR,
-      "unknown"
-  };
-
-  static final Object[][] IVALUES = {
-      {"0",0,1,"test"},
-      {"#ffffff",123,-1},
-      {"#ffffff",123,-1},
-      {"#ffffff",123,-1},
-  };
-
-  @Test
-  public void testIndicator() throws Exception {
-    WXIndicator indicator = createIndicator(component);
-    ComponentTest.create(indicator);
-    component.addChild(indicator);
-    ComponentTest.setProperty(indicator,IPROPS,IVALUES);
-  }
-
-  @Test
-  public void testOnScrollListener() throws Exception {
-    component.mViewPager.addOnPageChangeListener(new WXSlider.SliderOnScrollListener(component));
-    component.setOffsetXAccuracy(0.05f);
-    component.mViewPager.setCurrentItem(0);
-    for (int index=1;index<component.mViewPager.getRealCount();index++) {
-      component.mViewPager.setCurrentItem(index,true);
-    }
-    for (int index=component.mViewPager.getRealCount() - 1;index>=0;index--) {
-      component.mViewPager.setCurrentItem(index,true);
-    }
-    component.mViewPager.setCurrentItem(3,true);
-    component.mViewPager.setCurrentItem(0,true);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    ComponentTest.destory(component);
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSwitchTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSwitchTest.java
deleted file mode 100644
index 63f8d6a..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXSwitchTest.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import com.taobao.weex.ui.view.WXSwitchView;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Created by sospartan on 28/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXSwitchTest {
-
-  public static WXSwitch create() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXSwitch) new SimpleComponentHolder(WXSwitch.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  WXSwitch component;
-
-  @Before
-  public void setUp() throws Exception {
-    component = create();
-    ComponentTest.create(component, Mockito.mock(WXSwitchView.class));
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    component.destroy();
-  }
-
-  @Test
-  public void testAddEvent() throws Exception {
-    component.addEvent(Constants.Event.CHANGE);
-  }
-
-  @Test
-  public void testSetProperty() throws Exception {
-    component.setProperty(Constants.Name.CHECKED,true);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXTextTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXTextTest.java
deleted file mode 100644
index c311ffb..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXTextTest.java
+++ /dev/null
@@ -1,161 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.SimpleComponentHolder;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertTrue;
-
-/**
- * Created by gulin on 16/2/4.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class)
-public class WXTextTest {
-    private WXText mWXText;
-    private WXDiv mParent;
-    private WXTextDomObject mDomObject;
-    private WXDomObject mParentDomObj;
-
-    @Before
-    public void setUp() throws Exception {
-        WXEnvironment.sApplication = RuntimeEnvironment.application;
-        WXSDKInstance instance = Mockito.mock(WXSDKInstance.class);
-        Mockito.when(instance.getContext()).thenReturn(RuntimeEnvironment.application);
-
-        mParentDomObj = Mockito.spy(new WXDomObject());
-        Mockito.when(mParentDomObj.getPadding()).thenReturn(new Spacing());
-        Mockito.when(mParentDomObj.getBorder()).thenReturn(new Spacing());
-        Mockito.when(mParentDomObj.clone()).thenReturn(mParentDomObj);
-        TestDomObject.setRef(mParentDomObj,WXDomObject.ROOT);
-
-        mDomObject = Mockito.spy(new WXTextDomObject());
-        TestDomObject.setRef(mDomObject,"1");
-        mDomObject.addEvent(Constants.Event.CLICK);
-        Mockito.when(mDomObject.clone()).thenReturn(mDomObject);
-        Mockito.when(mDomObject.getPadding()).thenReturn(new Spacing());
-        Mockito.when(mDomObject.getBorder()).thenReturn(new Spacing());
-        Mockito.when(mDomObject.getMargin()).thenReturn(new Spacing());
-        Mockito.when(mDomObject.getLayoutWidth()).thenReturn(100f);
-        Mockito.when(mDomObject.getLayoutHeight()).thenReturn(100f);
-
-        mParent = new WXDiv(instance, mParentDomObj, null);
-        mParent.createView();
-        mWXText = new WXText(instance, mDomObject, mParent);
-        mWXText.bindHolder(new SimpleComponentHolder(WXText.class));
-        assertNotNull(instance.getContext());
-    }
-
-    @Test
-    public void testSetProperties() throws Exception {
-        mWXText.setProperty(Constants.Name.LINES,null);
-        mWXText.setProperty(Constants.Name.FONT_SIZE,null);
-        mWXText.setProperty(Constants.Name.FONT_WEIGHT,null);
-        mWXText.setProperty(Constants.Name.FONT_STYLE,null);
-        mWXText.setProperty(Constants.Name.COLOR,null);
-        mWXText.setProperty(Constants.Name.TEXT_DECORATION,null);
-        mWXText.setProperty(Constants.Name.FONT_FAMILY,null);
-        mWXText.setProperty(Constants.Name.TEXT_ALIGN,null);
-        mWXText.setProperty(Constants.Name.TEXT_OVERFLOW,null);
-        mWXText.setProperty(Constants.Name.LINE_HEIGHT,null);
-    }
-
-    @Test
-    public void testCreateView(){
-        mWXText.createView();
-        assertNotNull(mWXText.getHostView());
-    }
-
-    @Test
-    public void testSetLayout(){
-        testCreateView();
-        mWXText.setLayout(mDomObject);
-        assertNotNull(mWXText.getHostView().getLayoutParams());
-        assertEquals(100, mWXText.getHostView().getLayoutParams().height);
-        assertEquals(100, mWXText.getHostView().getLayoutParams().width);
-    }
-
-    @Test
-    public void testSetPadding(){
-        testCreateView();
-        mWXText.setPadding(mDomObject.getPadding(), mDomObject.getBorder());
-        assertEquals(0, mWXText.getHostView().getPaddingLeft());
-        assertEquals(0, mWXText.getHostView().getPaddingTop());
-        assertEquals(0, mWXText.getHostView().getPaddingRight());
-        assertEquals(0, mWXText.getHostView().getPaddingBottom());
-    }
-
-    @Test
-    public void testBind(){
-        testCreateView();
-//        mWXText.bind(null);
-        mWXText.applyLayoutAndEvent(mWXText);
-        mWXText.bindData(mWXText);
-
-        assertNotNull(mWXText.getHostView().getLayoutParams());
-        assertEquals(100, mWXText.getHostView().getLayoutParams().height);
-        assertEquals(100, mWXText.getHostView().getLayoutParams().width);
-
-        assertEquals(0, mWXText.getHostView().getPaddingLeft());
-        assertEquals(0, mWXText.getHostView().getPaddingTop());
-        assertEquals(0, mWXText.getHostView().getPaddingRight());
-        assertEquals(0, mWXText.getHostView().getPaddingBottom());
-    }
-
-    @Test
-    public void testAddEvent(){
-        testBind();
-        mWXText.addEvent(Constants.Event.CLICK);
-        assertTrue(mWXText.getHostView().isEnabled());
-        mWXText.getHostView().performClick();
-    }
-
-    @Test
-    public void testUpdateProperties(){
-        testBind();
-        Map<String, Object> prop = new HashMap<>();
-        prop.put(Constants.Name.DISABLED, "false");
-        prop.put(Constants.Name.OPACITY, 0.8f);
-        mWXText.updateProperties(prop);
-        assertTrue(mWXText.getHostView().isEnabled());
-        assertEquals(0.8f, mWXText.getHostView().getAlpha(), 0.001f);
-
-        prop.put(Constants.Name.DISABLED, "true");
-        mWXText.updateProperties(prop);
-        assertFalse(mWXText.getHostView().isEnabled());
-    }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXVideoTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXVideoTest.java
deleted file mode 100644
index d01caa5..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXVideoTest.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-
-/**
- * Created by sospartan on 8/10/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXVideoTest {
-
-  WXVideo component;
-
-  static final String[] PROPS = {
-      Constants.Name.PLAY_STATUS,
-      Constants.Name.AUTO_PLAY,
-      "unknown",
-      Constants.Name.SRC,
-  };
-
-  static final Object[][] VALUES = {
-      {"", Constants.Value.PLAY, Constants.Value.PAUSE,Constants.Value.STOP,null},
-      {"","true","false",true,false,null},
-      {null,"","test"},
-      {"","http://taobao.com","0",100,null},
-  };
-
-  public static WXVideo create() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXVideo) new SimpleComponentHolder(WXVideo.class)
-        .createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  @Before
-  public void setUp() throws Exception {
-    component = create();
-    ComponentTest.create(component);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    ComponentTest.destory(component);
-  }
-
-  @Test
-  public void testSetProperty() throws Exception {
-    component.mPrepared = true;
-    ComponentTest.setProperty(component,PROPS,VALUES);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXWebTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/WXWebTest.java
deleted file mode 100644
index 53d1773..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/WXWebTest.java
+++ /dev/null
@@ -1,174 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component;
-
-import android.view.View;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.common.Constants;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import com.taobao.weex.ui.view.IWebView;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by sospartan on 28/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXWebTest {
-
-  public static WXWeb create() throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXWeb) new SimpleComponentHolder(WXWeb.class).createInstance(WXSDKInstanceTest.createInstance(), new TestDomObject(), WXDivTest.create());
-  }
-
-  WXWeb component;
-  ProxyWebView mWebView;
-
-  static class ProxyWebView implements IWebView {
-    IWebView mIWebView;
-    OnPageListener mOnPageListener;
-    OnErrorListener mOnErrorListener;
-    OnMessageListener mOnMessageListener;
-
-    ProxyWebView(IWebView proxy){
-      mIWebView = proxy;
-    }
-
-    @Override
-    public View getView() {
-      return mIWebView.getView();
-    }
-
-    @Override
-    public void destroy() {
-      mIWebView.destroy();
-    }
-
-    @Override
-    public void loadUrl(String url) {
-      mIWebView.loadUrl(url);
-    }
-
-    @Override
-    public void loadDataWithBaseURL(String source) {
-      mIWebView.loadDataWithBaseURL(source);
-    }
-
-    @Override
-    public void reload() {
-      mIWebView.reload();
-    }
-
-    @Override
-    public void goBack() {
-      mIWebView.goBack();
-    }
-
-    @Override
-    public void goForward() {
-      mIWebView.goForward();
-    }
-
-    @Override
-    public void postMessage(Object msg) {}
-
-    @Override
-    public void setShowLoading(boolean shown) {
-      mIWebView.setShowLoading(shown);
-    }
-
-    @Override
-    public void setOnErrorListener(OnErrorListener listener) {
-      mIWebView.setOnErrorListener(listener);
-      mOnErrorListener = listener;
-    }
-
-    @Override
-    public void setOnPageListener(OnPageListener listener) {
-      mIWebView.setOnPageListener(listener);
-      mOnPageListener = listener;
-    }
-
-    @Override
-    public void setOnMessageListener(OnMessageListener listener) {
-      mIWebView.setOnMessageListener(listener);
-      mOnMessageListener = listener;
-    }
-  }
-
-  @Before
-  public void setUp() throws Exception {
-    component = create();
-    mWebView = new ProxyWebView(component.mWebView);
-    component.mWebView = mWebView;
-    ComponentTest.create(component);
-
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    component.destroy();
-  }
-
-  @Test
-  public void testSetProperty() throws Exception {
-    component.setProperty(Constants.Name.SHOW_LOADING,true);
-    component.setProperty(Constants.Name.SRC,"http://taobao.com");
-    component.setProperty(Constants.Name.SOURCE, "<p><span>hello weex</span></p>");
-  }
-
-  @Test
-  public void testSetAction() throws Exception {
-    Map<String, Object> msg = new HashMap<>();
-    msg.put("test1", 1);
-    msg.put("test2", "2");
-    component.setAction(WXWeb.GO_BACK, null);
-    component.setAction(WXWeb.GO_FORWARD, null);
-    component.setAction(WXWeb.RELOAD, null);
-    component.setAction(WXWeb.POST_MESSAGE, msg);
-  }
-
-  @Test
-  public void testListener() throws Exception {
-    Map<String, Object> msg = new HashMap<>();
-    msg.put("test1", 1);
-    msg.put("test2", "2");
-    component.addEvent(Constants.Event.RECEIVEDTITLE);
-    component.addEvent(Constants.Event.PAGESTART);
-    component.addEvent(Constants.Event.PAGEFINISH);
-    component.addEvent(Constants.Event.ERROR);
-    component.addEvent(Constants.Event.ONMESSAGE);
-    mWebView.mOnPageListener.onPageFinish("http://taobao.com",true,true);
-    mWebView.mOnPageListener.onReceivedTitle("test");
-    mWebView.mOnPageListener.onPageStart("http://taobao.com");
-    mWebView.mOnErrorListener.onError("test","error occurred");
-    mWebView.mOnMessageListener.onMessage(msg);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/helper/WXTimeInputHelperTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/helper/WXTimeInputHelperTest.java
deleted file mode 100644
index f9e9ee2..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/helper/WXTimeInputHelperTest.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.helper;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.appfram.pickers.DatePickerImpl;
-
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.Method;
-
-/**
- * Created by moxun on 16/10/24.
- */
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({"org.mockito.*", "org.robolectric.*", "android.*", "org.json.*"})
-@PrepareForTest()
-public class WXTimeInputHelperTest {
-    @Rule
-    public PowerMockRule rule = new PowerMockRule();
-
-    @Test
-    public void testParseDate() throws Exception{
-        Method parseDate = DatePickerImpl.class.getDeclaredMethod("parseDate", String.class);
-        parseDate.setAccessible(true);
-        parseDate.invoke(null, "");
-        parseDate.invoke(null, "test");
-        parseDate.invoke(null, "2016-12-11");
-        parseDate.invoke(null, "2016-1-1");
-        parseDate.invoke(null, "9999-99-99");
-    }
-
-    @Test
-    public void testParseTime() throws Exception{
-        Method parseTime = DatePickerImpl.class.getDeclaredMethod("parseTime", String.class);
-        parseTime.setAccessible(true);
-        parseTime.invoke(null, "");
-        parseTime.invoke(null, "test");
-        parseTime.invoke(null, "11:11");
-        parseTime.invoke(null, "1:1");
-        parseTime.invoke(null, "25:61");
-    }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/list/DefaultDragHelperTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/list/DefaultDragHelperTest.java
deleted file mode 100644
index 474bdcf..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/list/DefaultDragHelperTest.java
+++ /dev/null
@@ -1,129 +0,0 @@
-/*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import com.taobao.weex.ui.component.ComponentTest;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXDiv;
-import com.taobao.weex.ui.component.WXDivTest;
-import com.taobao.weex.ui.component.WXVContainer;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.ArrayList;
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
-import static org.mockito.Matchers.anyMap;
-import static org.mockito.Matchers.eq;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.verify;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class DefaultDragHelperTest {
-
-    WXListComponent listComponent;
-
-    WXCell fakeCell;
-
-    private DragHelper mFakeDragHelper;
-
-    private EventTrigger mockedEventTrigger;
-
-    private WXComponent c1;
-    private WXComponent c2;
-    private WXComponent c3;
-
-    private List<WXComponent> mFakeDataSource;
-
-    public static WXListComponent create(WXVContainer parent) throws IllegalAccessException, InstantiationException, InvocationTargetException {
-        return create(parent,new WXListDomObject());
-    }
-
-    public static WXListComponent create(WXVContainer parent, WXDomObject dom) throws IllegalAccessException, InstantiationException, InvocationTargetException {
-        return (WXListComponent) new SimpleComponentHolder(WXListComponent.class).createInstance(WXSDKInstanceTest.createInstance(), dom, parent);
-    }
-
-    @Before
-    public void setUp() throws Exception {
-        WXDiv div = WXDivTest.create();
-        ComponentTest.create(div);
-        listComponent = create(div);
-        ComponentTest.create(listComponent);
-
-        fakeCell = new WXCell(WXSDKInstanceTest.createInstance(),new TestDomObject(),null,false);
-
-        c1 = new WXCell(WXSDKInstanceTest.createInstance(),new TestDomObject(),null,false);
-        c2 = new WXCell(WXSDKInstanceTest.createInstance(),new TestDomObject(),null,false);
-        c3 = new WXCell(WXSDKInstanceTest.createInstance(),new TestDomObject(),null,false);
-
-        mFakeDataSource = new ArrayList<>();
-        mFakeDataSource.add(c1);
-        mFakeDataSource.add(c2);
-        mFakeDataSource.add(c3);
-
-        mockedEventTrigger = mock(EventTrigger.class);
-
-        mFakeDragHelper = new DefaultDragHelper(mFakeDataSource,listComponent.getHostView().getInnerView(), mockedEventTrigger);
-    }
-
-    @After
-    public void tearDown() throws Exception {
-        listComponent.destroy();
-    }
-
-    @Test
-    public void onDragStart() throws Exception {
-        WXComponent c = new WXCell(WXSDKInstanceTest.createInstance(),new TestDomObject(),null,false);
-        mFakeDragHelper.onDragStart(c,3);
-        verify(mockedEventTrigger).triggerEvent(eq("dragstart"),anyMap());
-    }
-
-    @Test
-    public void onDragEnd() throws Exception {
-        WXComponent c = new WXCell(WXSDKInstanceTest.createInstance(),new TestDomObject(),null,false);
-        mFakeDragHelper.onDragEnd(c,1,2);
-        verify(mockedEventTrigger).triggerEvent(eq("dragend"),anyMap());
-    }
-
-    @Test
-    public void onDragging() throws Exception {
-        assertEquals(mFakeDataSource.get(0),c1);
-        assertEquals(mFakeDataSource.get(1),c2);
-
-        mFakeDragHelper.onDragging(0,1);
-
-        assertEquals(mFakeDataSource.get(0),c2);
-        assertEquals(mFakeDataSource.get(1),c1);
-    }
-
-
-}
\ No newline at end of file
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/component/list/WXListComponentTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/component/list/WXListComponentTest.java
deleted file mode 100644
index feb2b05..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/component/list/WXListComponentTest.java
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.component.list;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.ui.SimpleComponentHolder;
-import com.taobao.weex.ui.component.ComponentTest;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXDiv;
-import com.taobao.weex.ui.component.WXDivTest;
-import com.taobao.weex.ui.component.WXHeaderTest;
-import com.taobao.weex.ui.component.WXVContainer;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.lang.reflect.InvocationTargetException;
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by sospartan on 8/29/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXListComponentTest {
-
-  WXListComponent component;
-
-  public static WXListComponent create(WXVContainer parent) throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return create(parent,new WXListDomObject());
-  }
-
-  public static WXListComponent create(WXVContainer parent, WXDomObject dom) throws IllegalAccessException, InstantiationException, InvocationTargetException {
-    return (WXListComponent) new SimpleComponentHolder(WXListComponent.class).createInstance(WXSDKInstanceTest.createInstance(), dom, parent);
-  }
-
-  @Before
-  public void setUp() throws Exception {
-    WXDiv div = WXDivTest.create();
-    ComponentTest.create(div);
-    component = create(div);
-    ComponentTest.create(component);
-  }
-
-  @Test
-  public void testAddChild() throws Exception {
-    WXComponent child = WXDivTest.create(component);
-    ComponentTest.create(child);
-    component.addChild(child);
-
-    child = WXHeaderTest.create(component);
-    ComponentTest.create(child);
-    component.addChild(child);
-
-  }
-
-  @Test
-  public void testScrollTo() throws Exception {
-    WXComponent child = WXDivTest.create(component);
-    ComponentTest.create(child);
-    component.addChild(child);
-
-    child = WXHeaderTest.create(component);
-    ComponentTest.create(child);
-    component.addChild(child);
-
-    Map<String, Object> options = new HashMap<>(2);
-    options.put("offset", 10);
-    options.put("animated", false);
-    component.scrollTo(child,options);
-  }
-
-  @Test
-  public void testAppear() throws Exception {
-    WXComponent child = WXDivTest.create(component);
-    ComponentTest.create(child);
-    component.addChild(child);
-
-    component.bindAppearEvent(child);
-
-    component.notifyAppearStateChange(0,0,0,10);
-  }
-
-  @Test
-  public void testParseTransforms() throws Exception {
-    WXDiv div = WXDivTest.create();
-    ComponentTest.create(div);
-
-    WXDomObject dom = new WXListDomObject();
-    dom.getAttrs().put(WXListComponent.TRANSFORM,"scale(0.9,0.8);translate(10,20);opacity(0.5);rotate(100)");
-    component = create(div,dom);
-    ComponentTest.create(component);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    component.destroy();
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/module/WXMetaModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/module/WXMetaModuleTest.java
deleted file mode 100644
index d58a0dc..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/module/WXMetaModuleTest.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.bridge.WXBridgeManager;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static junit.framework.Assert.assertTrue;
-
-/**
- * Created by zhengshihan on 16/12/21.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-@PrepareForTest(WXBridgeManager.class)
-public class WXMetaModuleTest {
-
-    WXMetaModule mMeta;
-    @Before
-    public void setUp() throws Exception {
-        mMeta = new WXMetaModule();
-        mMeta.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-
-    }
-
-    @Test
-    public void setViewport() throws Exception {
-        JSONObject jsonObject  = new JSONObject();
-        jsonObject.put(WXMetaModule.WIDTH,640);
-        mMeta.setViewport(jsonObject.toString());
-        assertTrue(mMeta.mWXSDKInstance.getInstanceViewPortWidth() == 640);
-
-        jsonObject.put(WXMetaModule.WIDTH,320.5);
-        mMeta.setViewport(jsonObject.toString());
-        assertTrue(mMeta.mWXSDKInstance.getInstanceViewPortWidth() == 320);
-
-        jsonObject.put(WXMetaModule.WIDTH,"-200");
-        mMeta.setViewport(jsonObject.toString());
-        assertTrue(mMeta.mWXSDKInstance.getInstanceViewPortWidth() == 320);
-
-        jsonObject.put(WXMetaModule.WIDTH,"error");
-        mMeta.setViewport(jsonObject.toString());
-        assertTrue(mMeta.mWXSDKInstance.getInstanceViewPortWidth() == 320);
-
-
-        mMeta.setViewport("ads");
-        assertTrue(mMeta.mWXSDKInstance.getInstanceViewPortWidth() == 320);
-    }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/module/WXModalUIModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/module/WXModalUIModuleTest.java
deleted file mode 100644
index 17d3fba..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/module/WXModalUIModuleTest.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.bridge.JSCallback;
-
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 7/28/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*","org.json.*" })
-@PrepareForTest()
-public class WXModalUIModuleTest {
-
-  @Rule
-  public PowerMockRule rule = new PowerMockRule();
-
-  WXModalUIModule module;
-
-  @Before
-  public void setUp() throws Exception {
-    module = new WXModalUIModule();
-    module.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-
-  }
-
-  @Test
-  public void testToast() throws Exception {
-    module.toast("{}");
-  }
-
-  @Test
-  public void testAlert() throws Exception {
-    JSCallback callback = Mockito.mock(JSCallback.class);
-    module.alert("{}",callback);
-
-  }
-
-  @Test
-  public void testConfirm() throws Exception {
-    JSCallback callback = Mockito.mock(JSCallback.class);
-    module.confirm("{}",callback);
-  }
-
-  @Test
-  public void testPrompt() throws Exception {
-    JSCallback callback = Mockito.mock(JSCallback.class);
-    module.prompt("{}",callback);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/module/WXTimerModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/module/WXTimerModuleTest.java
deleted file mode 100644
index 7fe508c..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/module/WXTimerModuleTest.java
+++ /dev/null
@@ -1,197 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import static org.hamcrest.CoreMatchers.is;
-import static org.junit.Assert.assertThat;
-import static org.mockito.Matchers.any;
-import static org.mockito.Mockito.never;
-import static org.mockito.Mockito.times;
-import static org.mockito.Mockito.when;
-
-import android.os.Handler;
-import android.os.Message;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.InitConfig;
-import com.taobao.weex.WXSDKEngine;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.bridge.WXBridgeManager;
-import com.taobao.weex.bridge.WXBridgeManagerTest;
-import com.taobao.weex.common.WXThread;
-import java.util.concurrent.TimeUnit;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.Shadows;
-import org.robolectric.annotation.Config;
-import org.robolectric.shadows.ShadowLooper;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class)
-@PowerMockIgnore({"org.mockito.*", "org.robolectric.*", "android.*"})
-@PrepareForTest(WXBridgeManager.class)
-public class WXTimerModuleTest {
-
-  public final static int VALID_FUNC_ID = 20;
-  public final static int NO_CACHING_FUNC_ID = 565654;
-  public final static int INVALID_FUNC_ID = 0;
-  public final static int DELAY = 50;
-  public final static int IMMEDIATELY = 0;
-  public final static int INVALID_DELAY = -50;
-
-  @Rule
-  public PowerMockRule rule = new PowerMockRule();
-  WXTimerModule module;
-  ShadowLooper mLooper;
-
-  @Before
-  public void setup() throws Exception {
-    WXSDKEngine.initialize(RuntimeEnvironment.application, new InitConfig.Builder().build());
-    WXBridgeManager bridge = Mockito.mock(WXBridgeManager.class);
-    when(bridge.getJSLooper()).thenReturn(new WXThread("js").getLooper());
-    WXBridgeManagerTest.setBridgeManager(bridge);
-
-    module = Mockito.spy(new WXTimerModule());
-    module.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-    Handler handler = new Handler(WXBridgeManager.getInstance().getJSLooper(), module);
-    mLooper = Shadows.shadowOf(handler.getLooper());
-    module.setHandler(handler);
-  }
-
-  @Test
-  public void testSetTimeoutDelay() throws Exception {
-    module.setTimeout(VALID_FUNC_ID, DELAY);
-    mLooper.idle(DELAY);
-    Mockito.verify(module, times(1)).handleMessage(any(Message.class));
-  }
-
-  @Test
-  public void testSetTimeoutImmediately() throws Exception {
-    module.setTimeout(VALID_FUNC_ID, IMMEDIATELY);
-    mLooper.idle(IMMEDIATELY);
-    Mockito.verify(module, times(1)).handleMessage(any(Message.class));
-  }
-
-  @SuppressWarnings("Range")
-  @Test
-  public void testSetTimeoutError1() throws Exception {
-    module.setTimeout(INVALID_FUNC_ID, DELAY);
-    mLooper.idle(DELAY);
-    Mockito.verify(module, never()).handleMessage(any(Message.class));
-  }
-
-  @SuppressWarnings("Range")
-  @Test
-  public void testSetTimeoutError2() throws Exception {
-    module.setTimeout(VALID_FUNC_ID, INVALID_DELAY);
-    mLooper.runToEndOfTasks();
-    Mockito.verify(module, never()).handleMessage(any(Message.class));
-  }
-
-  @SuppressWarnings("Range")
-  @Test
-  public void testSetIntervalError1() throws Exception {
-    module.setInterval(INVALID_FUNC_ID, DELAY);
-    mLooper.idle(DELAY);
-    Mockito.verify(module, never()).handleMessage(any(Message.class));
-  }
-
-  @SuppressWarnings("Range")
-  @Test
-  public void testSetIntervalError2() throws Exception {
-    module.setInterval(VALID_FUNC_ID, INVALID_DELAY);
-    mLooper.runToEndOfTasks();
-    Mockito.verify(module, never()).handleMessage(any(Message.class));
-  }
-
-  @Test
-  public void testSetIntervalImmediately() throws Exception {
-    long start, end, duration;
-    module.setInterval(VALID_FUNC_ID, DELAY);
-
-    start = mLooper.getScheduler().getCurrentTime();
-    mLooper.runOneTask();
-    end = mLooper.getScheduler().getCurrentTime();
-    duration = end - start;
-
-    assertThat(duration, is((long) DELAY));
-
-    mLooper.runOneTask();
-    mLooper.runOneTask();
-    mLooper.runOneTask();
-    mLooper.runOneTask();
-    Mockito.verify(module, times(5)).handleMessage(any(Message.class));
-  }
-
-  @Test
-  public void testSetIntervalDelay() {
-    long start, end, duration;
-    module.setInterval(VALID_FUNC_ID, DELAY);
-
-    start = mLooper.getScheduler().getCurrentTime();
-    mLooper.runOneTask();
-    end = mLooper.getScheduler().getCurrentTime();
-    duration = end - start;
-
-    assertThat(duration, is((long) DELAY));
-
-    mLooper.runOneTask();
-    mLooper.runOneTask();
-    Mockito.verify(module, times(3)).handleMessage(any(Message.class));
-  }
-
-  @Test
-  public void testClearTimeout() throws Exception {
-    module.setTimeout(VALID_FUNC_ID, DELAY);
-    module.clearTimeout(VALID_FUNC_ID);
-    mLooper.idle(DELAY, TimeUnit.MILLISECONDS);
-    Mockito.verify(module, never()).handleMessage(any(Message.class));
-  }
-
-  @Test
-  public void testClearInterval() throws Exception {
-    module.setInterval(VALID_FUNC_ID, DELAY);
-    module.clearInterval(VALID_FUNC_ID);
-    mLooper.idle(DELAY, TimeUnit.MILLISECONDS);
-    Mockito.verify(module, never()).handleMessage(any(Message.class));
-  }
-
-  @Test
-  public void setClearTimeout2(){
-    module.setTimeout(NO_CACHING_FUNC_ID, DELAY);
-    module.clearTimeout(NO_CACHING_FUNC_ID);
-    mLooper.idle(DELAY, TimeUnit.MILLISECONDS);
-    Mockito.verify(module, never()).handleMessage(any(Message.class));
-  }
-
-  @Test
-  public void setClearInterval2(){
-    module.setInterval(NO_CACHING_FUNC_ID, DELAY);
-    module.clearInterval(NO_CACHING_FUNC_ID);
-    mLooper.idle(DELAY, TimeUnit.MILLISECONDS);
-    Mockito.verify(module, never()).handleMessage(any(Message.class));
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/module/WXWebViewModuleTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/module/WXWebViewModuleTest.java
deleted file mode 100644
index acb8e86..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/module/WXWebViewModuleTest.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.module;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.WXSDKInstanceTest;
-import com.taobao.weex.bridge.WXBridgeManager;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 7/28/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-@PrepareForTest(WXBridgeManager.class)
-public class WXWebViewModuleTest {
-  WXWebViewModule module;
-
-  @Before
-  public void setUp() throws Exception {
-    module = new WXWebViewModule();
-    module.mWXSDKInstance = WXSDKInstanceTest.createInstance();
-  }
-
-  @Test
-  public void testGoBack() throws Exception {
-    module.goBack("");
-  }
-
-  @Test
-  public void testGoForward() throws Exception {
-    module.goForward("");
-  }
-
-  @Test
-  public void testReload() throws Exception {
-    module.reload("");
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/view/WXCirclePageAdapterTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/view/WXCirclePageAdapterTest.java
deleted file mode 100644
index 90b96f7..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/view/WXCirclePageAdapterTest.java
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.app.Activity;
-import android.support.v4.view.ViewPager;
-import android.view.View;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.TestActivity;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.Robolectric;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 9/7/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXCirclePageAdapterTest {
-
-  WXCirclePageAdapter adapter;
-  View child;
-
-  @Before
-  public void setUp() throws Exception {
-    adapter = new WXCirclePageAdapter();
-  }
-
-  @After
-  public void tearDown() throws Exception {
-  }
-
-  @Test
-  public void testAddPageView() throws Exception {
-    Activity activity = Robolectric.setupActivity(TestActivity.class);
-    child = new View(activity);
-    adapter.addPageView(child);
-    child = new View(activity);
-    adapter.addPageView(child);
-    child = new View(activity);
-    adapter.addPageView(child);
-
-    assertEquals(adapter.getRealCount(),3);
-  }
-
-  @Test
-  public void testRemovePageView() throws Exception {
-    testAddPageView();
-    adapter.removePageView(child);
-    assertEquals(adapter.getRealCount(),2);
-  }
-
-
-  @Test
-  public void testInstantiateItem() throws Exception {
-    testAddPageView();
-    ViewPager viewPager = new ViewPager(child.getContext());
-    viewPager.setAdapter(adapter);
-    Object obj = adapter.instantiateItem(viewPager,adapter.getRealCount());
-    assertEquals(child,obj);
-  }
-
-  @Test
-  public void testReplacePageView() throws Exception {
-    testAddPageView();
-    View relace = new View(child.getContext());
-
-    adapter.replacePageView(child,relace);
-
-    assertEquals(adapter.getRealCount(),3);
-    
-  }
-
-  @Test
-  public void testGetRealPosition() throws Exception {
-    testAddPageView();
-    assertEquals(adapter.getRealPosition(0), adapter.getRealCount() - 1);
-    assertEquals(adapter.getRealPosition(1), 0);
-    assertEquals(adapter.getRealPosition(adapter.getRealCount() + 1), 0);
-    assertEquals(adapter.getRealPosition(100), -1);
-    assertEquals(adapter.getRealPosition(-1), -1);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/view/WXScrollViewTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/view/WXScrollViewTest.java
deleted file mode 100644
index 3873aa1..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/view/WXScrollViewTest.java
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import android.app.Activity;
-import android.view.MotionEvent;
-import android.view.View;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.TestActivity;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.Robolectric;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 9/7/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXScrollViewTest {
-
-  WXScrollView view;
-
-  static final int[] EVENTS = {MotionEvent.ACTION_DOWN,MotionEvent.ACTION_MOVE,MotionEvent.ACTION_UP};
-
-  @Before
-  public void setUp() throws Exception {
-    Activity activity = Robolectric.setupActivity(TestActivity.class);
-    view = new WXScrollView(activity);
-    View child = new View(activity);
-    view.addView(child);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    view.destroy();
-  }
-
-  @Test
-  public void testDispatchTouchEvent() throws Exception {
-    for(int action:EVENTS) {
-      MotionEvent event = MotionEvent.obtain(100, 100, action,
-          10, 10, 0);
-      view.dispatchTouchEvent(event);
-      event.recycle();
-    }
-  }
-
-  @Test
-  public void testOnTouchEvent() throws Exception {
-    for(int action:EVENTS) {
-      MotionEvent event = MotionEvent.obtain(100, 100, action,
-          10, 10, 0);
-      view.onTouchEvent(event);
-      event.recycle();
-    }
-  }
-
-  @Test
-  public void testOnScrollChanged() throws Exception {
-    view.onScrollChanged(0,10,0,20);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/view/WXWebViewTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/view/WXWebViewTest.java
deleted file mode 100644
index 7b8b5cd..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/view/WXWebViewTest.java
+++ /dev/null
@@ -1,128 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view;
-
-import static org.junit.Assert.assertNotNull;
-
-import android.app.Activity;
-import android.view.ViewGroup;
-import android.webkit.WebChromeClient;
-import android.webkit.WebView;
-import android.webkit.WebViewClient;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.TestActivity;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.Robolectric;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.Shadows;
-import org.robolectric.annotation.Config;
-import org.robolectric.shadows.ShadowWebView;
-
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- * Created by sospartan on 9/7/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXWebViewTest {
-
-  IWebView view;
-  WebView webView;
-  ShadowWebView shadow;
-
-  @Before
-  public void setUp() throws Exception {
-    Activity activity = Robolectric.setupActivity(TestActivity.class);
-    view = new WXWebView(activity, null);
-    webView = (WebView)((ViewGroup)view.getView()).getChildAt(0);//first child
-    shadow = Shadows.shadowOf(webView);
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    view.destroy();
-  }
-
-  @Test
-  public void testDestory() throws Exception {
-
-  }
-
-  @Test
-  public void testGetView() throws Exception {
-    assertNotNull(view);
-  }
-
-  @Test
-  public void testLoadUrl() throws Exception {
-    String url = "http://www.taobao.com";
-    view.loadUrl(url);
-    WebViewClient client = shadow.getWebViewClient();
-    client.onPageStarted(webView,url,null);
-    client.onPageFinished(webView,url);
-
-    WebChromeClient chromeClient = shadow.getWebChromeClient();
-    chromeClient.onProgressChanged(webView,10);
-    chromeClient.onProgressChanged(webView,100);
-    chromeClient.onReceivedTitle(webView,"test");
-
-  }
-
-  @Test
-  public void testLoadDataWithBaseURL() throws Exception {
-    String source = "<p><span>hello weex</span></p>";
-    view.loadDataWithBaseURL(source);
-  }
-
-
-  @Test
-  public void testReload() throws Exception {
-    view.reload();
-    testLoadUrl();
-    view.reload();
-  }
-
-  @Test
-  public void testGoBack() throws Exception {
-    testLoadUrl();
-    view.loadUrl("http://www.w3c.org");
-    view.goBack();
-  }
-
-  @Test
-  public void testGoForward() throws Exception {
-    testGoBack();
-    view.goForward();
-  }
-
-  @Test
-  public void testPostMessage() throws Exception {
-    Map<String, Object> msg = new HashMap<>();
-    msg.put("test1", 1);
-    msg.put("test2", "2");
-    view.postMessage(msg);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/view/border/BorderCornerTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/view/border/BorderCornerTest.java
deleted file mode 100644
index 827e632..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/view/border/BorderCornerTest.java
+++ /dev/null
@@ -1,320 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.Point;
-import android.graphics.PointF;
-import android.graphics.RectF;
-import android.support.annotation.Nullable;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Set;
-
-import static org.hamcrest.CoreMatchers.is;
-import static org.junit.Assert.*;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(manifest = Config.NONE)
-public class BorderCornerTest {
-
-  private final static String TOP_LEFT = "TopLeft";
-  private final static String TOP_RIGHT = "TopRight";
-  private final static String BOTTOM_RIGHT = "BottomRight";
-  private final static String BOTTOM_LEFT = "BottomLeft";
-
-  private List<BorderCorner> borderCorners = new ArrayList<>();
-  private RectF borderBox = new RectF(0, 0, 400, 400);
-  private List<Float> radiusList = Arrays.asList(-10f, 0f, 10f, 25f, 50f, 75f, 150f);
-  private List<Float> preWidthList = Arrays.asList(-10f, 0f, 10f, 50f, 100f);
-  private List<Float> postWidthList = Arrays.asList(-10f, 0f, 10f, 50f, 100f);
-  private List<String> cornerList = Arrays.asList(TOP_LEFT, TOP_RIGHT, BOTTOM_RIGHT, BOTTOM_LEFT);
-
-  private
-  @Nullable
-  BorderCorner createBorderCorner(String corner, float
-      radius, float preWidth, float postWidth, RectF borderBox) {
-    switch (corner) {
-      case TOP_LEFT:
-        return new TopLeftCorner(radius, preWidth, postWidth, borderBox);
-      case TOP_RIGHT:
-        return new TopRightCorner(radius, preWidth, postWidth, borderBox);
-      case BOTTOM_RIGHT:
-        return new BottomRightCorner(radius, preWidth, postWidth, borderBox);
-      case BOTTOM_LEFT:
-        return new BottomLeftCorner(radius, preWidth, postWidth, borderBox);
-      default:
-        return null;
-    }
-  }
-
-  @Before
-  public void setUp() throws Exception {
-
-  }
-
-  @After
-  public void tearDown() throws Exception {
-    borderCorners.clear();
-  }
-
-  @Test
-  public void testHasOuterCorner() throws Exception {
-    for (float preWidth : preWidthList) {
-      for (float postWidth : postWidthList) {
-        for (String corner : cornerList) {
-          assertThat(createBorderCorner(corner, 0f, preWidth, postWidth, borderBox).hasOuterCorner(), is(false));
-          assertThat(createBorderCorner(corner, 50f, preWidth, postWidth, borderBox)
-                         .hasOuterCorner(), is(true));
-          assertThat(createBorderCorner(corner, -10f, preWidth, postWidth, borderBox)
-                         .hasOuterCorner(), is(false));
-        }
-      }
-    }
-  }
-
-  @Test
-  public void testHasInnerCorner() throws Exception {
-    for (String corner : cornerList) {
-      for (float preWidth : preWidthList) {
-        for (float postWidth : postWidthList) {
-          assertThat(createBorderCorner(corner, -10, preWidth, postWidth, borderBox).hasInnerCorner()
-              , is(false));
-          assertThat(createBorderCorner(corner, 0, preWidth, postWidth, borderBox)
-                         .hasInnerCorner()
-              , is(false));
-        }
-      }
-      assertThat(createBorderCorner(corner, 25, -10, -10, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, -10, 0, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, -10, 10, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, -10, 50, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, 0, -10, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, 0, 0, borderBox).hasInnerCorner()
-          , is(true));
-      assertThat(createBorderCorner(corner, 25, 0, 10, borderBox).hasInnerCorner()
-          , is(true));
-      assertThat(createBorderCorner(corner, 25, 0, 50, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, 10, -10, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, 10, 0, borderBox).hasInnerCorner()
-          , is(true));
-      assertThat(createBorderCorner(corner, 25, 10, 10, borderBox).hasInnerCorner()
-          , is(true));
-      assertThat(createBorderCorner(corner, 25, 10, 50, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, 50, -10, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, 50, 0, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, 50, 10, borderBox).hasInnerCorner()
-          , is(false));
-      assertThat(createBorderCorner(corner, 25, 50, 50, borderBox).hasInnerCorner()
-          , is(false));
-    }
-  }
-
-  @Test
-  public void testGetCornerStart() throws Exception {
-    PointF topLeft = createBorderCorner(TOP_LEFT, 25, 10, 50, borderBox)
-        .getCornerStart();
-    assertThat(topLeft.x, is(5f));
-    assertThat(topLeft.y, is(25f));
-    PointF topRight = createBorderCorner(TOP_RIGHT, 25, 10, 50, borderBox)
-        .getCornerStart();
-    assertThat(topRight.x, is(375f));
-    assertThat(topRight.y, is(5f));
-    PointF bottomRight = createBorderCorner(BOTTOM_RIGHT, 25, 10, 50, borderBox)
-        .getCornerStart();
-    assertThat(bottomRight.x, is(395f));
-    assertThat(bottomRight.y, is(375f));
-    PointF bottomLeft = createBorderCorner(BOTTOM_LEFT, 25, 10, 50, borderBox)
-        .getCornerStart();
-    assertThat(bottomLeft.x, is(25f));
-    assertThat(bottomLeft.y, is(395f));
-  }
-
-  @Test
-  public void testGetCornerEnd() throws Exception {
-    PointF topLeft = createBorderCorner(TOP_LEFT, 0, 10, 50, borderBox)
-        .getCornerEnd();
-    assertThat(topLeft.x, is(5f));
-    assertThat(topLeft.y, is(25f));
-    PointF topRight = createBorderCorner(TOP_RIGHT, 0, 10, 50, borderBox)
-        .getCornerEnd();
-    assertThat(topRight.x, is(375f));
-    assertThat(topRight.y, is(5f));
-    PointF bottomRight = createBorderCorner(BOTTOM_RIGHT, 0, 10, 50, borderBox)
-        .getCornerEnd();
-    assertThat(bottomRight.x, is(395f));
-    assertThat(bottomRight.y, is(375f));
-    PointF bottomLeft = createBorderCorner(BOTTOM_LEFT, 0, 10, 50, borderBox)
-        .getCornerEnd();
-    assertThat(bottomLeft.x, is(25f));
-    assertThat(bottomLeft.y, is(395f));
-  }
-
-  @Test
-  public void testGetRoundCornerStart() throws Exception {
-    PointF topLeft = createBorderCorner(TOP_LEFT, 25, 10, 50, borderBox)
-        .getRoundCornerStart();
-    assertThat(topLeft.x, is(5f));
-    assertThat(topLeft.y, is(25f));
-    PointF topRight = createBorderCorner(TOP_RIGHT, 25, 10, 50, borderBox)
-        .getRoundCornerStart();
-    assertThat(topRight.x, is(375f));
-    assertThat(topRight.y, is(5f));
-    PointF bottomRight = createBorderCorner(BOTTOM_RIGHT, 25, 10, 50, borderBox)
-        .getRoundCornerStart();
-    assertThat(bottomRight.x, is(395f));
-    assertThat(bottomRight.y, is(375f));
-    PointF bottomLeft = createBorderCorner(BOTTOM_LEFT, 25, 10, 50, borderBox)
-        .getRoundCornerStart();
-    assertThat(bottomLeft.x, is(25f));
-    assertThat(bottomLeft.y, is(395f));
-  }
-
-  @Test
-  public void testGetRoundCornerEnd() throws Exception {
-    PointF topLeft = createBorderCorner(TOP_LEFT, 25, 10, 50, borderBox)
-        .getRoundCornerEnd();
-    assertThat(topLeft.x, is(25f));
-    assertThat(topLeft.y, is(25f));
-    PointF topRight = createBorderCorner(TOP_RIGHT, 25, 10, 50, borderBox)
-        .getRoundCornerEnd();
-    assertThat(topRight.x, is(375f));
-    assertThat(topRight.y, is(25f));
-    PointF bottomRight = createBorderCorner(BOTTOM_RIGHT, 25, 10, 50, borderBox)
-        .getRoundCornerEnd();
-    assertThat(bottomRight.x, is(375f));
-    assertThat(bottomRight.y, is(375f));
-    PointF bottomLeft = createBorderCorner(BOTTOM_LEFT, 25, 10, 50, borderBox)
-        .getRoundCornerEnd();
-    assertThat(bottomLeft.x, is(25f));
-    assertThat(bottomLeft.y, is(375f));
-  }
-
-  @Test
-  public void testGetSharpCornerVertex() throws Exception {
-    PointF topLeft = createBorderCorner(TOP_LEFT, 0, 10, 50, borderBox)
-        .getSharpCornerVertex();
-    assertThat(topLeft.x, is(5f));
-    assertThat(topLeft.y, is(25f));
-    PointF topRight = createBorderCorner(TOP_RIGHT, 0, 10, 50, borderBox)
-        .getSharpCornerVertex();
-    assertThat(topRight.x, is(375f));
-    assertThat(topRight.y, is(5f));
-    PointF bottomRight = createBorderCorner(BOTTOM_RIGHT, 0, 10, 50, borderBox)
-        .getSharpCornerVertex();
-    assertThat(bottomRight.x, is(395f));
-    assertThat(bottomRight.y, is(375f));
-    PointF bottomLeft = createBorderCorner(BOTTOM_LEFT, 0, 10, 50, borderBox)
-        .getSharpCornerVertex();
-    assertThat(bottomLeft.x, is(25f));
-    assertThat(bottomLeft.y, is(395f));
-  }
-
-  @Test
-  public void testGetSharpCornerStart() throws Exception {
-    PointF topLeft = createBorderCorner(TOP_LEFT, 0, 10, 50, borderBox)
-        .getSharpCornerStart();
-    assertThat(topLeft.x, is(0f));
-    assertThat(topLeft.y, is(25f));
-    PointF topRight = createBorderCorner(TOP_RIGHT, 0, 10, 50, borderBox)
-        .getSharpCornerStart();
-    assertThat(topRight.x, is(375f));
-    assertThat(topRight.y, is(0f));
-    PointF bottomRight = createBorderCorner(BOTTOM_RIGHT, 0, 10, 50, borderBox)
-        .getSharpCornerStart();
-    assertThat(bottomRight.x, is(400f));
-    assertThat(bottomRight.y, is(375f));
-    PointF bottomLeft = createBorderCorner(BOTTOM_LEFT, 0, 10, 50, borderBox)
-        .getSharpCornerStart();
-    assertThat(bottomLeft.x, is(25f));
-    assertThat(bottomLeft.y, is(400f));
-  }
-
-  @Test
-  public void testGetSharpCornerEnd() throws Exception {
-    PointF topLeft = createBorderCorner(TOP_LEFT, 0, 10, 50, borderBox)
-        .getSharpCornerEnd();
-    assertThat(topLeft.x, is(5f));
-    assertThat(topLeft.y, is(0f));
-    PointF topRight = createBorderCorner(TOP_RIGHT, 0, 10, 50, borderBox)
-        .getSharpCornerEnd();
-    assertThat(topRight.x, is(400f));
-    assertThat(topRight.y, is(5f));
-    PointF bottomRight = createBorderCorner(BOTTOM_RIGHT, 0, 10, 50, borderBox)
-        .getSharpCornerEnd();
-    assertThat(bottomRight.x, is(395f));
-    assertThat(bottomRight.y, is(400f));
-    PointF bottomLeft = createBorderCorner(BOTTOM_LEFT, 0, 10, 50, borderBox)
-        .getSharpCornerEnd();
-    assertThat(bottomLeft.x, is(0f));
-    assertThat(bottomLeft.y, is(395f));
-  }
-
-  @Test
-  public void testGetOvalIfInnerCornerExist() throws Exception {
-    RectF topLeft = createBorderCorner(TOP_LEFT, 100, 10, 50, borderBox)
-        .getOvalIfInnerCornerExist();
-    assertThat(topLeft, is(new RectF(5, 25, 195, 175)));
-    RectF topRight = createBorderCorner(TOP_RIGHT, 100, 10, 50, borderBox)
-        .getOvalIfInnerCornerExist();
-    assertThat(topRight, is(new RectF(225, 5, 375, 195)));
-    RectF bottomRight = createBorderCorner(BOTTOM_RIGHT, 100, 10, 50, borderBox)
-        .getOvalIfInnerCornerExist();
-    assertThat(bottomRight, is(new RectF(205, 225, 395, 375)));
-    RectF bottomLeft = createBorderCorner(BOTTOM_LEFT, 100, 10, 50, borderBox)
-        .getOvalIfInnerCornerExist();
-    assertThat(bottomLeft, is(new RectF(25, 205, 175, 395)));
-  }
-
-  @Test
-  public void testGetOvalIfInnerCornerNotExist() throws Exception {
-    RectF topLeft = createBorderCorner(TOP_LEFT, 50, 10, 50, borderBox).getOvalIfInnerCornerNotExist();
-    assertThat(topLeft, is(new RectF(25, 25, 75, 75)));
-    RectF topRight = createBorderCorner(TOP_RIGHT, 50, 10, 50, borderBox).getOvalIfInnerCornerNotExist();
-    assertThat(topRight, is(new RectF(325, 25, 375, 75)));
-    RectF bottomRight = createBorderCorner(BOTTOM_RIGHT, 50, 10, 50, borderBox).getOvalIfInnerCornerNotExist();
-    assertThat(bottomRight, is(new RectF(325, 325, 375, 375)));
-    RectF bottomLeft = createBorderCorner(BOTTOM_LEFT, 50, 10, 50, borderBox)
-        .getOvalIfInnerCornerNotExist();
-    assertThat(bottomLeft, is(new RectF(25, 325, 75, 375)));
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/view/border/BorderDrawableTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/view/border/BorderDrawableTest.java
deleted file mode 100644
index 49caafa..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/view/border/BorderDrawableTest.java
+++ /dev/null
@@ -1,377 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-package com.taobao.weex.ui.view.border;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.PixelFormat;
-import android.graphics.Rect;
-
-import com.taobao.weex.utils.WXResourceUtils;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.hamcrest.CoreMatchers.is;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertThat;
-
-@RunWith(RobolectricTestRunner.class)
-@Config(manifest = Config.NONE)
-public class BorderDrawableTest {
-
-  @Before
-  public void setUp() throws Exception {
-
-  }
-
-  @Test
-  public void testGetOpacity() throws Exception {
-    BorderDrawable opaque = new BorderDrawable();
-    opaque.setColor(Color.GREEN);
-    assertThat(opaque.getOpacity(), is(PixelFormat.OPAQUE));
-
-    BorderDrawable transparent = new BorderDrawable();
-    transparent.setColor(WXResourceUtils.getColor("#00ff0000"));
-    assertThat(transparent.getOpacity(), is(PixelFormat.TRANSPARENT));
-
-    BorderDrawable half = new BorderDrawable();
-    half.setColor(WXResourceUtils.getColor("#aaff0000"));
-    assertThat(half.getOpacity(), is(PixelFormat.TRANSLUCENT));
-
-    BorderDrawable changeAlpha = new BorderDrawable();
-    changeAlpha.setColor(Color.RED);
-    changeAlpha.setAlpha(15);
-    assertThat(changeAlpha.getOpacity(), is(PixelFormat.TRANSLUCENT));
-  }
-
-  @Test
-  public void testBorderWidth() throws Exception {
-    BorderDrawable none = new BorderDrawable();
-    assertThat(none.getBorderWidth(Spacing.ALL), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(none.getBorderWidth(Spacing.LEFT), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(none.getBorderWidth(Spacing.RIGHT), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(none.getBorderWidth(Spacing.TOP), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(none.getBorderWidth(Spacing.BOTTOM), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-
-    BorderDrawable full = new BorderDrawable();
-    full.setBorderWidth(Spacing.ALL, 12);
-    assertThat(full.getBorderWidth(Spacing.ALL), is(12f));
-    assertThat(full.getBorderWidth(Spacing.LEFT), is(12f));
-    assertThat(full.getBorderWidth(Spacing.RIGHT), is(12f));
-    assertThat(full.getBorderWidth(Spacing.TOP), is(12f));
-    assertThat(full.getBorderWidth(Spacing.BOTTOM), is(12f));
-
-    BorderDrawable noneAndPart = new BorderDrawable();
-    noneAndPart.setBorderWidth(Spacing.LEFT, 5);
-    noneAndPart.setBorderWidth(Spacing.TOP, 12);
-    assertThat(noneAndPart.getBorderWidth(Spacing.LEFT), is(5f));
-    assertThat(noneAndPart.getBorderWidth(Spacing.RIGHT), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(noneAndPart.getBorderWidth(Spacing.TOP), is(12f));
-    assertThat(noneAndPart.getBorderWidth(Spacing.BOTTOM), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-
-    BorderDrawable fullAndPart = new BorderDrawable();
-    fullAndPart.setBorderWidth(Spacing.ALL, 5);
-    fullAndPart.setBorderWidth(Spacing.LEFT, 12);
-    fullAndPart.setBorderWidth(Spacing.TOP, 19);
-    assertThat(fullAndPart.getBorderWidth(Spacing.LEFT), is(12f));
-    assertThat(fullAndPart.getBorderWidth(Spacing.RIGHT), is(5f));
-    assertThat(fullAndPart.getBorderWidth(Spacing.TOP), is(19f));
-    assertThat(fullAndPart.getBorderWidth(Spacing.BOTTOM), is(5f));
-
-    BorderDrawable partAndFull = new BorderDrawable();
-    partAndFull.setBorderWidth(Spacing.LEFT, 12);
-    partAndFull.setBorderWidth(Spacing.ALL, 5);
-    assertThat(partAndFull.getBorderWidth(Spacing.ALL), is(5f));
-    assertThat(partAndFull.getBorderWidth(Spacing.LEFT), is(5f));
-    assertThat(partAndFull.getBorderWidth(Spacing.RIGHT), is(5f));
-    assertThat(partAndFull.getBorderWidth(Spacing.TOP), is(5f));
-    assertThat(partAndFull.getBorderWidth(Spacing.BOTTOM), is(5f));
-  }
-
-  @Test
-  public void testBorderRadius() throws Exception {
-    BorderDrawable none = new BorderDrawable();
-    none.draw(new Canvas());
-    assertThat(none.getBorderRadius(BorderDrawable.BORDER_RADIUS_ALL), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(none.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(none.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(none.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(none.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-
-    BorderDrawable full = new BorderDrawable();
-    full.setBorderRadius(BorderDrawable.BORDER_RADIUS_ALL, 12);
-    full.setBounds(new Rect(0, 0, 400, 400));
-    full.draw(new Canvas());
-    assertThat(full.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is(12f));
-    assertThat(full.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is(12f));
-    assertThat(full.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is(12f));
-    assertThat(full.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS), is(12f));
-
-    BorderDrawable noneAndPart = new BorderDrawable();
-    noneAndPart.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 5);
-    noneAndPart.setBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS, 12);
-    noneAndPart.setBounds(new Rect(0, 0, 400, 400));
-    noneAndPart.draw(new Canvas());
-    assertThat(noneAndPart.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is(5f));
-    assertThat(noneAndPart.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-    assertThat(noneAndPart.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is(12f));
-    assertThat(noneAndPart.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS), is(BorderDrawable.DEFAULT_BORDER_WIDTH));
-
-    BorderDrawable fullAndPart = new BorderDrawable();
-    fullAndPart.setBorderRadius(BorderDrawable.BORDER_RADIUS_ALL, 5);
-    fullAndPart.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 12);
-    fullAndPart.setBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS, 19);
-    fullAndPart.setBounds(new Rect(0, 0, 400, 400));
-    fullAndPart.draw(new Canvas());
-    assertThat(fullAndPart.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is(12f));
-    assertThat(fullAndPart.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is(5f));
-    assertThat(fullAndPart.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is(19f));
-    assertThat(fullAndPart.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS), is(5f));
-
-    BorderDrawable partAndFull = new BorderDrawable();
-    partAndFull.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 12);
-    partAndFull.setBorderRadius(BorderDrawable.BORDER_RADIUS_ALL, 5);
-    partAndFull.setBounds(new Rect(0, 0, 400, 400));
-    partAndFull.draw(new Canvas());
-    assertThat(partAndFull.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is(5f));
-    assertThat(partAndFull.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is(5f));
-    assertThat(partAndFull.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is(5f));
-    assertThat(partAndFull.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS), is(5f));
-
-    BorderDrawable noOverLapping = new BorderDrawable();
-    noOverLapping.setBounds(new Rect(0, 0, 400, 400));
-    noOverLapping.setBorderRadius(BorderDrawable.BORDER_RADIUS_ALL, 0);
-    noOverLapping.draw(new Canvas());
-    assertThat(noOverLapping.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is(0f));
-    assertThat(noOverLapping.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is(0f));
-    assertThat(noOverLapping.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is(0f));
-    assertThat(noOverLapping.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS), is(0f));
-
-    BorderDrawable overlappingOneLine = new BorderDrawable();
-    overlappingOneLine.setBounds(new Rect(0, 0, 400, 400));
-    overlappingOneLine.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 300);
-    overlappingOneLine.setBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS, 200);
-    overlappingOneLine.draw(new Canvas());
-    assertThat(overlappingOneLine.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is(240f));
-    assertThat(overlappingOneLine.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is(160f));
-    assertThat(overlappingOneLine.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS), is
-        (0f));
-    assertThat(overlappingOneLine.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is
-        (0f));
-
-    BorderDrawable overlappingAdjoinLine = new BorderDrawable();
-    overlappingAdjoinLine.setBounds(new Rect(0, 0, 400, 400));
-    overlappingAdjoinLine.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 300);
-    overlappingAdjoinLine.setBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS, 200);
-    overlappingAdjoinLine.setBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS, 300);
-    overlappingAdjoinLine.setBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS, 50);
-    overlappingAdjoinLine.draw(new Canvas());
-    assertThat(overlappingAdjoinLine.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is
-        (240f));
-    assertThat(overlappingAdjoinLine.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is
-        (160f));
-    assertThat(overlappingAdjoinLine.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is
-        (240f));
-    assertThat(overlappingAdjoinLine.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS),
-               is(40f));
-
-    BorderDrawable overlappingNonadjoinLine = new BorderDrawable();
-    overlappingNonadjoinLine.setBounds(new Rect(0, 0, 400, 800));
-    overlappingNonadjoinLine.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 300);
-    overlappingNonadjoinLine.setBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS, 200);
-    overlappingNonadjoinLine.setBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS, 300);
-    overlappingNonadjoinLine.setBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS, 200);
-    overlappingNonadjoinLine.draw(new Canvas());
-    assertThat(overlappingNonadjoinLine.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS), is
-        (240f));
-    assertThat(overlappingNonadjoinLine.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS), is
-        (160f));
-    assertThat(overlappingNonadjoinLine.getBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS), is
-        (240f));
-    assertThat(overlappingNonadjoinLine.getBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS),
-               is(160f));
-
-    BorderDrawable overlappingThreeLines = new BorderDrawable();
-    overlappingThreeLines.setBounds(new Rect(0, 0, 400, 500));
-    overlappingThreeLines.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 300);
-    overlappingThreeLines.setBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS, 200);
-    overlappingThreeLines.setBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS, 600);
-    overlappingThreeLines.setBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS, 100);
-    overlappingThreeLines.draw(new Canvas());
-    assertEquals(300f * 4 / 7,
-                 overlappingThreeLines.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS),
-                 .00001f);
-    assertEquals(200f * 4 / 7, overlappingThreeLines.getBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS),
-                 .00001f);
-    assertEquals(600f * 4 / 7, overlappingThreeLines.getBorderRadius(BorderDrawable
-                                                                         .BORDER_BOTTOM_RIGHT_RADIUS),
-                 .00001f);
-    assertEquals(100f * 4 / 7, overlappingThreeLines.getBorderRadius(BorderDrawable
-                                                                         .BORDER_BOTTOM_LEFT_RADIUS),
-                 .00001f);
-
-    BorderDrawable overlappingFourLines = new BorderDrawable();
-    overlappingFourLines.setBounds(new Rect(0, 0, 400, 500));
-    overlappingFourLines.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 500);
-    overlappingFourLines.setBorderRadius(BorderDrawable.BORDER_TOP_RIGHT_RADIUS, 600);
-    overlappingFourLines.setBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS, 700);
-    overlappingFourLines.setBorderRadius(BorderDrawable.BORDER_BOTTOM_LEFT_RADIUS, 800);
-    overlappingFourLines.draw(new Canvas());
-    assertEquals(500f * 4 / 15,
-                 overlappingFourLines.getBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS),
-                 .0001f);
-    assertEquals(600f * 4 / 15, overlappingFourLines.getBorderRadius(BorderDrawable
-                                                                         .BORDER_TOP_RIGHT_RADIUS),
-                 .0001f);
-    assertEquals(700f * 4 / 15, overlappingFourLines.getBorderRadius(BorderDrawable
-                                                                         .BORDER_BOTTOM_RIGHT_RADIUS),
-                 .0001f);
-    assertEquals(800f * 4 / 15, overlappingFourLines.getBorderRadius(BorderDrawable
-                                                                         .BORDER_BOTTOM_LEFT_RADIUS),
-                 .0001f);
-  }
-
-  @Test
-  public void testBorderColor() throws Exception {
-    BorderDrawable none = new BorderDrawable();
-    assertThat(none.getBorderColor(Spacing.ALL), is(BorderDrawable.DEFAULT_BORDER_COLOR));
-    assertThat(none.getBorderColor(Spacing.LEFT), is(BorderDrawable.DEFAULT_BORDER_COLOR));
-    assertThat(none.getBorderColor(Spacing.RIGHT), is(BorderDrawable.DEFAULT_BORDER_COLOR));
-    assertThat(none.getBorderColor(Spacing.TOP), is(BorderDrawable.DEFAULT_BORDER_COLOR));
-    assertThat(none.getBorderColor(Spacing.BOTTOM), is(BorderDrawable.DEFAULT_BORDER_COLOR));
-
-    BorderDrawable full = new BorderDrawable();
-    full.setBorderColor(Spacing.ALL, Color.RED);
-    assertThat(full.getBorderColor(Spacing.ALL), is(Color.RED));
-    assertThat(full.getBorderColor(Spacing.LEFT), is(Color.RED));
-    assertThat(full.getBorderColor(Spacing.RIGHT), is(Color.RED));
-    assertThat(full.getBorderColor(Spacing.TOP), is(Color.RED));
-    assertThat(full.getBorderColor(Spacing.BOTTOM), is(Color.RED));
-
-    BorderDrawable noneAndPart = new BorderDrawable();
-    noneAndPart.setBorderColor(Spacing.LEFT, Color.BLUE);
-    noneAndPart.setBorderColor(Spacing.TOP, Color.GREEN);
-    assertThat(noneAndPart.getBorderColor(Spacing.LEFT), is(Color.BLUE));
-    assertThat(noneAndPart.getBorderColor(Spacing.RIGHT), is(BorderDrawable.DEFAULT_BORDER_COLOR));
-    assertThat(noneAndPart.getBorderColor(Spacing.TOP), is(Color.GREEN));
-    assertThat(noneAndPart.getBorderColor(Spacing.BOTTOM), is(BorderDrawable.DEFAULT_BORDER_COLOR));
-
-    BorderDrawable fullAndPart = new BorderDrawable();
-    fullAndPart.setBorderColor(Spacing.ALL, Color.BLUE);
-    fullAndPart.setBorderColor(Spacing.LEFT, Color.GREEN);
-    fullAndPart.setBorderColor(Spacing.TOP, Color.RED);
-    assertThat(fullAndPart.getBorderColor(Spacing.LEFT), is(Color.GREEN));
-    assertThat(fullAndPart.getBorderColor(Spacing.RIGHT), is(Color.BLUE));
-    assertThat(fullAndPart.getBorderColor(Spacing.TOP), is(Color.RED));
-    assertThat(fullAndPart.getBorderColor(Spacing.BOTTOM), is(Color.BLUE));
-
-    BorderDrawable partAndFull = new BorderDrawable();
-    partAndFull.setBorderColor(Spacing.LEFT, Color.RED);
-    partAndFull.setBorderColor(Spacing.ALL, Color.BLUE);
-    assertThat(partAndFull.getBorderColor(Spacing.ALL), is(Color.BLUE));
-    assertThat(partAndFull.getBorderColor(Spacing.LEFT), is(Color.BLUE));
-    assertThat(partAndFull.getBorderColor(Spacing.RIGHT), is(Color.BLUE));
-    assertThat(partAndFull.getBorderColor(Spacing.TOP), is(Color.BLUE));
-    assertThat(partAndFull.getBorderColor(Spacing.BOTTOM), is(Color.BLUE));
-
-  }
-
-  @Test
-  public void testBorderStyle() throws Exception {
-    BorderDrawable none = new BorderDrawable();
-    assertThat(none.getBorderStyle(Spacing.ALL), is(BorderStyle.SOLID.ordinal()));
-    assertThat(none.getBorderStyle(Spacing.LEFT), is(BorderStyle.SOLID.ordinal()));
-    assertThat(none.getBorderStyle(Spacing.RIGHT), is(BorderStyle.SOLID.ordinal()));
-    assertThat(none.getBorderStyle(Spacing.TOP), is(BorderStyle.SOLID.ordinal()));
-    assertThat(none.getBorderStyle(Spacing.BOTTOM), is(BorderStyle.SOLID.ordinal()));
-
-    BorderDrawable full = new BorderDrawable();
-    full.setBorderStyle(Spacing.ALL, BorderStyle.DOTTED.name());
-    assertThat(full.getBorderStyle(Spacing.ALL), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(full.getBorderStyle(Spacing.LEFT), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(full.getBorderStyle(Spacing.RIGHT), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(full.getBorderStyle(Spacing.TOP), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(full.getBorderStyle(Spacing.BOTTOM), is(BorderStyle.DOTTED.ordinal()));
-
-    BorderDrawable noneAndPart = new BorderDrawable();
-    noneAndPart.setBorderStyle(Spacing.LEFT, BorderStyle.DOTTED.name());
-    noneAndPart.setBorderStyle(Spacing.TOP, BorderStyle.DASHED.name());
-    assertThat(noneAndPart.getBorderStyle(Spacing.LEFT), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(noneAndPart.getBorderStyle(Spacing.RIGHT), is(BorderStyle.SOLID.ordinal()));
-    assertThat(noneAndPart.getBorderStyle(Spacing.TOP), is(BorderStyle.DASHED.ordinal()));
-    assertThat(noneAndPart.getBorderStyle(Spacing.BOTTOM), is(BorderStyle.SOLID.ordinal()));
-
-    BorderDrawable fullAndPart = new BorderDrawable();
-    fullAndPart.setBorderStyle(Spacing.ALL, BorderStyle.DASHED.name());
-    fullAndPart.setBorderStyle(Spacing.LEFT, BorderStyle.DOTTED.name());
-    fullAndPart.setBorderStyle(Spacing.TOP, BorderStyle.SOLID.name());
-    assertThat(fullAndPart.getBorderStyle(Spacing.LEFT), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(fullAndPart.getBorderStyle(Spacing.RIGHT), is(BorderStyle.DASHED.ordinal()));
-    assertThat(fullAndPart.getBorderStyle(Spacing.TOP), is(BorderStyle.SOLID.ordinal()));
-    assertThat(fullAndPart.getBorderStyle(Spacing.BOTTOM), is(BorderStyle.DASHED.ordinal()));
-
-    BorderDrawable partAndFull = new BorderDrawable();
-    partAndFull.setBorderStyle(Spacing.LEFT, BorderStyle.DASHED.name());
-    partAndFull.setBorderStyle(Spacing.ALL, BorderStyle.DOTTED.name());
-    assertThat(partAndFull.getBorderStyle(Spacing.ALL), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(partAndFull.getBorderStyle(Spacing.LEFT), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(partAndFull.getBorderStyle(Spacing.RIGHT), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(partAndFull.getBorderStyle(Spacing.TOP), is(BorderStyle.DOTTED.ordinal()));
-    assertThat(partAndFull.getBorderStyle(Spacing.BOTTOM), is(BorderStyle.DOTTED.ordinal()));
-  }
-
-  @Test
-  public void testIsRounded(){
-    BorderDrawable none = new BorderDrawable();
-    assertThat(none.isRounded(), is(false));
-
-    BorderDrawable full = new BorderDrawable();
-    full.setBorderRadius(BorderDrawable.BORDER_RADIUS_ALL, 12);
-    assertThat(full.isRounded(), is(true));
-
-    BorderDrawable noneAndPart = new BorderDrawable();
-    noneAndPart.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 5);
-    noneAndPart.setBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS, 12);
-    assertThat(noneAndPart.isRounded(), is(true));
-
-    BorderDrawable fullAndPart = new BorderDrawable();
-    fullAndPart.setBorderRadius(BorderDrawable.BORDER_RADIUS_ALL, 0);
-    fullAndPart.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 12);
-    fullAndPart.setBorderRadius(BorderDrawable.BORDER_BOTTOM_RIGHT_RADIUS, 19);
-    assertThat(fullAndPart.isRounded(), is(true));
-
-    BorderDrawable partAndFull = new BorderDrawable();
-    partAndFull.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 12);
-    partAndFull.setBorderRadius(BorderDrawable.BORDER_RADIUS_ALL, 0);
-    assertThat(partAndFull.isRounded(), is(true));
-
-    BorderDrawable zeroAll = new BorderDrawable();
-    zeroAll.setBorderRadius(BorderDrawable.BORDER_RADIUS_ALL, 0);
-    assertThat(zeroAll.isRounded(), is(false));
-
-    BorderDrawable zeroPart = new BorderDrawable();
-    zeroPart.setBorderRadius(BorderDrawable.BORDER_TOP_LEFT_RADIUS, 0);
-    assertThat(zeroPart.isRounded(), is(false));
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/ui/view/gesture/WXGestureTest.java b/android/sdk/src/test/java/com/taobao/weex/ui/view/gesture/WXGestureTest.java
deleted file mode 100644
index 125f9d1..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/ui/view/gesture/WXGestureTest.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.ui.view.gesture;
-
-import android.view.MotionEvent;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.TestActivity;
-import com.taobao.weex.ui.component.ComponentTest;
-import com.taobao.weex.ui.component.WXComponent;
-import com.taobao.weex.ui.component.WXDivTest;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.Robolectric;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 27/09/2016.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-public class WXGestureTest {
-
-  WXGesture mGesture;
-  WXComponent component;
-  @Before
-  public void setUp() throws Exception {
-    component = WXDivTest.create();
-    ComponentTest.create(component);
-
-    component.addEvent(WXGestureType.LowLevelGesture.ACTION_CANCEL.toString());
-    component.addEvent(WXGestureType.LowLevelGesture.ACTION_DOWN.toString());
-    component.addEvent(WXGestureType.LowLevelGesture.ACTION_MOVE.toString());
-    component.addEvent(WXGestureType.LowLevelGesture.ACTION_UP.toString());
-
-    TestActivity activity = Robolectric.setupActivity(TestActivity.class);
-    mGesture = new WXGesture(component, activity);
-
-  }
-
-  @Test
-  public void testOnTouch() throws Exception {
-    MotionEvent event = MotionEvent.obtain(System.currentTimeMillis(), System.currentTimeMillis(),MotionEvent.ACTION_DOWN,0,0,0);
-    mGesture.onTouch(component.getHostView(),event);
-
-    event = MotionEvent.obtain(System.currentTimeMillis(), System.currentTimeMillis(),MotionEvent.ACTION_MOVE,0,0,0);
-    mGesture.onTouch(component.getHostView(),event);
-
-    event = MotionEvent.obtain(System.currentTimeMillis(), System.currentTimeMillis(),MotionEvent.ACTION_UP,0,0,0);
-    mGesture.onTouch(component.getHostView(),event);
-
-    event = MotionEvent.obtain(System.currentTimeMillis(), System.currentTimeMillis(),MotionEvent.ACTION_POINTER_UP,0,0,0);
-    mGesture.onTouch(component.getHostView(),event);
-
-    event = MotionEvent.obtain(System.currentTimeMillis(), System.currentTimeMillis(),MotionEvent.ACTION_CANCEL,0,0,0);
-    mGesture.onTouch(component.getHostView(),event);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/utils/FunctionParserTest.java b/android/sdk/src/test/java/com/taobao/weex/utils/FunctionParserTest.java
deleted file mode 100644
index aa1c719..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/utils/FunctionParserTest.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import org.junit.Test;
-
-import java.util.List;
-
-/**
- * Created by sospartan on 27/09/2016.
- */
-public class FunctionParserTest {
-
-  @Test
-  public void testParse() throws Exception {
-    List<Integer> s = new SingleFunctionParser<>("blur(5px)", new SingleFunctionParser.FlatMapper<Integer>() {
-      @Override
-      public Integer map(String raw) {
-        return WXUtils.getInteger(raw,0);
-      }
-    }).parse("blur");
-    System.out.println(s);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/utils/TypefaceUtilTest.java b/android/sdk/src/test/java/com/taobao/weex/utils/TypefaceUtilTest.java
deleted file mode 100644
index 7416b8d..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/utils/TypefaceUtilTest.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.graphics.Paint;
-import android.graphics.Typeface;
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXSDKInstanceTest;
-
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 8/2/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-public class TypefaceUtilTest {
-
-  @Test
-  public void testPutFontDO() throws Exception {
-    FontDO font = new FontDO("test","url('local:///test')", WXSDKInstanceTest.createInstance());
-    TypefaceUtil.putFontDO(font);
-    assertEquals(TypefaceUtil.getFontDO("test").getUrl(),"local:///test");
-
-  }
-
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/utils/WXFileUtilsTest.java b/android/sdk/src/test/java/com/taobao/weex/utils/WXFileUtilsTest.java
deleted file mode 100644
index 64a0720..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/utils/WXFileUtilsTest.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import java.io.File;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 8/2/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-@PrepareForTest()
-public class WXFileUtilsTest {
-
-  @Rule
-  public PowerMockRule rule = new PowerMockRule();
-
-  @Test
-  public void testLoadFileContent() throws Exception {
-    File folder = new File("build/intermediates/bundles/debug/assets/");
-    if(!folder.exists()){
-      folder = new File("build/intermediates/bundles/debug/assets/");
-      folder.mkdirs();
-    }
-    File file = new File(folder,"test");
-    System.out.println(file.getAbsolutePath());
-    if(!file.exists()){
-      file.createNewFile();
-    }
-
-    WXFileUtils.loadAsset("test", RuntimeEnvironment.application);
-  }
-
-  @Test
-  public void testSaveFile() throws Exception {
-    WXFileUtils.saveFile("build/test","test".getBytes(),RuntimeEnvironment.application);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/utils/WXJsonUtilsTest.java b/android/sdk/src/test/java/com/taobao/weex/utils/WXJsonUtilsTest.java
deleted file mode 100644
index 92f64eb..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/utils/WXJsonUtilsTest.java
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import com.alibaba.fastjson.JSON;
-import org.junit.Test;
-
-import java.math.BigDecimal;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-import java.util.Objects;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 8/2/16.
- */
-public class WXJsonUtilsTest {
-
-
-  static class TestObj{
-    int a;
-
-    public int getA() {
-      return a;
-    }
-
-    public void setA(int a) {
-      this.a = a;
-    }
-  }
-
-  @Test
-  public void testGetList() throws Exception {
-    List<TestObj> list = WXJsonUtils.getList("[{'a':1},{'a':2}]",TestObj.class);
-
-    assertEquals(list.size(),2);
-    assertEquals(list.get(0).getA(),1);
-    assertEquals(list.get(1).getA(),2);
-
-    list = WXJsonUtils.getList("{}",TestObj.class);
-
-    assertEquals(list.size(),0);
-  }
-
-  @Test
-  public void testFromObjectToJSONString() throws Exception {
-    TestObj obj = new TestObj();
-    obj.a  = 1;
-    assertEquals(WXJsonUtils.fromObjectToJSONString(obj),"{\"a\":1}");
-    assertEquals(WXJsonUtils.fromObjectToJSONString(null),"null");
-    assertEquals(WXJsonUtils.fromObjectToJSONString(new Object()),"{}");
-
-    Map<String,Object> data = new HashMap<>();
-    data.put("a",536649655068L);
-    BigDecimal d = new BigDecimal(536649655068L);
-    data.put("d",d);
-    data.put("b",new Long(536649655068L));
-
-
-    Object resp = JSON.parse("[{\"offerId\":536449659068,\"subject\":\"jv2测试offer\",\"offerUnit\":\"千克\",\"price\":{\"price\":234.0},\"imageList\":[\"http://product.1688nongchanping.com/offer/7730-1503041G910-51.jpg\",\"http://product.1688nongchanping.com/offer/7730-1503041G910-51.jpg\",\"http://product.1688nongchanping.com/offer/140-150302120045.jpg\"],\"featureList\":[],\"companyInfo\":null,\"saleInfo\":{\"saledCount\":null,\"avaliableAmount\":100.0},\"detailURL\":\"<p>http://view.m.1688.com/cms/native/offerdetail.html?url=http://img02.taobaocdn.com/tfscom/TB18Z_5KVXXXXbAXXXXXXXXXXXX</p>\"},{\"offerId\":536489059003,\"subject\":\"jv 测试offer——detailURL\",\"offerUnit\":\"千克\",\"price\":{\"price\":12.0},\"imageList\":[\"http://product.1688nongchanping.com/offer/1139304780d4f14e57o.jpg\",\"http://product.1688nongchanping.com/offer/1139304780d4f14e57o.jpg\"],\"featureList\":[],\"companyInfo\":null,\"saleInfo\":{\"saledCount\":null,\"avaliableAmount\":100.0},\"detailURL\":\"<p style=\\\"text-align: center;\\\"><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/147/565/3280565741_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/741/475/3280574147_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/790/816/3280618097_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/841/475/3280574148_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/232/516/3280615232_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/222/949/3281949222_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/247/565/3280565742_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/332/516/3280615233_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/896/865/3280568698_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/790/259/3281952097_1600896868.jpg\\\" /></p>\"},{\"offerId\":536489059017,\"subject\":\"jv测试offer9\",\"offerUnit\":\"千克\",\"price\":{\"price\":12.0},\"imageList\":[\"http://product.1688nongchanping.com/offer/b356b09004d94f429f39c59c68768a38.jpg\",\"http://product.1688nongchanping.com/offer/b356b09004d94f429f39c59c68768a38.jpg\",\"http://product.1688nongchanping.com/offer/140-150302120045.jpg\"],\"featureList\":[],\"companyInfo\":null,\"saleInfo\":{\"saledCount\":null,\"avaliableAmount\":122.0},\"detailURL\":\"<div style=\\\"margin: 0px; padding: 0px;\\\">\\r\\n<p style=\\\"text-align: center;\\\"><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/147/565/3280565741_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/741/475/3280574147_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/790/816/3280618097_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/841/475/3280574148_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/232/516/3280615232_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/222/949/3281949222_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/247/565/3280565742_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/332/516/3280615233_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/896/865/3280568698_1600896868.jpg\\\" /><img style=\\\"visibility: visible;\\\" src=\\\"http://cbu01.alicdn.com/img/ibank/2016/790/259/3281952097_1600896868.jpg\\\" /></p>\\r\\n</div>\"},{\"offerId\":536489059001,\"subject\":\"正儿八经测试3\",\"offerUnit\":\"千克\",\"price\":{\"price\":12.0},\"imageList\":[\"http://product.1688nongchanping.com/offer/3132872979_999566913.jpg\",\"http://product.1688nongchanping.com/offer/3132872979_999566913.jpg\",\"http://product.1688nongchanping.com/offer/3214597083_919536840.jpg\"],\"featureList\":[],\"companyInfo\":null,\"saleInfo\":{\"saledCount\":null,\"avaliableAmount\":2323232.0},\"detailURL\":\"<p>&lt;p data-type=\\\"label-view\\\" style=\\\"color: rgb(255, 255, 255); font-size: 9px; height: 13px; margin-left: 15px; margin-top: 64px; width: 46px; background-image: url(&amp;quot;http://gtms02.alicdn.com/tps/i2/TB1dYb9KVXXXXX5XVXXjm1NHpXX-204-56.png&amp;quot;); background-size: contain; background-repeat: no-repeat;\\\" data-gravity=\\\"5\\\" roc-id=\\\"roc-13\\\"&gt;</p>\\r\\n<p>&nbsp; &nbsp; &lt;span class=\\\"label-content\\\" style=\\\"left: 0px; top: -2.5px;\\\"&gt;JV测试测试测试&lt;/span&gt;</p>\\r\\n<p>&lt;/p&gt;</p>\"},{\"offerId\":536449539162,\"subject\":\"正儿八经测试商品1\",\"offerUnit\":\"千克\",\"price\":{\"price\":23.0},\"imageList\":[\"http://product.1688nongchanping.com/offer/3211026576_999566913.jpg\",\"http://product.1688nongchanping.com/offer/3211026576_999566913.jpg\",\"http://product.1688nongchanping.com/offer/3132872979_999566913.jpg\"],\"featureList\":[],\"companyInfo\":null,\"saleInfo\":{\"saledCount\":null,\"avaliableAmount\":34567.0},\"detailURL\":\"<table>\\r\\n<tbody>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-comment\\\">&lt;!----&gt;</span><span class=\\\"html-doctype\\\">&lt;!DOCTYPE html&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;html&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;head&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;title&gt;</span>图文详情<span class=\\\"html-tag\\\">&lt;/title&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;meta <span class=\\\"html-attribute-name\\\">charset</span>=\\\"<span class=\\\"html-attribute-value\\\">gbk</span>\\\"&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;meta <span class=\\\"html-attribute-name\\\">name</span>=\\\"<span class=\\\"html-attribute-value\\\">data-spm</span>\\\" <span class=\\\"html-attribute-name\\\">content</span>=\\\"<span class=\\\"html-attribute-value\\\">a260g</span>\\\" /&gt;</span><span class=\\\"html-tag\\\">&lt;meta <span class=\\\"html-attribute-name\\\">name</span>='<span class=\\\"html-attribute-value\\\">date</span>' <span class=\\\"html-attribute-name\\\">content</span>='<span class=\\\"html-attribute-value\\\">1469761837251</span>'/&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;meta <span class=\\\"html-attribute-name\\\">name</span>=\\\"<span class=\\\"html-attribute-value\\\">viewport</span>\\\" <span class=\\\"html-attribute-name\\\">content</span>=\\\"<span class=\\\"html-attribute-value\\\">width=790px</span>\\\"&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;link <span class=\\\"html-attribute-name\\\">rel</span>=\\\"<span class=\\\"html-attribute-value\\\">stylesheet</span>\\\" <span class=\\\"html-attribute-name\\\">href</span>=\\\"<a class=\\\"html-attribute-value html-resource-link\\\" href=\\\"http://astyle.alicdn.com/fdevlib/css/lofty/port/lofty.css?_v=4900687.css\\\" target=\\\"_blank\\\">//astyle.alicdn.com/fdevlib/css/lofty/port/lofty.css?_v=4900687.css</a>\\\" /&gt;</span><span class=\\\"html-tag\\\">&lt;/link&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;script <span class=\\\"html-attribute-name\\\">type</span>=\\\"<span class=\\\"html-attribute-value\\\">text/javascript</span>\\\" <span class=\\\"html-attribute-name\\\">src</span>=\\\"<a class=\\\"html-attribute-value html-resource-link\\\" href=\\\"http://astyle.alicdn.com/m/lofty/port/lofty.js?_v=4900687.js\\\" target=\\\"_blank\\\">//astyle.alicdn.com/m/lofty/port/lofty.js?_v=4900687.js</a>\\\"&gt;</span><span class=\\\"html-tag\\\">&lt;/script&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;script <span class=\\\"html-attribute-name\\\">type</span>=\\\"<span class=\\\"html-attribute-value\\\">text/javascript</span>\\\" <span class=\\\"html-attribute-name\\\">src</span>=\\\"<a class=\\\"html-attribute-value html-resource-link\\\" href=\\\"http://astyle.alicdn.com/fdevlib/js/gallery/jquery/jquery-latest.js?_v=4900687.js\\\" target=\\\"_blank\\\">//astyle.alicdn.com/fdevlib/js/gallery/jquery/jquery-latest.js?_v=4900687.js</a>\\\"&gt;</span><span class=\\\"html-tag\\\">&lt;/script&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;style&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">div,p,td,a,strong,b,span{word-break:break-word}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">body img{</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">max-width:790px;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">vertical-align:bottom;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;/style&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;/head&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;body <span class=\\\"html-attribute-name\\\">data-spm</span>=\\\"<span class=\\\"html-attribute-value\\\">8029192</span>\\\"&gt;</span><span class=\\\"html-tag\\\">&lt;script <span class=\\\"html-attribute-name\\\">type</span>=<span class=\\\"html-attribute-value\\\">text/javascript</span>&gt;</span>var dmtrack_c='{-}'; var dmtrack_pageid='0ac6d5d80a6738c01470206317';</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">(function(d){var t=d.createElement('script');t.type='text/javascript';t.async=true;t.src='//astyle-src.alicdn.com/sys/js/beacon/cnb.js';d.getElementsByTagName('head')[0].appendChild(t);}(document));<span class=\\\"html-tag\\\">&lt;/script&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;noscript&gt;</span>&lt;img src=\\\"//dmtracking.1688.com/b.jpg?cD0yJnU9e3ZpZXcubS4xNjg4LmNvbSUyZmNtcyUyZm5hdGl2ZSUyZm9mZmVyZGV0YWlsJTJlaHRtbD91cmw9aHR0cCUzYSUyZiUyZmRzYyUyZXRhb2Jhb2NkbiUyZWNvbSUyZmk4JTJmNTMwJTJmMzgwJTJmNTM2MzgxODI4NjQ5JTJmVEIxRFpXb0xYWFhYWGJqWEZYWDhxdHBGWGxYJTJlZGVzYyUyNTdDdmFyJTI1NUVkZXNjJTI1M0JsYW5nJTI1NUVnYmslMjUzQnNpZ24lMjU1RTEwZDUwYzk3OTVmZmM0N2I3YmYwODhmZTAyZjExMzMzJTI1M0J0JTI1NUUxNDY5Njk3MDgzfSZtPXtHRVR9JnM9ezIwMH0mcj17LX0mYT17JTIyY19tcz0xfGNfbXQ9M3xjX21pZD1iMmItNjAyNDQ5Mjg4fGNfbGlkPW1yJTI1RTklMjVBMyUyNThFJTI1RTYlMjVCNSUyNTgxJTI1RTYlMjVCNiUyNTk1JTI1RTYlMjVCNyUyNThDJTIyfSZiPS0mYz17LX0K&amp;ver=40&amp;pageid=0ac6d5d80a6738c01470206317&amp;time=1470206317\\\" width=\\\"1\\\" height=\\\"1\\\" style=\\\"display:none\\\"&gt;<span class=\\\"html-tag\\\">&lt;/noscript&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;script <span class=\\\"html-attribute-name\\\">type</span>=<span class=\\\"html-attribute-value\\\">text/javascript</span>&gt;</span> var _SPM_a='{-}'; var _SPM_b='{-}';var _SPM_app_name='{-}';var _SPM_template_path='{-}';<span class=\\\"html-tag\\\">&lt;/script&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;script&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">with(document)with(body)with(insertBefore(createElement(\\\"script\\\"),firstChild))setAttribute(\\\"exparams\\\",\\\"category=&amp;userid=602449288&amp;aplus&amp;&amp;asid=AYil6CNtkaFXdONiEQAAAABPw8F55NX8kg==&amp;aat=%22c%5fms%3d1%7cc%5fmt%3d3%7cc%5fmid%3db2b%2d602449288%7cc%5flid%3dmr%25E9%25A3%258E%25E6%25B5%2581%25E6%25B6%2595%25E6%25B7%258C%22&amp;abi=42%2e120%2e74%2e159%2e1456797195765%2e338553%2e3&amp;abb=&amp;\\\",id=\\\"tb-beacon-aplus\\\",src=(location&gt;\\\"https\\\"?\\\"//g\\\":\\\"//g\\\")+\\\".alicdn.com/alilog/mlog/aplus_b2b.js\\\")</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;/script&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;/body&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;script <span class=\\\"html-attribute-name\\\">type</span>=\\\"<span class=\\\"html-attribute-value\\\">text/javascript</span>\\\"&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">define(['util/lazyload/1.0','jquery'],function(LazyLoad,J){</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var main={</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">init:function(){</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this.detailUrl =this._getUrlVars('url');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this.config = {},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this.container=J('body');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this._loadDesc();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_getUrlVars: function(name){</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var vars = [], hash;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var hashes = window.location.href.slice(window.location.href.indexOf('?') + 1).split('&amp;');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">for(var i = 0; i &lt; hashes.length; i++){</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">hash = hashes[i].split('=');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">vars.push(hash[0]);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">vars[hash[0]] = hash[1];</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">return decodeURI(vars[name]);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_loadDesc: function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (this.detailUrl) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this._initLazyLoadDescriptionTFS();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this._initLazyLoadDescription();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_initLazyLoadDescriptionTFS: function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var that = this,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">descURLTFS = that.detailUrl;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">//新老地址处理</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (typeof(descURLTFS) === \\\"string\\\" &amp;&amp; descURLTFS.indexOf(\\\"/tfscom/\\\") &gt;= 0 &amp;&amp; descURLTFS.indexOf(\\\"?t=\\\") &lt; 0) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">descURLTFS = descURLTFS + '?t=' + new Date().getTime();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">J.ajax({</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">url: descURLTFS,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">dataType: 'script',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">timeout: 3000,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">cache: true,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">success: function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (descURLTFS.indexOf(\\\"/tfscom/\\\") &gt;= 0) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (window.offer_details &amp;&amp; window.offer_details.content) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that._descriptionSuccessCallback(window.offer_details.content);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that._initLazyLoadDescription();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (window.desc) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that._descriptionSuccessCallback(window.desc);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that._initLazyLoadDescription();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">error: function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that._initLazyLoadDescription();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">});</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_initLazyLoadDescription: function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var that = this;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var descURL = that.detailUrl;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">//获取offer详情的数据</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">J.ajax(descURL, {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">dataType: 'jsonp',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">data: {},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">success: function(o) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (o.success === true) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that._descriptionSuccessCallback(o.offerDesc);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that.container.html('详情加载失败');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">error: function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that.container.html('详情加载失败');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">});</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_descriptionSuccessCallback: function(o) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var self = this,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">heightStyle = '',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">widthStyle = '',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">styles='',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">imgRegx = /(&lt;img[^&gt;]*)(src *= *(\\\"[^\\\"]*\\\"|'[^']*'|[^ &gt;]*)) *[^&gt;]*&gt;/g,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">heightRegx = /(height[^:]*=\\\\s*(\\\"[^\\\"]*\\\"|'[^']*'|[^ &gt;]*))/g,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">widthRegx = /(width[^:]*=\\\\s*(\\\"[^\\\"]*\\\"|'[^']*'|[^ &gt;]*))/g,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">styleRegx =/style[^=]*=\\\\s*\\\"[^\\\"]*\\\"/g,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">html = '',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">imgCount, count = 0,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">imgs, tempEl,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">SPACEBALL = '//cbu01.alicdn.com/cms/upload/other/lazyload.png',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">that = this;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">html = o || '';</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">imgCount = html.match(imgRegx) ? html.match(imgRegx).length : 0;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">html = html.replace(imgRegx, function(m, p1, p2, p3) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">count++;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">//if (count &lt; 1) return m; // 前 1 个图片不处理</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (m.match(widthRegx)) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">widthStyle = m.match(widthRegx);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">widthStyle = '';</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if(m.match(styleRegx)){</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">styles = m.match(styleRegx);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}else{</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">styles = '';</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (m.indexOf('height') !== -1) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">heightStyle = m.match(heightRegx);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">heightStyle = '';</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (self.config.platform === 'iOS' &amp;&amp; (self.config.networkType === '2g' || self.config.networkType === '3g' || J(window).height() &lt; 481)) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">p3 = handleImgSize(p3, '450x5000', '200x200');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// } else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// p3 = handleImgSize(p3, '450x5000', '400x400');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">return [</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">'&lt;img ',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">'src=\\\"https:' + SPACEBALL + '\\\" data-lazyload-src=',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">p3.replace(/_\\\\.webp\\\"$/,'\\\"') + ' ',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">styles + ' ',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">widthStyle + ' ',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">heightStyle + ' &gt;'</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">].join('');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">});</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">/* ref: http://blog.stevenlevithan.com/archives/faster-than-innerhtml */</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this.container.html(html);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (this.container.html() === '' || this.container.html() == '&lt;p&gt;&lt;/p&gt;') {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this.container.html('卖家暂未添加产品描述');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this._initLink();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">imgs = J('img', this.container);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">for (var i = 0, l = imgs.length; i &lt; l; i++) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">//显示图片，一开始的时候图片都是隐藏的</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">imgs.eq(i).css('visibility', 'visible');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">//图片加载后缩放到detail页宽度</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">imgs.bind('load', function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">J(this).css('visibility', 'visible');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (this.width &gt; that.detailWidth &amp;&amp; J(this).closest('table').length === 0) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">J(this).width('100%');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">J(this).height('auto');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}).error(function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">J(this).hide();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">});</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this._initScroller();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">function handleImgSize(img, size, taobaoSize) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var p = img.match(/(\\\\S+)(\\\\.jpg'|\\\\.jpg\\\"|\\\\.jpg)((\\\\?)?(\\\\S+))J/),</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_img;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">&nbsp;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (img.search(/(\\\\d+)x(\\\\d+)\\\\.jpg/) == -1 &amp;&amp; img.search(/(\\\\.jpg'|\\\\.jpg\\\"|\\\\.jpg)J/) !== -1) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">if (img.indexOf('taobaocdn') !== -1 || img.indexOf('img.alicdn.com') !== -1) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// _img = p[1]+'.jpg_'+ taobaoSize + p[2];</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_img = img;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_img = p[1] + '.' + size + p[2]+p[3];</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">} else {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_img = img;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// var _img = img.replace(/(\\\\S+\\\\.jpg['\\\"]?)\\\\??[^\\\"']*([\\\"'])?J/, function(p, p1, p2) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// return p1 + (p2 || '');</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// });</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">return _img;</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_initLink: function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">this.container.on('click', 'a', function(e) {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">e.preventDefault();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">/*var href = J(this).attr('href'),</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">result = href.match(/(\\\\d+)\\\\.html/);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">result[1] &amp;&amp; Wing.navigator.rewrite('URL', 'http://detail.m.1688.com/page/index.html?offerId=' + result[1]);*/</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">});</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">},</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">_initScroller: function() {</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// setTimeout(function(){</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// var myScroll = new Scroller({</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// container: '#d-content',</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// hScroll:true,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// vScroll:true,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// zoom: true,</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// checkDOMChanges: true</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// });</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">var lazy = new LazyLoad({</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">container: 'body'</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// scroller: myScroll</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">});</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">//lazy.init();</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">// }, 200);</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">}</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">};</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">J(function(){</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">main.init()</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">});</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\">});</td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;/script&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-tag\\\">&lt;/html&gt;</span></td>\\r\\n</tr>\\r\\n<tr>\\r\\n<td class=\\\"line-number\\\">&nbsp;</td>\\r\\n<td class=\\\"line-content\\\"><span class=\\\"html-comment\\\">&lt;!-- user defined footer --&gt;</span> <span class=\\\"html-end-of-file\\\"></span></td>\\r\\n</tr>\\r\\n</tbody>\\r\\n</table>\"}]");
-
-    data.put("c",resp);
-//    System.out.println("max long:"+Long.MAX_VALUE);
-    String result = WXJsonUtils.fromObjectToJSONString(data);
-    System.out.println(result);
-
-  }
-
-  static class TestObject{
-
-    private BigDecimal big = new BigDecimal(536649655068L);
-
-    public BigDecimal getBig() {
-      return big;
-    }
-
-    public void setBig(BigDecimal big) {
-      this.big = big;
-    }
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/utils/WXLogUtilsTest.java b/android/sdk/src/test/java/com/taobao/weex/utils/WXLogUtilsTest.java
deleted file mode 100644
index ece6e0e..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/utils/WXLogUtilsTest.java
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXEnvironment;
-import org.junit.Before;
-import org.junit.Rule;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.api.mockito.PowerMockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.rule.PowerMockRule;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-/**
- * Created by sospartan on 9/18/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-@PrepareForTest({WXEnvironment.class})
-public class WXLogUtilsTest {
-  static class Log extends WXLogUtils{};
-
-  @Rule
-  public PowerMockRule rule = new PowerMockRule();
-
-  @Before
-  public void setUp() throws Exception {
-    WXLogUtils.isShowLineNumber = true;
-    PowerMockito.mockStatic(WXEnvironment.class);
-    PowerMockito.when(WXEnvironment.isApkDebugable()).thenReturn(true);
-  }
-
-  @Test
-  public void testD() throws Exception {
-    Log.d("test");
-    Log.d(null);
-    Log.d("tag","test");
-    Log.d("tag","test | __ | __ __DEBUG | __ ");
-    Log.d("tag",new Throwable("test"));
-  }
-
-  @Test
-  public void testI() throws Exception {
-    Log.i("test");
-    Log.i(null);
-    Log.i("tag","test");
-    Log.i("tag",new Throwable("test"));
-  }
-
-  @Test
-  public void testV() throws Exception {
-    Log.v("test");
-    Log.v(null);
-    Log.v("tag","test");
-    Log.v("tag",new Throwable("test"));
-  }
-
-  @Test
-  public void testW() throws Exception {
-    Log.w("test");
-    Log.w(null);
-    Log.w("tag","test");
-    Log.w("tag",new Throwable("test"));
-  }
-
-  @Test
-  public void testE() throws Exception {
-    Log.e("test");
-    Log.e(null);
-    Log.e("tag","test");
-    Log.e("tag",new Throwable("test"));
-  }
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/utils/WXReflectionUtilsTest.java b/android/sdk/src/test/java/com/taobao/weex/utils/WXReflectionUtilsTest.java
deleted file mode 100644
index 18df379..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/utils/WXReflectionUtilsTest.java
+++ /dev/null
@@ -1,126 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import com.alibaba.fastjson.JSON;
-import com.alibaba.fastjson.JSONArray;
-import com.alibaba.fastjson.JSONObject;
-import com.taobao.weappplus_sdk.BuildConfig;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.List;
-import java.util.Map;
-
-import static org.junit.Assert.*;
-
-/**
- * Created by sospartan on 8/2/16.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore({ "org.mockito.*", "org.robolectric.*", "android.*" })
-public class WXReflectionUtilsTest {
-
-  static class TestA{
-    private boolean value = false;
-  }
-
-  @Test
-  public void testParseArgument() throws Exception {
-   Object value =  WXReflectionUtils.parseArgument(String.class,"dkdkdkdk");
-    assertTrue(value instanceof String);
-
-    value = WXReflectionUtils.parseArgument(long.class,"123444");
-    assertTrue(value instanceof Long);
-
-    value = WXReflectionUtils.parseArgument(int.class,"123444");
-    assertTrue(value instanceof Integer);
-
-    value = WXReflectionUtils.parseArgument(Integer.class,"123444");
-    assertTrue(value instanceof Integer);
-
-    value = WXReflectionUtils.parseArgument(int.class,123444);
-    assertTrue(value instanceof Integer);
-
-    value = WXReflectionUtils.parseArgument(double.class, Double.toString(123.444d));
-    assertTrue(value instanceof Double);
-
-
-
-    JSONObject j = new JSONObject();
-    j.put("a","b");
-    j.put("c",23);
-    value = WXReflectionUtils.parseArgument(String.class,j);
-    assertTrue(value instanceof String);
-
-    value = WXReflectionUtils.parseArgument(Map.class,j);
-    assertTrue(value instanceof Map);
-    assertEquals(((Map)value).get("a"),"b");
-
-    value = WXReflectionUtils.parseArgument(JSONObject.class,j);
-    assertTrue(value instanceof JSONObject);
-    assertEquals(((JSONObject)value).get("a"),"b");
-    assertEquals(((JSONObject)value).get("c"),23);
-
-    value = WXReflectionUtils.parseArgument(JSONObject.class, JSON.toJSONString(j));
-    assertTrue(value instanceof JSONObject);
-    assertEquals(((JSONObject)value).get("a"),"b");
-    assertEquals(((JSONObject)value).get("c"),23);
-
-    JSONArray k = new JSONArray();
-    k.add("b");
-    k.add(23);
-    value = WXReflectionUtils.parseArgument(String[].class, k);
-    assertTrue(value instanceof String[]);
-    assertEquals(((String[])value)[0],"b");
-    assertEquals(((String[])value)[1],"23");
-
-    value = WXReflectionUtils.parseArgument(String[].class, JSON.toJSONString(k));
-    assertTrue(value instanceof String[]);
-    assertEquals(((String[])value)[0],"b");
-    assertEquals(((String[])value)[1],"23");
-
-    value = WXReflectionUtils.parseArgument(List.class, JSON.toJSONString(k));
-    assertTrue(value instanceof List);
-    assertEquals(((List)value).get(0),"b");
-    assertEquals(((List)value).get(1),23);
-
-    k = new JSONArray();
-    k.add(1);
-    k.add(23);
-    value = WXReflectionUtils.parseArgument(int[].class, JSON.toJSONString(k));
-    assertTrue(value instanceof int[]);
-    assertEquals(((int[])value)[0],1);
-    assertEquals(((int[])value)[1],23);
-  }
-
-  @Test
-  public void testSetValue() throws Exception {
-    TestA a = new TestA();
-
-    WXReflectionUtils.setValue(a,"value","true");
-    assertTrue(a.value);
-  }
-
-
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/utils/WXResourceUtilsTest.java b/android/sdk/src/test/java/com/taobao/weex/utils/WXResourceUtilsTest.java
deleted file mode 100644
index caaf8ab..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/utils/WXResourceUtilsTest.java
+++ /dev/null
@@ -1,145 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.graphics.Shader;
-
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.robolectric.RobolectricTestRunner;
-import org.robolectric.annotation.Config;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertNull;
-
-/**
- * Created by caolijie on 16/8/4.
- */
-@RunWith(RobolectricTestRunner.class)
-@Config(manifest = Config.NONE)
-public class WXResourceUtilsTest {
-
-  @Test
-  public void testColor1() throws Exception {
-    int color = WXResourceUtils.getColor("#ffffff");
-    assertEquals(color, 0xffffffff);
-
-    color = WXResourceUtils.getColor("#99ffffff");
-    assertEquals(color, 0x99ffffff);
-
-    color = WXResourceUtils.getColor("#aa123123");
-    assertEquals(color, 0xaa123123);
-
-    color = WXResourceUtils.getColor("#00000000");
-    assertEquals(color, 0x00000000);
-
-    //can't match
-    color = WXResourceUtils.getColor("#ssssss");
-    assertEquals(color, Integer.MIN_VALUE);
-  }
-
-  @Test
-  public void testColor2() throws Exception {
-    int color = WXResourceUtils.getColor("#123");
-    assertEquals(color, 0xff112233);
-
-    color = WXResourceUtils.getColor("#abc");
-    assertEquals(color, 0xffaabbcc);
-
-    //can't match
-    color = WXResourceUtils.getColor("#12332");
-    assertEquals(color, Integer.MIN_VALUE);
-
-    color = WXResourceUtils.getColor("#sss");
-    assertEquals(color, Integer.MIN_VALUE);
-  }
-
-  @Test
-  public void testColor3() throws Exception {
-    int color = WXResourceUtils.getColor("rgba(50%,50%,50%, 0.5)");
-    assertEquals(color, 0x7f7f7f7f);
-
-    color = WXResourceUtils.getColor("rgba( 50%, 50% , 50%   , 0.5 )");
-    assertEquals(color, 0x7f7f7f7f);
-
-    color = WXResourceUtils.getColor("rgba(255, 255, 255, 1.0)");
-    assertEquals(color, 0xffffffff);
-
-    color = WXResourceUtils.getColor("rgba(1%, 1% ,1%, 1)");
-    assertEquals(color, 0xff020202);
-
-    color = WXResourceUtils.getColor("rgba(0%, 0, 1%, 0.1)");
-    assertEquals(color, 0x19000002);
-
-    color = WXResourceUtils.getColor("rgba(100%, 100%, 100%, 0.1)");
-    assertEquals(color, 0x19ffffff);
-
-    color = WXResourceUtils.getColor("rgba(1, 1, 1, 1.0)");
-    assertEquals(color, 0xff010101);
-
-    //can't match
-    color = WXResourceUtils.getColor("rgba(0.1, 0.1, 0.1, 1.0)");
-    assertEquals(color, Integer.MIN_VALUE);
-
-    color = WXResourceUtils.getColor("rgba(10.0%, 101%, -0.1, 50%)");
-    assertEquals(color, Integer.MIN_VALUE);
-  }
-
-  @Test
-  public void testColor4() throws Exception {
-    int color = WXResourceUtils.getColor("rgb(255, 255, 255)");
-    assertEquals(color, 0xffffffff);
-
-    color = WXResourceUtils.getColor("rgb(000000, 255, 255)");
-    assertEquals(color, 0xff00ffff);
-
-    //can't match
-    color = WXResourceUtils.getColor("rgb(256, 256, 256)");
-    assertEquals(color, 0xffffffff);
-
-    color = WXResourceUtils.getColor("rgb(-1, 255, 255)");
-    assertEquals(color, 0xff00ffff);
-  }
-
-  @Test
-  public void testColor5() throws Exception {
-    int color = WXResourceUtils.getColor("aliceblue");
-    assertEquals(color, 0XFFF0F8FF);
-
-    color = WXResourceUtils.getColor("pink");
-    assertEquals(color, 0XFFFFC0CB);
-
-    //can't match
-    color = WXResourceUtils.getColor("jahskdja");
-    assertEquals(color, Integer.MIN_VALUE);
-  }
-
-  @Test
-  public void testGetShader() throws Exception {
-    Shader shader = WXResourceUtils.getShader("linear-gradient(to bottom,#a80077,blue)", 100, 100);
-    assertNotNull(shader);
-    shader = WXResourceUtils.getShader("linear-gradient(to bottom,#a80077,rgb(255,255,0))", 100, 100);
-    assertNotNull(shader);
-    shader = WXResourceUtils.getShader("linear-gradient(to bottom,#a80077,rgba(255,255,0,0.5))", 100, 100);
-    assertNotNull(shader);
-    shader = WXResourceUtils.getShader("gradient", 100, 100);
-    assertNull(shader);
-  }
-}
diff --git a/android/sdk/src/test/java/com/taobao/weex/utils/WXUtilsTest.java b/android/sdk/src/test/java/com/taobao/weex/utils/WXUtilsTest.java
deleted file mode 100644
index e981c69..0000000
--- a/android/sdk/src/test/java/com/taobao/weex/utils/WXUtilsTest.java
+++ /dev/null
@@ -1,184 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package com.taobao.weex.utils;
-
-import android.text.TextUtils;
-
-import com.taobao.weappplus_sdk.BuildConfig;
-import com.taobao.weex.WXEnvironment;
-import com.taobao.weex.WXSDKInstance;
-import com.taobao.weex.common.WXConfig;
-
-import junit.framework.TestCase;
-
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.invocation.InvocationOnMock;
-import org.mockito.stubbing.Answer;
-import org.powermock.api.mockito.PowerMockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.PowerMockRunner;
-import org.robolectric.annotation.Config;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import static org.mockito.Matchers.any;
-
-/**
- * Created by lixinke on 16/2/24.
- */
-@RunWith(PowerMockRunner.class)
-@Config(constants = BuildConfig.class, sdk = 19)
-@PowerMockIgnore( {"org.mockito.*", "org.robolectric.*", "android.*"})
-@PrepareForTest( {WXEnvironment.class, WXViewUtils.class, WXSDKInstance.class, TextUtils.class})
-public class WXUtilsTest extends TestCase {
-
-    public static final float TEST_DENSITY = 3.0f;
-    public static final int TEST_SCREEN_WIDTH = 1024;
-    public static final int TEST_VIEW_PORT = 800;
-
-    @Before
-    public void setUp() throws Exception {
-        super.setUp();
-
-        Map<String, String> map = new HashMap<>();
-        map.put(WXConfig.scale, Float.toString(TEST_DENSITY));
-        PowerMockito.mockStatic(WXEnvironment.class);
-        PowerMockito.when(WXEnvironment.class, "getConfig").thenReturn(map);
-
-        PowerMockito.mockStatic(WXViewUtils.class);
-        PowerMockito.when(WXViewUtils.class, "getScreenWidth").thenReturn(TEST_SCREEN_WIDTH);
-
-        PowerMockito.mockStatic(WXSDKInstance.class);
-        PowerMockito.when(WXSDKInstance.class, "getViewPortWidth").thenReturn(TEST_VIEW_PORT);
-
-        PowerMockito.mockStatic(TextUtils.class);
-        PowerMockito.when(TextUtils.isEmpty(any(CharSequence.class))).thenAnswer(new Answer<Boolean>() {
-            @Override
-            public Boolean answer(InvocationOnMock invocation) throws Throwable {
-                CharSequence a = (CharSequence) invocation.getArguments()[0];
-                return !(a != null && a.length() > 0);
-            }
-        });
-        // also look at @PrepareForTest if add mock of new class
-    }
-
-    @Test
-    public void testGetFloat() throws Exception {
-        float test_float = WXUtils.getFloat("12324.9px");
-        assertEquals(12324.9, test_float, 0.01);
-
-        assertEquals(WXUtils.fastGetFloat("1.2345",2), 1.23f);
-    }
-
-    @Test
-    public void testGetInt() throws Exception {
-        int test_int = WXUtils.getInt("23px");
-        assertEquals(23, test_int);
-    }
-
-    @Test
-    public void testGetLong() throws Exception {
-        long test_long = WXUtils.getLong("8098px");
-        assertEquals(8098, test_long);
-    }
-
-    @Test
-    public void testGetDouble() throws Exception {
-        double test_Double = WXUtils.getDouble("8098.8989px");
-        assertEquals(8098.8, test_Double, 0.1);
-    }
-
-    @Test
-    public void testGetFloatWX() throws Exception {
-        Float test_float = WXUtils.getFloatByViewport("100wx", TEST_VIEW_PORT);
-        Float want = 100 * TEST_DENSITY * TEST_VIEW_PORT / TEST_SCREEN_WIDTH;
-        assertEquals(test_float, want , 0.01);
-
-        test_float = WXUtils.getFloatByViewport("100px", TEST_VIEW_PORT);
-        want = 100F;
-        assertEquals(test_float, want);
-
-        test_float = WXUtils.getFloatByViewport("100.2", TEST_VIEW_PORT);
-        want = 100.2F;
-        assertEquals(test_float, want);
-
-        test_float = WXUtils.getFloatByViewport(100.2F, TEST_VIEW_PORT);
-        want = 100.2F;
-        assertEquals(test_float, want, 0.0001);
-
-        test_float = WXUtils.getFloatByViewport(100.2D, TEST_VIEW_PORT);
-        want = 100.2F;
-        assertEquals(test_float, want, 0.0001);
-
-        test_float = WXUtils.getFloatByViewport("NaN", TEST_VIEW_PORT);
-        want = Float.NaN;
-        assertEquals(test_float, want);
-    }
-
-    @Test
-    public void testGetIntWX() throws Exception {
-        Integer test_int = WXUtils.getInt("100wx");
-        Integer want = (int)(100 * TEST_DENSITY * 750 / TEST_SCREEN_WIDTH);
-        assertEquals(test_int, want);
-
-        test_int = WXUtils.getInt("100px");
-        want = 100;
-        assertEquals(test_int, want);
-
-        test_int = WXUtils.getInt("100");
-        want = 100;
-        assertEquals(test_int, want);
-
-        test_int = WXUtils.getInt(100);
-        want = 100;
-        assertEquals(test_int, want);
-
-        test_int = WXUtils.getInt(100.1);
-        want = 0;
-        assertEquals(test_int, want); // double can not cast to integer
-    }
-
-    @Test
-    public void testGetDoubleWX() throws Exception {
-        Double test_double = WXUtils.getDouble("100.32wx");
-        Double want = (100.32D * TEST_DENSITY * 750 / TEST_SCREEN_WIDTH);
-        assertEquals(test_double, want, 0.01);
-
-        test_double = WXUtils.getDouble("100px");
-        want = 100D;
-        assertEquals(test_double, want, 0.01);
-
-        test_double = WXUtils.getDouble("100");
-        want = 100D;
-        assertEquals(test_double, want, 0.01);
-
-        test_double = WXUtils.getDouble(100);
-        want = 100D;
-        assertEquals(test_double, want, 0.01);
-
-        test_double = WXUtils.getDouble(100.1);
-        want = 100.1D;
-        assertEquals(test_double, want, 0.01);
-    }
-
-}
diff --git a/android/sdk/src/test/java/org/mockito/configuration/MockitoConfiguration.java b/android/sdk/src/test/java/org/mockito/configuration/MockitoConfiguration.java
deleted file mode 100644
index d6f285c..0000000
--- a/android/sdk/src/test/java/org/mockito/configuration/MockitoConfiguration.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-package org.mockito.configuration;
-
-/**
- * Created by sospartan on 7/28/16.
- */
-public class MockitoConfiguration extends DefaultMockitoConfiguration {
-  @Override
-  public boolean enableClassCache() {
-    return false;
-  }
-}
diff --git a/android/sdk/wrap.sh b/android/sdk/wrap.sh
index 2b0dfbe..0dc64d6 100644
--- a/android/sdk/wrap.sh
+++ b/android/sdk/wrap.sh
@@ -1,4 +1,20 @@
 #!/system/bin/sh
+# 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
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# 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.
 HERE="$(cd "$(dirname "$0")" && pwd)"
 export ASAN_OPTIONS=log_to_syslog=false,allow_user_segv_handler=1,use_sigaltstack=0
 ASAN_LIB=$(ls $HERE/libclang_rt.asan-*-android.so)
diff --git a/android/settings.gradle b/android/settings.gradle
index 31eb854..a0d9042 100644
--- a/android/settings.gradle
+++ b/android/settings.gradle
@@ -1,3 +1,21 @@
+/*
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
 rootProject.name = 'weex-project'
 
 include ":playground"
diff --git a/dangerfile-output.js b/dangerfile-output.js
index 3f58afe..9a5346a 100644
--- a/dangerfile-output.js
+++ b/dangerfile-output.js
@@ -40,20 +40,7 @@
   }
 }
 
-if (title === 'OCLint Result') {
-  const command = 'cat ios/sdk/oclint.log | grep -v "Summary: TotalFiles=" | grep -i "P[1|2]"'
-  const child = shell.exec(command)
-  if (child.stdout !== '') {
-    fail(child.stdout)
-    fail(title)
-  }
-  if (child.stderr !== '') {
-    fail(child.stderr)
-    fail(title)
-  }
-}
-else if (title === 'AndroidLint Result') {
-  var content = fs.readFileSync('android/sdk/build/reports/lint-results.html', 'utf8')
+function check_android_lint(content){
   // in xml report,Overview Section,Disabled Checks Section and Suppressing Warnings and Errors Section is not reported.
   // in html report, those Section are included,
   // but Overview Section can't work in markdown,
@@ -68,4 +55,23 @@
     fail(content)
     fail(title)
   }
+}
+
+if (title === 'OCLint Result') {
+  const command = 'cat ios/sdk/oclint.log | grep -v "Summary: TotalFiles=" | grep -i "P[1|2]"'
+  const child = shell.exec(command)
+  if (child.stdout !== '') {
+    fail(child.stdout)
+    fail(title)
+  }
+  if (child.stderr !== '') {
+    fail(child.stderr)
+    fail(title)
+  }
+}
+else if (title === 'AndroidLint Result') {
+  var apacheRelease_content = fs.readFileSync('android/sdk/build/reports/lint-results-apacheRelease.html', 'utf8')
+  var legacyRelease_content = fs.readFileSync('android/sdk/build/reports/lint-results-apacheRelease.html', 'utf8')
+  check_android_lint(apacheRelease_content)
+  check_android_lint(legacyRelease_content)
 }
\ No newline at end of file
diff --git a/dangerfile.js b/dangerfile.js
index 9f3cedd..8058c8e 100644
--- a/dangerfile.js
+++ b/dangerfile.js
@@ -292,6 +292,7 @@
   'test/js\-framework/case',
   'android/playground/app/src/main/assets',
   'android/sdk/assets',
+  'android/sdk/src/main/java/org/apache/weex/utils/WXDataStructureUtil.java',
   'ios/playground/bundlejs',
   'ios/sdk/WeexSDK/Resources',
   'ios/sdk/WeexSDK/Sources/Layout',
@@ -525,7 +526,6 @@
     message("According to the blame info, we recommended " + names.join(' , ') + " to be the reviewers.")
   }
 }
-message('danger test finished.')
 /*
  * find reviewer end
  */
diff --git a/ios/sdk/WeexSDK.xcodeproj/project.pbxproj b/ios/sdk/WeexSDK.xcodeproj/project.pbxproj
index feda1d7..4d18eaa 100644
--- a/ios/sdk/WeexSDK.xcodeproj/project.pbxproj
+++ b/ios/sdk/WeexSDK.xcodeproj/project.pbxproj
@@ -618,6 +618,16 @@
 		D735F1B222D761F800B53CDF /* log_utils.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D735F1AC22D761F800B53CDF /* log_utils.cpp */; };
 		D735F1B322D761F800B53CDF /* log_utils.cpp in Sources */ = {isa = PBXBuildFile; fileRef = D735F1AC22D761F800B53CDF /* log_utils.cpp */; };
 		D77286FF22C9B22C00E1DA7D /* eagle_bridge.cpp in Sources */ = {isa = PBXBuildFile; fileRef = BD9205FA223651D800EDF93D /* eagle_bridge.cpp */; };
+		D7D15AF723960F5D0024BC33 /* WXDarkSchemeModule.m in Sources */ = {isa = PBXBuildFile; fileRef = D7D15AF523960F5C0024BC33 /* WXDarkSchemeModule.m */; };
+		D7D15AF823960F5D0024BC33 /* WXDarkSchemeModule.m in Sources */ = {isa = PBXBuildFile; fileRef = D7D15AF523960F5C0024BC33 /* WXDarkSchemeModule.m */; };
+		D7D15AF923960F5D0024BC33 /* WXDarkSchemeModule.h in Headers */ = {isa = PBXBuildFile; fileRef = D7D15AF623960F5D0024BC33 /* WXDarkSchemeModule.h */; };
+		D7D15AFA23960F5D0024BC33 /* WXDarkSchemeModule.h in Headers */ = {isa = PBXBuildFile; fileRef = D7D15AF623960F5D0024BC33 /* WXDarkSchemeModule.h */; };
+		D7D6B6E2238E1B1D00BE56DD /* WXDarkSchemeProtocol.h in Headers */ = {isa = PBXBuildFile; fileRef = D7D6B6E1238E1B1D00BE56DD /* WXDarkSchemeProtocol.h */; settings = {ATTRIBUTES = (Public, ); }; };
+		D7D6B6E3238E1B1D00BE56DD /* WXDarkSchemeProtocol.h in Headers */ = {isa = PBXBuildFile; fileRef = D7D6B6E1238E1B1D00BE56DD /* WXDarkSchemeProtocol.h */; settings = {ATTRIBUTES = (Public, ); }; };
+		D7D6B6E6238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.m in Sources */ = {isa = PBXBuildFile; fileRef = D7D6B6E4238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.m */; };
+		D7D6B6E7238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.m in Sources */ = {isa = PBXBuildFile; fileRef = D7D6B6E4238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.m */; };
+		D7D6B6E8238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.h in Headers */ = {isa = PBXBuildFile; fileRef = D7D6B6E5238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.h */; };
+		D7D6B6E9238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.h in Headers */ = {isa = PBXBuildFile; fileRef = D7D6B6E5238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.h */; };
 		DC03ADB91D508719003F76E7 /* WXTextAreaComponent.mm in Sources */ = {isa = PBXBuildFile; fileRef = DC03ADB71D508719003F76E7 /* WXTextAreaComponent.mm */; };
 		DC03ADBA1D508719003F76E7 /* WXTextAreaComponent.h in Headers */ = {isa = PBXBuildFile; fileRef = DC03ADB81D508719003F76E7 /* WXTextAreaComponent.h */; };
 		DC15A3DB2010BC93009C8977 /* weex-main-jsfm.js in Resources */ = {isa = PBXBuildFile; fileRef = DC15A3D92010BC93009C8977 /* weex-main-jsfm.js */; };
@@ -1351,6 +1361,11 @@
 		D3FC0DF61C508B2A002B9E31 /* WXTimerModule.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = WXTimerModule.m; sourceTree = "<group>"; };
 		D735F1AB22D761F800B53CDF /* log_utils.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = log_utils.h; sourceTree = "<group>"; };
 		D735F1AC22D761F800B53CDF /* log_utils.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = log_utils.cpp; sourceTree = "<group>"; };
+		D7D15AF523960F5C0024BC33 /* WXDarkSchemeModule.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = WXDarkSchemeModule.m; sourceTree = "<group>"; };
+		D7D15AF623960F5D0024BC33 /* WXDarkSchemeModule.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WXDarkSchemeModule.h; sourceTree = "<group>"; };
+		D7D6B6E1238E1B1D00BE56DD /* WXDarkSchemeProtocol.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WXDarkSchemeProtocol.h; sourceTree = "<group>"; };
+		D7D6B6E4238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = WXDarkSchemeDefaultImpl.m; sourceTree = "<group>"; };
+		D7D6B6E5238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WXDarkSchemeDefaultImpl.h; sourceTree = "<group>"; };
 		DAB176F008F516E4F9391C61 /* libPods-WeexSDK.a */ = {isa = PBXFileReference; explicitFileType = archive.ar; includeInIndex = 0; path = "libPods-WeexSDK.a"; sourceTree = BUILT_PRODUCTS_DIR; };
 		DC03ADB71D508719003F76E7 /* WXTextAreaComponent.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = WXTextAreaComponent.mm; sourceTree = "<group>"; };
 		DC03ADB81D508719003F76E7 /* WXTextAreaComponent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WXTextAreaComponent.h; sourceTree = "<group>"; };
@@ -1476,6 +1491,8 @@
 		59A583031CF5B2FD0081FD3E /* Handler */ = {
 			isa = PBXGroup;
 			children = (
+				D7D6B6E5238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.h */,
+				D7D6B6E4238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.m */,
 				33CE190C2153443000CF9670 /* WXJSFrameworkLoadDefaultImpl.h */,
 				33CE190D2153443000CF9670 /* WXJSFrameworkLoadDefaultImpl.m */,
 				59A583041CF5B2FD0081FD3E /* WXNavigationDefaultImpl.h */,
@@ -1857,6 +1874,7 @@
 		77D1611C1C02DD3C0010B15B /* Protocol */ = {
 			isa = PBXGroup;
 			children = (
+				D7D6B6E1238E1B1D00BE56DD /* WXDarkSchemeProtocol.h */,
 				33CE19122153444900CF9670 /* WXJSFrameworkLoadProtocol.h */,
 				17036A5220FDE7490029AE3D /* WXApmProtocol.h */,
 				17C74F0E2072147A00AB4CAB /* WXAnalyzerProtocol.h */,
@@ -1937,6 +1955,8 @@
 		77E659D71C07F585008B8775 /* Module */ = {
 			isa = PBXGroup;
 			children = (
+				D7D15AF623960F5D0024BC33 /* WXDarkSchemeModule.h */,
+				D7D15AF523960F5C0024BC33 /* WXDarkSchemeModule.m */,
 				7704894622AA358400E7606F /* WXConsoleLogModule.h */,
 				BD35ADE92303BEA60050ED82 /* WXConsoleLogModule.mm */,
 				BA5F00EF1FC5AFFE00F76B5C /* WXLocaleModule.h */,
@@ -2421,6 +2441,7 @@
 				BD88C13F22F02111004467AA /* render_action_remove_child_from_richtext.h in Headers */,
 				BD9205FB223651D900EDF93D /* eagle_bridge.h in Headers */,
 				BD9205F82236518700EDF93D /* WXDataRenderHandler.h in Headers */,
+				D7D6B6E2238E1B1D00BE56DD /* WXDarkSchemeProtocol.h in Headers */,
 				7715EB6221A69DD9001F1108 /* WXRichText.h in Headers */,
 				B8D66C1B21255730003960BD /* style.h in Headers */,
 				B8D66C2321255730003960BD /* layout.h in Headers */,
@@ -2443,6 +2464,7 @@
 				745ED2DA1C5F2C7E002DB5A8 /* WXView.h in Headers */,
 				B8F3323C2141A4C600701BA0 /* string_util.h in Headers */,
 				17B122252090AAB000387E33 /* WXSDKError.h in Headers */,
+				D7D6B6E8238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.h in Headers */,
 				2AE5B7521CAB7DBD0082FDDB /* WXAComponent.h in Headers */,
 				B8D66C4521255730003960BD /* render_action_createbody.h in Headers */,
 				77D1614F1C02E3880010B15B /* WXUtility.h in Headers */,
@@ -2616,6 +2638,7 @@
 				B8D66CA921255730003960BD /* wson_util.h in Headers */,
 				7704894822AA358500E7606F /* WXConsoleLogModule.h in Headers */,
 				B8D66C8B21255730003960BD /* render_list_factory.h in Headers */,
+				D7D15AF923960F5D0024BC33 /* WXDarkSchemeModule.h in Headers */,
 				745B2D681E5A8E1E0092D38A /* WXMultiColumnLayout.h in Headers */,
 				B89543F720EB18B5006EAD63 /* WXCoreBridge.h in Headers */,
 				2A60CE9C1C91733E00857B9F /* WXSwitchComponent.h in Headers */,
@@ -2671,6 +2694,7 @@
 				B8D66C2621255730003960BD /* flex_enum.h in Headers */,
 				DCA445D21EFA594600D0CFA8 /* WXComponent+Display.h in Headers */,
 				DCA445A81EFA572B00D0CFA8 /* WXResourceResponse.h in Headers */,
+				D7D6B6E3238E1B1D00BE56DD /* WXDarkSchemeProtocol.h in Headers */,
 				DCA445BC1EFA57B000D0CFA8 /* WXConvert.h in Headers */,
 				B8D66C8021255730003960BD /* render_scroller_factory.h in Headers */,
 				DCA445C11EFA57D000D0CFA8 /* WXBridgeManager.h in Headers */,
@@ -2696,6 +2720,7 @@
 				B8D66C9221255730003960BD /* render_factory_interface.h in Headers */,
 				DCA445B41EFA577F00D0CFA8 /* WXJSExceptionProtocol.h in Headers */,
 				B8D66CA221255730003960BD /* WeexApiHeader.h in Headers */,
+				D7D6B6E9238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.h in Headers */,
 				74B81AEF1F73C3E900D3A61D /* WXComponent+DataBinding.h in Headers */,
 				DCA445B51EFA578400D0CFA8 /* WXJSExceptionInfo.h in Headers */,
 				B8D66C9E21255730003960BD /* json11.hpp in Headers */,
@@ -2822,6 +2847,7 @@
 				B8D66C3E21255730003960BD /* render_action_createfinish.h in Headers */,
 				DCA445F21EFA5A2300D0CFA8 /* WXHeaderComponent.h in Headers */,
 				DCA445DD1EFA59B300D0CFA8 /* WXRecyclerUpdateController.h in Headers */,
+				D7D15AFA23960F5D0024BC33 /* WXDarkSchemeModule.h in Headers */,
 				DCA4461E1EFA5AAF00D0CFA8 /* WXComponentFactory.h in Headers */,
 				33CE190F2153443000CF9670 /* WXJSFrameworkLoadDefaultImpl.h in Headers */,
 				B87B9E7E21539B3300B6DC61 /* WXVersion.h in Headers */,
@@ -2997,8 +3023,7 @@
 					};
 					77D160FC1C02DBE70010B15B = {
 						CreatedOnToolsVersion = 7.1.1;
-						DevelopmentTeam = 5783442933;
-						ProvisioningStyle = Automatic;
+						ProvisioningStyle = Manual;
 					};
 					DCA445241EFA555400D0CFA8 = {
 						CreatedOnToolsVersion = 8.3.3;
@@ -3154,6 +3179,7 @@
 				747DF6831E31AEE4005C53A8 /* WXLength.m in Sources */,
 				17E5ACE2209211BD00EE81F1 /* WXTransition.mm in Sources */,
 				77E65A0E1C155E99008B8775 /* WXDivComponent.m in Sources */,
+				D7D6B6E6238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.m in Sources */,
 				B8D66CAB21255730003960BD /* wson_util.cpp in Sources */,
 				ED053502207F4DEB007B4568 /* JSContext+Weex.m in Sources */,
 				2A60CE9D1C91733E00857B9F /* WXSwitchComponent.mm in Sources */,
@@ -3318,6 +3344,7 @@
 				742AD72F1DF98C45007DC46C /* WXResourceRequest.m in Sources */,
 				7461F8931CFB373100F62D44 /* WXLayer.m in Sources */,
 				74D205211E091B8000128F44 /* WXCallJSMethod.m in Sources */,
+				D7D15AF723960F5D0024BC33 /* WXDarkSchemeModule.m in Sources */,
 				BD88C14522F02120004467AA /* render_action_update_richtext_child_attr.cpp in Sources */,
 				C41E1A981DC1FD15009C7F90 /* WXDatePickerManager.m in Sources */,
 				BDEEADBA22F2902E0099F1D7 /* time_calculator.cpp in Sources */,
@@ -3345,6 +3372,7 @@
 				B82A159920F857200098A509 /* WXSDKError.m in Sources */,
 				B82A159820F8556F0098A509 /* WXSDKInstance_performance.m in Sources */,
 				B82A159B20F857470098A509 /* WXWebSocketModule.m in Sources */,
+				D7D6B6E7238E1B2A00BE56DD /* WXDarkSchemeDefaultImpl.m in Sources */,
 				BA5F00F41FC6834C00F76B5C /* WXLocaleModule.m in Sources */,
 				DCA4452F1EFA55B300D0CFA8 /* WXResourceLoader.m in Sources */,
 				DCA445301EFA55B300D0CFA8 /* WXComponent+Events.m in Sources */,
@@ -3509,6 +3537,7 @@
 				DCA445931EFA55B300D0CFA8 /* WXComponentManager.mm in Sources */,
 				DCA445941EFA55B300D0CFA8 /* WXComponentFactory.m in Sources */,
 				DCA445951EFA55B300D0CFA8 /* WXRuleManager.m in Sources */,
+				D7D15AF823960F5D0024BC33 /* WXDarkSchemeModule.m in Sources */,
 				BD88C14622F02120004467AA /* render_action_update_richtext_child_attr.cpp in Sources */,
 				DCA445961EFA55B300D0CFA8 /* WXMonitor.m in Sources */,
 				BDEEADBB22F2902E0099F1D7 /* time_calculator.cpp in Sources */,
@@ -3743,10 +3772,10 @@
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = NO;
 				CODE_SIGN_IDENTITY = "iPhone Developer";
 				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
-				CODE_SIGN_STYLE = Automatic;
+				CODE_SIGN_STYLE = Manual;
 				DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
 				DEFINES_MODULE = YES;
-				DEVELOPMENT_TEAM = 5783442933;
+				DEVELOPMENT_TEAM = "";
 				DYLIB_COMPATIBILITY_VERSION = 1;
 				DYLIB_CURRENT_VERSION = 1;
 				DYLIB_INSTALL_NAME_BASE = "@rpath";
@@ -3785,6 +3814,7 @@
 				PRODUCT_BUNDLE_IDENTIFIER = com.taobao.WeexSDK;
 				PRODUCT_NAME = "$(TARGET_NAME)";
 				PROVISIONING_PROFILE_SPECIFIER = "";
+				"PROVISIONING_PROFILE_SPECIFIER[sdk=macosx*]" = "";
 				SKIP_INSTALL = YES;
 				VALID_ARCHS = "arm64 armv7 x86_64 i386";
 				WARNING_CFLAGS = "";
@@ -3802,9 +3832,9 @@
 				CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = NO;
 				CODE_SIGN_IDENTITY = "iPhone Developer";
 				"CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "";
-				CODE_SIGN_STYLE = Automatic;
+				CODE_SIGN_STYLE = Manual;
 				DEFINES_MODULE = YES;
-				DEVELOPMENT_TEAM = 5783442933;
+				DEVELOPMENT_TEAM = "";
 				DYLIB_COMPATIBILITY_VERSION = 1;
 				DYLIB_CURRENT_VERSION = 1;
 				DYLIB_INSTALL_NAME_BASE = "@rpath";
@@ -3843,6 +3873,7 @@
 				PRODUCT_BUNDLE_IDENTIFIER = com.taobao.WeexSDK;
 				PRODUCT_NAME = "$(TARGET_NAME)";
 				PROVISIONING_PROFILE_SPECIFIER = "";
+				"PROVISIONING_PROFILE_SPECIFIER[sdk=macosx*]" = "";
 				SKIP_INSTALL = YES;
 				VALID_ARCHS = "arm64 armv7 x86_64 i386";
 				WARNING_CFLAGS = "";
diff --git a/ios/sdk/WeexSDK/Sources/Bridge/WXBridgeContext.m b/ios/sdk/WeexSDK/Sources/Bridge/WXBridgeContext.m
index 922986b..d72c379 100644
--- a/ios/sdk/WeexSDK/Sources/Bridge/WXBridgeContext.m
+++ b/ios/sdk/WeexSDK/Sources/Bridge/WXBridgeContext.m
@@ -145,12 +145,12 @@
     }];
     
     [_jsBridge registerCallUpdateComponentData:^NSInteger(NSString *instanceId, NSString *componentId, NSString *jsonData) {
-        if (_dataRenderHandler) {
+        if (weakSelf.dataRenderHandler) {
             WXPerformBlockOnComponentThread(^{
                 long start = [WXUtility getUnixFixTimeMillis];
                 WXSDKInstance *instance = [WXSDKManager instanceForID:instanceId];
                 [instance.apmInstance addUpdateComponentDataTimestamp:start];
-                [_dataRenderHandler callUpdateComponentData:instanceId componentId:componentId jsonData:jsonData];
+                [weakSelf.dataRenderHandler callUpdateComponentData:instanceId componentId:componentId jsonData:jsonData];
                 [instance.apmInstance addUpdateComponentDataTime:[WXUtility getUnixFixTimeMillis] - start];
             });
         }
@@ -567,6 +567,7 @@
                         JSObjectSetPrototype(instanceContextRef, JSValueToObject(instanceContextRef, [instanceContextEnvironment valueForProperty:key].JSValueRef, NULL), JSObjectGetPrototype(instanceContextRef, instanceGlobalObject));
                     }
                     JSObjectSetProperty(instanceContextRef, instanceGlobalObject, propertyName, [instanceContextEnvironment valueForProperty:key].JSValueRef, 0, NULL);
+                    JSStringRelease(propertyName);
                 }
                 
                 if (WX_SYS_VERSION_LESS_THAN(@"10.2")) {
diff --git a/ios/sdk/WeexSDK/Sources/Bridge/WXCoreBridge.mm b/ios/sdk/WeexSDK/Sources/Bridge/WXCoreBridge.mm
index e241609..f232ada 100644
--- a/ios/sdk/WeexSDK/Sources/Bridge/WXCoreBridge.mm
+++ b/ios/sdk/WeexSDK/Sources/Bridge/WXCoreBridge.mm
@@ -1302,6 +1302,7 @@
         _customPages[sId] = page;
     }
     
+    SetConvertCurrentPage(pageId);
     [WXCustomPageBridge parseRenderObject:data parentRef:"" index:0 genObject:^(const std::string &ref, const std::string &type, const std::string &parentRef, std::map<std::string, std::string> *styles, std::map<std::string, std::string> *attrs, std::set<std::string> *events, int index) {
         if (parentRef.empty()) {
             // is root body
@@ -1343,6 +1344,7 @@
 {
     RenderPageCustom* page = [self getPage:pageId];
     if (page && page->IsValid()) {
+        SetConvertCurrentPage(pageId);
         page->UpdateAttr([ref UTF8String] ?: "", [WXCustomPageBridge parseMapValuePairs:data]);
     }
 }
@@ -1351,6 +1353,7 @@
 {
     RenderPageCustom* page = [self getPage:pageId];
     if (page && page->IsValid()) {
+        SetConvertCurrentPage(pageId);
         page->UpdateStyle([ref UTF8String] ?: "", [WXCustomPageBridge parseMapValuePairs:data]);
     }
 }
@@ -1406,6 +1409,7 @@
         if (target && target->shouldHandleModuleMethod([moduleName UTF8String] ?: "", [methodName UTF8String] ?: "")) {
             __block const char* seralizedArguments = nullptr;
             __block const char* seralizedOptions = nullptr;
+            SetConvertCurrentPage(pageId);
             ConvertToCString(arguments, ^(const char * value) {
                 if (value != nullptr) {
                     seralizedArguments = strdup(value);
@@ -1495,6 +1499,7 @@
         if (target) {
             __block const char* seralizedArguments = nullptr;
             __block const char* seralizedOptions = nullptr;
+            SetConvertCurrentPage(pageId);
             ConvertToCString(arguments, ^(const char * value) {
                 if (value != nullptr) {
                     seralizedArguments = strdup(value);
@@ -1565,6 +1570,8 @@
         WeexCore::WeexCoreManager::Instance()->set_script_bridge(jsBridge);
         
         WeexCore::WeexCoreManager::Instance()->set_measure_function_adapter(new WeexCore::WXCoreMeasureFunctionBridge());
+
+        [[WXSDKManager bridgeMgr] checkJSThread];
     });
 }
 
@@ -1847,6 +1854,7 @@
         return;
     }
     
+    SetConvertCurrentPage(pageId);
     const std::string page([pageId UTF8String] ?: "");
     RenderManager::GetInstance()->CreatePage(page, [&] (RenderPage* pageInstance) -> RenderObject* {
         pageInstance->set_before_layout_needed(false); // we do not need before and after layout
@@ -1868,11 +1876,13 @@
 
 + (void)callUpdateAttrs:(NSString*)pageId ref:(NSString*)ref data:(NSDictionary*)data
 {
+    SetConvertCurrentPage(pageId);
     WeexCore::RenderManager::GetInstance()->UpdateAttr([pageId UTF8String] ?: "", [ref UTF8String] ?: "", [self _parseMapValuePairs:data]);
 }
 
 + (void)callUpdateStyle:(NSString*)pageId ref:(NSString*)ref data:(NSDictionary*)data
 {
+    SetConvertCurrentPage(pageId);
     WeexCore::RenderManager::GetInstance()->UpdateStyle([pageId UTF8String] ?: "", [ref UTF8String] ?: "", [self _parseMapValuePairs:data]);
 }
 
diff --git a/ios/sdk/WeexSDK/Sources/Bridge/WXJSCoreBridge.mm b/ios/sdk/WeexSDK/Sources/Bridge/WXJSCoreBridge.mm
index 9293fa5..413b6d9 100644
--- a/ios/sdk/WeexSDK/Sources/Bridge/WXJSCoreBridge.mm
+++ b/ios/sdk/WeexSDK/Sources/Bridge/WXJSCoreBridge.mm
@@ -39,6 +39,7 @@
 #import "WXCoreBridge.h"
 #import "WXAnalyzerCenter.h"
 
+
 #import <dlfcn.h>
 
 #import <mach/mach.h>
@@ -80,6 +81,7 @@
 {
     _jsContext.instanceId = nil;
     __block JSContext* theContext = _jsContext;
+    _jsContext = nil; // Make sure that the context MUST be freed in JS thread.
     WXPerformBlockOnBridgeThreadForInstance(^{
          theContext = nil; // release the context in js thread to avoid main-thread deadlock
     }, _weexInstanceId);
@@ -142,7 +144,10 @@
 - (JSValue *)callJSMethod:(NSString *)method args:(NSArray *)args
 {
     WXLogDebug(@"Calling JS... method:%@, args:%@", method, args);
-//    __checkMutable(args);
+    WXPerformBlockOnMainThread(^{
+        [[WXBridgeManager sharedManager].lastMethodInfo setObject:method ?: @"" forKey:@"method"];
+        [[WXBridgeManager sharedManager].lastMethodInfo setObject:args ?: @[] forKey:@"args"];
+    });
     return [[_jsContext globalObject] invokeMethod:method withArguments:args];
 }
 
@@ -396,7 +401,7 @@
 
 - (void)resetEnvironment
 {
-    NSDictionary *data = [WXUtility getEnvironment];
+    NSDictionary *data = [WXUtility getEnvironmentForJSContext];
     _jsContext[@"WXEnvironment"] = data;
 }
 
diff --git a/ios/sdk/WeexSDK/Sources/Component/RecycleList/WXJSASTParser.mm b/ios/sdk/WeexSDK/Sources/Component/RecycleList/WXJSASTParser.mm
index cfea370..2d26ff0 100644
--- a/ios/sdk/WeexSDK/Sources/Component/RecycleList/WXJSASTParser.mm
+++ b/ios/sdk/WeexSDK/Sources/Component/RecycleList/WXJSASTParser.mm
@@ -760,7 +760,7 @@
 
 - (WXJSExpression *)parsePrimaryExpression
 {
-    int type = _lookahead->type;
+    WXJSTokenType type = _lookahead->type;
     
     if (type == WXJSTokenTypePunctuator) {
         if (_lookahead->value == "[") {
diff --git a/ios/sdk/WeexSDK/Sources/Component/WXComponent_internal.h b/ios/sdk/WeexSDK/Sources/Component/WXComponent_internal.h
index c58a796..dee6a8c 100644
--- a/ios/sdk/WeexSDK/Sources/Component/WXComponent_internal.h
+++ b/ios/sdk/WeexSDK/Sources/Component/WXComponent_internal.h
@@ -49,8 +49,12 @@
     /**
      *  View
      */
-    UIColor *_backgroundColor;
+    UIColor *_styleBackgroundColor;
+    UIColor *_darkSchemeBackgroundColor;
+    UIColor *_lightSchemeBackgroundColor;
     NSString *_backgroundImage;
+    NSString *_darkSchemeBackgroundImage;
+    NSString *_lightSchemeBackgroundImage;
     NSString *_clipRadius;
     WXClipType _clipToBounds;
     UIView *_view;
@@ -59,6 +63,8 @@
     WXBoxShadow *_originalBoxShadow;
     WXBoxShadow *_lastBoxShadow;
     WXBoxShadow *_boxShadow;
+    WXBoxShadow *_darkSchemeBoxShadow;
+    WXBoxShadow *_lightSchemeBoxShadow;
     
     /**
      * accessibility support
@@ -115,9 +121,17 @@
     WXThreadSafeCounter *_displayCounter;
     
     UIColor *_borderTopColor;
+    UIColor *_darkSchemeBorderTopColor;
+    UIColor *_lightSchemeBorderTopColor;
     UIColor *_borderRightColor;
+    UIColor *_darkSchemeBorderRightColor;
+    UIColor *_lightSchemeBorderRightColor;
     UIColor *_borderLeftColor;
+    UIColor *_darkSchemeBorderLeftColor;
+    UIColor *_lightSchemeBorderLeftColor;
     UIColor *_borderBottomColor;
+    UIColor *_darkSchemeBorderBottomColor;
+    UIColor *_lightSchemeBorderBottomColor;
     
     CGFloat _borderTopWidth;
     CGFloat _borderRightWidth;
@@ -170,11 +184,18 @@
     NSMutableDictionary<NSString *, NSArray *> *_eventParameters;
 }
 
-/* _transform may be modified in mutiple threads. DO NOT use "_transform = XXX" directly.
+/* DO NOT use "_transform = XXX" directly.
  Ivar access in ObjC is compiled to code with additional release or retain. So use Ivar in mutiple
  thread may lead to crash. Use an ATOMIC property is well enough. */
 @property (atomic, strong) WXTransform *transform;
 
+/**
+ DO NOT use "_backgroundColor" directly. The same reason as '_transform'.
+ */
+@property (atomic, strong) UIColor* styleBackgroundColor;
+@property (atomic, strong) UIColor* darkSchemeBackgroundColor;
+@property (atomic, strong) UIColor* lightSchemeBackgroundColor;
+
 ///--------------------------------------
 /// @name Package Internal Methods
 ///--------------------------------------
@@ -296,4 +317,6 @@
 
 - (BOOL)_isAffineTypeAs:(NSString *)type;
 
+- (WXBoxShadow*)_chooseBoxShadow;
+
 @end
diff --git a/ios/sdk/WeexSDK/Sources/Component/WXCycleSliderComponent.mm b/ios/sdk/WeexSDK/Sources/Component/WXCycleSliderComponent.mm
index 865778c..5519de8 100644
--- a/ios/sdk/WeexSDK/Sources/Component/WXCycleSliderComponent.mm
+++ b/ios/sdk/WeexSDK/Sources/Component/WXCycleSliderComponent.mm
@@ -364,12 +364,24 @@
 }
 
 - (void)scrollViewDidEndScrollingAnimation:(UIScrollView *)scrollView {
+    /* In this case, we forbid animation temporarily so that
+     setContentOffset in setCurrentIndex won't cause endless loop
+     on some devices.
+     We have to use _forbidSlideAnimation in setCurrentIndex because
+     sometimes JS will trigger the slider to slide to some posistion
+     with animation.
+     */
+    BOOL oldValue = _forbidSlideAnimation;
+    _forbidSlideAnimation = YES;
+    
     if (_infinite) {
         [self resetScrollView];
     } else {
         NSInteger index = _scrollView.contentOffset.x / self.width;
         [self setCurrentIndex:index];
     }
+        
+    _forbidSlideAnimation = oldValue;
 }
 
 @end
diff --git a/ios/sdk/WeexSDK/Sources/Component/WXImageComponent.m b/ios/sdk/WeexSDK/Sources/Component/WXImageComponent.m
index 1cb8245..54700e0 100644
--- a/ios/sdk/WeexSDK/Sources/Component/WXImageComponent.m
+++ b/ios/sdk/WeexSDK/Sources/Component/WXImageComponent.m
@@ -53,14 +53,16 @@
 
 @interface WXImageComponent ()
 {
-    NSString * _imageSrc;
-    pthread_mutex_t _imageSrcMutex;
-    pthread_mutexattr_t _propertMutexAttr;
     BOOL _shouldUpdateImage;
     BOOL _mainImageSuccess;
 }
 
+@property (atomic, strong) NSString *src;
+@property (atomic, strong) NSString *darkSchemeSrc;
+@property (atomic, strong) NSString *lightSchemeSrc;
 @property (atomic, strong) NSString *placeholdSrc;
+@property (atomic, strong) NSString *darkSchemePlaceholderSrc;
+@property (atomic, strong) NSString *lightSchemePlaceholderSrc;
 @property (nonatomic, assign) CGFloat blurRadius;
 @property (nonatomic, assign) UIViewContentMode resizeMode;
 @property (nonatomic, assign) WXImageQuality imageQuality;
@@ -71,7 +73,7 @@
 @property (nonatomic) BOOL imageLoadEvent;
 @property (nonatomic) BOOL imageDownloadFinish;
 @property (nonatomic) BOOL downloadImageWithURL;
-@property (nonatomic ,strong) NSString* preUrl;
+@property (nonatomic, strong) NSString* preUrl;
 
 @end
 
@@ -88,17 +90,18 @@
             WXImageUpdateQueue = dispatch_queue_create("com.taobao.weex.ImageUpdateQueue", DISPATCH_QUEUE_SERIAL);
         }
         
-        pthread_mutexattr_init(&(_propertMutexAttr));
-        pthread_mutexattr_settype(&(_propertMutexAttr), PTHREAD_MUTEX_RECURSIVE);
-        pthread_mutex_init(&(_imageSrcMutex), &(_propertMutexAttr));
-        
         if (attributes[@"src"]) {
-             pthread_mutex_lock(&(_imageSrcMutex));
-            _imageSrc = [[WXConvert NSString:attributes[@"src"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
-             pthread_mutex_unlock(&(_imageSrcMutex));
+            self.src = [[WXConvert NSString:attributes[@"src"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
         } else {
             WXLogWarning(@"image src is nil");
         }
+        if (attributes[@"darkSchemeSrc"]) {
+            self.darkSchemeSrc = [[WXConvert NSString:attributes[@"darkSchemeSrc"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
+        }
+        if (attributes[@"lightSchemeSrc"]) {
+            self.lightSchemeSrc = [[WXConvert NSString:attributes[@"lightSchemeSrc"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
+        }
+        
         [self configPlaceHolder:attributes];
         
         NSString *resizeMode = attributes[@"resize"];
@@ -135,6 +138,12 @@
     if (attributes[@"placeHolder"] || attributes[@"placeholder"]) {
         self.placeholdSrc = [[WXConvert NSString:attributes[@"placeHolder"]?:attributes[@"placeholder"]]stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
     }
+    if (attributes[@"darkSchemePlaceholder"]) {
+        self.darkSchemePlaceholderSrc = [[WXConvert NSString:attributes[@"darkSchemePlaceholder"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
+    }
+    if (attributes[@"lightSchemePlaceholder"]) {
+        self.lightSchemePlaceholderSrc = [[WXConvert NSString:attributes[@"lightSchemePlaceholder"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
+    }
 }
 
 - (void)configFilter:(NSDictionary *)styles needUpdate:(BOOL)needUpdate
@@ -258,12 +267,16 @@
 - (void)dealloc
 {
     [self cancelImage];
-    pthread_mutex_destroy(&(_imageSrcMutex));
-    pthread_mutexattr_destroy(&_propertMutexAttr);
 }
 
 - (void)updateAttributes:(NSDictionary *)attributes
 {
+    if (attributes[@"darkSchemeSrc"]) {
+        self.darkSchemeSrc = [[WXConvert NSString:attributes[@"darkSchemeSrc"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
+    }
+    if (attributes[@"lightSchemeSrc"]) {
+        self.lightSchemeSrc = [[WXConvert NSString:attributes[@"lightSchemeSrc"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
+    }
     if (attributes[@"src"]) {
         [self setImageSrc:[[WXConvert NSString:attributes[@"src"]] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]]];
     }
@@ -293,7 +306,17 @@
     [self _clipsToBounds];
     
     [self updateImage];
-    
+}
+
+- (void)schemeDidChange:(NSString*)scheme
+{
+    [super schemeDidChange:scheme];
+    if (_view) {
+        if (self.darkSchemeSrc || self.darkSchemePlaceholderSrc ||
+            self.lightSchemeSrc || self.lightSchemePlaceholderSrc) {
+            [self updateImage];
+        }
+    }
 }
 
 - (BOOL)_needsDrawBorder
@@ -358,26 +381,15 @@
     }
 }
 
-- (NSString *)imageSrc
-{
-    pthread_mutex_lock(&(_imageSrcMutex));
-    NSString * imageSrcCpy = [_imageSrc copy];
-    pthread_mutex_unlock(&(_imageSrcMutex));
-    
-    return imageSrcCpy;
-}
-
 - (void)setImageSrc:(NSString*)src
 {
-    if ([src isEqualToString:_imageSrc]) {
+    if ([src isEqualToString:self.src]) {
         // if image src is equal to then ignore it.
         return;
     }
-    pthread_mutex_lock(&(_imageSrcMutex));
-    _imageSrc = src;
+    self.src = src;
     _imageDownloadFinish = NO;
     ((UIImageView*)self.view).image = nil;
-    pthread_mutex_unlock(&(_imageSrcMutex));
     
     [self updateImage];
 }
@@ -391,20 +403,42 @@
     }
 }
 
+- (NSString*)chooseImage:(NSString*)src lightSrc:(NSString*)lightSrc darkSrc:(NSString*)darkSrc
+{
+    if ([self.weexInstance isDarkScheme]) {
+        if (darkSrc) {
+            return darkSrc;
+        }
+        else {
+            return src;
+        }
+    }
+    else if (lightSrc) {
+        return lightSrc;
+    }
+    else {
+        return src;
+    }
+}
+
 - (void)updateImage
 {
     if (CGSizeEqualToSize(_view.frame.size, CGSizeZero)) {
         _shouldUpdateImage = YES;
         return;
     }
+    
+    NSString* choosedSrc = [self chooseImage:self.src lightSrc:self.lightSchemeSrc darkSrc:self.darkSchemeSrc];
+    NSString* choosedPlaceholder = [self chooseImage:self.placeholdSrc lightSrc:self.lightSchemePlaceholderSrc darkSrc:self.darkSchemePlaceholderSrc];
+    
     __weak typeof(self) weakSelf = self;
     if (_downloadImageWithURL && [[self imageLoader] respondsToSelector:@selector(setImageViewWithURL:url:placeholderImage:options:progress:completed:)]) {
         _mainImageSuccess = NO;
         
         NSString *newURL = nil;
-        if (self.placeholdSrc) {
-            newURL = [self.placeholdSrc copy];
-            WX_REWRITE_URL([self placeholdSrc], WXResourceTypeImage, self.weexInstance)
+        if (choosedPlaceholder) {
+            newURL = [choosedPlaceholder copy];
+            WX_REWRITE_URL(choosedPlaceholder, WXResourceTypeImage, self.weexInstance)
             NSDictionary* extInfo = @{@"instanceId":[self _safeInstanceId], @"pageURL": self.weexInstance.scriptURL ?: @""};
             [[self imageLoader] setImageViewWithURL:(UIImageView*)self.view url:[NSURL URLWithString:newURL] placeholderImage:nil options:extInfo progress:nil completed:^(UIImage *image, NSError *error, WXImageLoaderCacheType cacheType, NSURL *imageURL) {
                 /* We cannot rely on image library even if we call setImage with placeholer before calling setImage with real url.
@@ -414,8 +448,8 @@
                     UIImageView *imageView = (UIImageView *)strongSelf.view;
                     if (imageView && imageView.image == image && strongSelf->_mainImageSuccess) {
                         // reload image with main image url
-                        NSString* newURL = [[strongSelf imageSrc] copy];
-                        WX_REWRITE_URL([strongSelf imageSrc], WXResourceTypeImage, strongSelf.weexInstance)
+                        NSString* newURL = [choosedSrc copy];
+                        WX_REWRITE_URL(choosedSrc, WXResourceTypeImage, strongSelf.weexInstance)
                         NSDictionary *userInfo = @{@"imageQuality":@(strongSelf.imageQuality), @"imageSharp":@(strongSelf.imageSharp),  @"blurRadius":@(strongSelf.blurRadius), @"instanceId":[strongSelf _safeInstanceId], @"pageURL": strongSelf.weexInstance.scriptURL ?: @""};
                         [[strongSelf imageLoader] setImageViewWithURL:imageView url:[NSURL URLWithString:newURL] placeholderImage:nil options:userInfo progress:nil completed:^(UIImage *image, NSError *error, WXImageLoaderCacheType cacheType, NSURL *imageURL) {
                             WXLogInfo(@"Image re-requested because placeholder may override main image. %@", imageURL);
@@ -424,11 +458,11 @@
                 }
             }];
         }
-        newURL = [[self imageSrc] copy];
+        newURL = [choosedSrc copy];
         if ([newURL length] == 0) {
             return;
         }
-        WX_REWRITE_URL([self imageSrc], WXResourceTypeImage, self.weexInstance)
+        WX_REWRITE_URL(choosedSrc, WXResourceTypeImage, self.weexInstance)
         NSDictionary *userInfo = @{@"imageQuality":@(self.imageQuality), @"imageSharp":@(self.imageSharp),  @"blurRadius":@(self.blurRadius), @"instanceId":[self _safeInstanceId], @"pageURL": self.weexInstance.scriptURL ?: @""};
         [[self imageLoader] setImageViewWithURL:(UIImageView*)self.view url:[NSURL URLWithString:newURL] placeholderImage:nil options:userInfo progress:^(NSInteger receivedSize, NSInteger expectedSize) {
             // progress when loading image
@@ -444,9 +478,9 @@
                 WXLogError(@"Error downloading image: %@, detail:%@", imageURL.absoluteString, [error localizedDescription]);
                 
                 // retry set placeholder, maybe placeholer image can be downloaded
-                if (strongSelf.placeholdSrc) {
-                    NSString *newURL = [strongSelf.placeholdSrc copy];
-                    WX_REWRITE_URL([strongSelf placeholdSrc], WXResourceTypeImage, strongSelf.weexInstance)
+                if (choosedPlaceholder) {
+                    NSString *newURL = [choosedPlaceholder copy];
+                    WX_REWRITE_URL(choosedPlaceholder, WXResourceTypeImage, strongSelf.weexInstance)
                     [[strongSelf imageLoader] setImageViewWithURL:(UIImageView*)strongSelf.view
                                                               url:[NSURL URLWithString:newURL]
                                                  placeholderImage:nil
@@ -513,7 +547,7 @@
             [strongSelf updatePlaceHolderWithFailedBlock:downloadFailed];
             [strongSelf updateContentImageWithFailedBlock:downloadFailed];
 
-            if (!strongSelf.imageSrc && !strongSelf.placeholdSrc) {
+            if (!choosedSrc && !choosedPlaceholder) {
                 dispatch_async(dispatch_get_main_queue(), ^{
                     strongSelf.layer.contents = nil;
                     strongSelf.imageDownloadFinish = YES;
@@ -526,15 +560,15 @@
 
 - (void)updatePlaceHolderWithFailedBlock:(void(^)(NSString *, NSError *))downloadFailedBlock
 {
-    NSString *placeholderSrc = self.placeholdSrc;
+    NSString* choosedPlaceholder = [self chooseImage:self.placeholdSrc lightSrc:self.lightSchemePlaceholderSrc darkSrc:self.darkSchemePlaceholderSrc];
     
-    if ([WXUtility isBlankString:placeholderSrc]) {
+    if ([WXUtility isBlankString:choosedPlaceholder]) {
         return;
     }
     
-    WXLogDebug(@"Updating image, component:%@, placeholder:%@ ", self.ref, placeholderSrc);
-    NSString *newURL = [self.placeholdSrc copy];
-    WX_REWRITE_URL(self.placeholdSrc, WXResourceTypeImage, self.weexInstance)
+    WXLogDebug(@"Updating image, component:%@, placeholder:%@ ", self.ref, choosedPlaceholder);
+    NSString *newURL = [choosedPlaceholder copy];
+    WX_REWRITE_URL(choosedPlaceholder, WXResourceTypeImage, self.weexInstance)
     
     __weak typeof(self) weakSelf = self;
     self.placeholderOperation = [[self imageLoader] downloadImageWithURL:newURL imageFrame:self.calculatedFrame
@@ -543,16 +577,21 @@
     {
         dispatch_async(dispatch_get_main_queue(), ^{
             __strong typeof(self) strongSelf = weakSelf;
+            if (strongSelf == nil) {
+                return;
+            }
             UIImage *viewImage = ((UIImageView *)strongSelf.view).image;
             if (error) {
-                downloadFailedBlock(placeholderSrc,error);
+                downloadFailedBlock(choosedPlaceholder, error);
                 if ([strongSelf isViewLoaded] && !viewImage) {
                     ((UIImageView *)(strongSelf.view)).image = nil;
                     [strongSelf readyToRender];
                 }
                 return;
             }
-            if (![placeholderSrc isEqualToString:strongSelf.placeholdSrc]) {
+            
+            NSString* currentPlaceholder = [strongSelf chooseImage:strongSelf.placeholdSrc lightSrc:strongSelf.lightSchemePlaceholderSrc darkSrc:strongSelf.darkSchemePlaceholderSrc];
+            if (![choosedPlaceholder isEqualToString:currentPlaceholder]) {
                 return;
             }
             
@@ -570,20 +609,24 @@
 
 - (void)updateContentImageWithFailedBlock:(void(^)(NSString *, NSError *))downloadFailedBlock
 {
-    NSString *imageSrc = [NSString stringWithFormat:@"%@", self.imageSrc?:@""];
-    if ([WXUtility isBlankString:imageSrc]) {
+    NSString* choosedSrc = [self chooseImage:self.src lightSrc:self.lightSchemeSrc darkSrc:self.darkSchemeSrc];
+    
+    if ([WXUtility isBlankString:choosedSrc]) {
         WXLogError(@"image src is empty");
         return;
     }
     
-    WXLogDebug(@"Updating image:%@, component:%@", self.imageSrc, self.ref);
+    WXLogDebug(@"Updating image:%@, component:%@", choosedSrc, self.ref);
     NSDictionary *userInfo = @{@"imageQuality":@(self.imageQuality), @"imageSharp":@(self.imageSharp), @"blurRadius":@(self.blurRadius), @"instanceId":[self _safeInstanceId], @"pageURL": self.weexInstance.scriptURL ?: @""};
-    NSString * newURL = [imageSrc copy];
-    WX_REWRITE_URL(imageSrc, WXResourceTypeImage, self.weexInstance)
+    NSString * newURL = [choosedSrc copy];
+    WX_REWRITE_URL(choosedSrc, WXResourceTypeImage, self.weexInstance)
     __weak typeof(self) weakSelf = self;
     weakSelf.imageOperation = [[weakSelf imageLoader] downloadImageWithURL:newURL imageFrame:weakSelf.calculatedFrame userInfo:userInfo completed:^(UIImage *image, NSError *error, BOOL finished) {
         dispatch_async(dispatch_get_main_queue(), ^{
             __strong typeof(self) strongSelf = weakSelf;
+            if (strongSelf == nil) {
+                return;
+            }
             
             if (strongSelf.imageLoadEvent) {
                 NSMutableDictionary *sizeDict = [NSMutableDictionary new];
@@ -598,12 +641,13 @@
                 [strongSelf fireEvent:@"load" params:@{ @"success": error? @false : @true,@"size":sizeDict}];
             }
             if (error) {
-                downloadFailedBlock(imageSrc, error);
+                downloadFailedBlock(choosedSrc, error);
                 [strongSelf readyToRender];
                 return ;
             }
             
-            if (![imageSrc isEqualToString:strongSelf.imageSrc]) {
+            NSString* currentSrc = [strongSelf chooseImage:strongSelf.src lightSrc:strongSelf.lightSchemeSrc darkSrc:strongSelf.darkSchemeSrc];
+            if (![choosedSrc isEqualToString:currentSrc]) {
                 return ;
             }
             
diff --git a/ios/sdk/WeexSDK/Sources/Component/WXRichText.mm b/ios/sdk/WeexSDK/Sources/Component/WXRichText.mm
index 8ffeaf3..d007d60 100644
--- a/ios/sdk/WeexSDK/Sources/Component/WXRichText.mm
+++ b/ios/sdk/WeexSDK/Sources/Component/WXRichText.mm
@@ -27,6 +27,7 @@
 #import "WXImgLoaderProtocol.h"
 #import "WXComponentManager.h"
 #import "WXLog.h"
+#import "WXDarkSchemeProtocol.h"
 #include <pthread/pthread.h>
 
 @interface WXRichNode : NSObject
@@ -35,7 +36,11 @@
 @property (nonatomic, strong) NSString  *ref;
 @property (nonatomic, strong) NSString  *text;
 @property (nonatomic, strong) UIColor   *color;
+@property (nonatomic, strong) UIColor   *darkSchemeColor;
+@property (nonatomic, strong) UIColor   *lightSchemeColor;
 @property (nonatomic, strong) UIColor   *backgroundColor;
+@property (nonatomic, strong) UIColor   *darkSchemeBackgroundColor;
+@property (nonatomic, strong) UIColor   *lightSchemeBackgroundColor;
 @property (nonatomic, strong) NSString  *fontFamily;
 @property (nonatomic, assign) CGFloat   fontSize;
 @property (nonatomic, assign) CGFloat   fontWeight;
@@ -91,7 +96,9 @@
     id value = styles[@#key]; \
     if (value) { \
         node.key = [WXConvert type:value];\
-    } else if (!([@#key isEqualToString:@"backgroundColor"] || [@#key isEqualToString:@"textDecoration"]) && superNode.key ) { \
+    } else if (!([@#key isEqualToString:@"backgroundColor"] || \
+        [@#key isEqualToString:@"weexDarkSchemeBackgroundColor"] || \
+        [@#key isEqualToString:@"textDecoration"]) && superNode.key ) { \
         node.key = superNode.key; \
     } \
 } while(0);
@@ -183,14 +190,18 @@
             [self recursivelyAddChildNode:dict toSuperNode:rootNode];
         }
         
-        _backgroundColor = rootNode.backgroundColor?:[UIColor whiteColor];
+        _backgroundColor = rootNode.backgroundColor?:[UIColor clearColor];
     }
 }
 
 - (void)fillCSSStyles:(NSDictionary *)styles toNode:(WXRichNode *)node superNode:(WXRichNode *)superNode
 {
     WX_STYLE_FILL_RICHTEXT(color, UIColor)
+    WX_STYLE_FILL_RICHTEXT(darkSchemeColor, UIColor)
+    WX_STYLE_FILL_RICHTEXT(lightSchemeColor, UIColor)
     WX_STYLE_FILL_RICHTEXT(backgroundColor, UIColor)
+    WX_STYLE_FILL_RICHTEXT(darkSchemeBackgroundColor, UIColor)
+    WX_STYLE_FILL_RICHTEXT(lightSchemeBackgroundColor, UIColor)
     WX_STYLE_FILL_RICHTEXT(fontFamily, NSString)
     WX_STYLE_FILL_RICHTEXT_PIXEL(fontSize)
     WX_STYLE_FILL_RICHTEXT(fontWeight, WXTextWeight)
@@ -308,7 +319,7 @@
         if (_styles) {
             [self fillCSSStyles:_styles toNode:rootNode superNode:nil];
         }
-        _backgroundColor = rootNode.backgroundColor?:[UIColor whiteColor];
+        _backgroundColor = rootNode.backgroundColor?:[UIColor clearColor];
     }
 
     WXRichNode* superNode = [self findRichNode:@"_root"];
@@ -421,6 +432,20 @@
     };
 }
 
+- (void)schemeDidChange:(NSString*)scheme
+{
+    [super schemeDidChange:scheme];
+    if ([self isViewLoaded]) {
+        // Force inner layout
+        [self innerLayout];
+    }
+}
+
+- (WXColorScene)colorSceneType
+{
+    return WXColorSceneText;
+}
+
 #pragma mark Text Building
 
 - (NSMutableAttributedString *)buildAttributeString
@@ -434,6 +459,16 @@
     NSMutableAttributedString *attrStr = [[NSMutableAttributedString alloc] init];
     NSUInteger location;
     
+    BOOL invert = self.invertForDarkScheme;
+    
+    // Invert default background color.
+    UIColor* defaultTextColor = [UIColor blackColor];
+    UIColor* defaultBackgroundColor = _backgroundColor;
+    if (invert && [self.weexInstance isDarkScheme]) {
+        defaultTextColor = [[WXSDKInstance darkSchemeColorHandler] getInvertedColorFor:[UIColor blackColor] ofScene:[self colorSceneType] withDefault:[UIColor blackColor]];
+        defaultBackgroundColor = [[WXSDKInstance darkSchemeColorHandler] getInvertedColorFor:_backgroundColor ofScene:[self colorSceneType] withDefault:_backgroundColor];
+    }
+    
     __weak typeof(self) weakSelf = self;
     for (WXRichNode *node in array) {
         location = attrStr.length;
@@ -444,8 +479,10 @@
                 [attrStr.mutableString appendString:text];
                 
                 NSRange range = NSMakeRange(location, text.length);
-                [attrStr addAttribute:NSForegroundColorAttributeName value:node.color ?: [UIColor blackColor] range:range];
-                [attrStr addAttribute:NSBackgroundColorAttributeName value:node.backgroundColor ?: _backgroundColor range:range];
+                UIColor* textColor = [self.weexInstance chooseColor:node.color lightSchemeColor:node.lightSchemeColor darkSchemeColor:node.darkSchemeColor invert:invert scene:[self colorSceneType]];
+                UIColor* bgColor = [self.weexInstance chooseColor:node.backgroundColor lightSchemeColor:node.lightSchemeBackgroundColor darkSchemeColor:node.darkSchemeBackgroundColor invert:invert scene:[self colorSceneType]];
+                [attrStr addAttribute:NSForegroundColorAttributeName value:textColor ?: defaultTextColor range:range];
+                [attrStr addAttribute:NSBackgroundColorAttributeName value:bgColor ?: defaultBackgroundColor range:range];
                 
                 UIFont *font = [WXUtility fontWithSize:node.fontSize textWeight:node.fontWeight textStyle:WXTextStyleNormal fontFamily:node.fontFamily scaleFactor:self.weexInstance.pixelScaleFactor];
                 if (font) {
diff --git a/ios/sdk/WeexSDK/Sources/Component/WXScrollerComponent.mm b/ios/sdk/WeexSDK/Sources/Component/WXScrollerComponent.mm
index 4d3f4c9..981a7af 100644
--- a/ios/sdk/WeexSDK/Sources/Component/WXScrollerComponent.mm
+++ b/ios/sdk/WeexSDK/Sources/Component/WXScrollerComponent.mm
@@ -1152,6 +1152,11 @@
             _flexCssNode->calculateLayout(renderPageSize);
             _flexCssNode->setParent(parent, _flexCssNode);
             
+            /* We must clear BFCs becuase we have set parent of _flexCSSNode to nullptr and
+             manually called its calculateLayout method. This will cause a non-bfc layout node
+             to have items in its BFCs vector. Later, a wild pointer may cause crash. */
+            _flexCssNode->clearBFCs();
+            
             // set origin and size back
             _flexCssNode->rewriteLayoutResult(left, top, width, height);
         }
diff --git a/ios/sdk/WeexSDK/Sources/Component/WXTextComponent.mm b/ios/sdk/WeexSDK/Sources/Component/WXTextComponent.mm
index a796b49..c937680 100644
--- a/ios/sdk/WeexSDK/Sources/Component/WXTextComponent.mm
+++ b/ios/sdk/WeexSDK/Sources/Component/WXTextComponent.mm
@@ -119,7 +119,10 @@
 static CGFloat WXTextDefaultLineThroughWidth = 1.2;
 
 @interface WXTextComponent()
-@property (nonatomic, strong) NSString *useCoreTextAttr;
+@property (atomic, strong) NSString *fontFamily;
+@property (atomic, strong) UIColor *textColor;
+@property (atomic, strong) UIColor *darkSchemeTextColor;
+@property (atomic, strong) UIColor *lightSchemeTextColor;
 @end
 
 @implementation WXTextComponent
@@ -128,8 +131,6 @@
     UIEdgeInsets _padding;
     NSTextStorage *_textStorage;
     float _textStorageWidth;
-    float _color[4];
-    NSString *_fontFamily;
     float _fontSize;
     float _fontWeight;
     WXTextStyle _fontStyle;
@@ -150,6 +151,8 @@
     pthread_mutexattr_t _propertMutexAttr;
     BOOL _observerIconfont;
     BOOL _enableCopy;
+    
+    BOOL _useCoreText;
 }
 
 - (instancetype)initWithRef:(NSString *)ref
@@ -169,12 +172,10 @@
         _textAlign = NSTextAlignmentNatural;
         
         if ([attributes objectForKey:@"coretext"]) {
-            _useCoreTextAttr = [WXConvert NSString:attributes[@"coretext"]];
+            _useCoreText = [WXConvert BOOL:attributes[@"coretext"]];
         } else {
-            _useCoreTextAttr = nil;
+            _useCoreText = YES;
         }
-        
-        _color[0] = -1.0;
 
         [self fillCSSStyles:styles];
         [self fillAttributes:attributes];
@@ -185,18 +186,12 @@
 
 - (BOOL)useCoreText
 {
-    if ([_useCoreTextAttr isEqualToString:@"true"]) {
-        return YES;
-    }
-    if ([_useCoreTextAttr isEqualToString:@"false"]) {
-        return NO;
-    }
-    return YES;
+    return _useCoreText;
 }
 
 - (void)dealloc
 {
-    if (_fontFamily && _observerIconfont) {
+    if (self.fontFamily && _observerIconfont) {
         [[NSNotificationCenter defaultCenter] removeObserver:self name:WX_ICONFONT_DOWNLOAD_NOTIFICATION object:nil];
     }
     pthread_mutex_destroy(&_ctAttributedStringMutex);
@@ -246,7 +241,15 @@
 
 - (void)fillCSSStyles:(NSDictionary *)styles
 {
-    WX_STYLE_FILL_TEXT(fontFamily, fontFamily, NSString, YES) //!OCLint
+    do {
+        id value = styles[@"fontFamily"];
+        if (value) {
+            self.fontFamily = [WXConvert NSString:value];
+            [self setNeedsRepaint];
+            [self setNeedsLayout];
+        }
+    } while(0);
+    
     WX_STYLE_FILL_TEXT_PIXEL(fontSize, fontSize, YES) //!OCLint
     WX_STYLE_FILL_TEXT(fontWeight, fontWeight, WXTextWeight, YES) //!OCLint
     WX_STYLE_FILL_TEXT(fontStyle, fontStyle, WXTextStyle, YES) //!OCLint
@@ -258,26 +261,58 @@
     WX_STYLE_FILL_TEXT_PIXEL(letterSpacing, letterSpacing, YES) //!OCLint
     WX_STYLE_FILL_TEXT(wordWrap, wordWrap, NSString, YES); //!OCLint
 
-    UIColor* color = nil;
-    id value = styles[@"color"];
-    if (value) {
-        if([WXUtility isBlankString:value]){
-            color = [UIColor blackColor];
-        } else {
-            color = [WXConvert UIColor:value];
+    do {
+        UIColor* color = nil;
+        id value = styles[@"color"];
+        if (value) {
+            if([WXUtility isBlankString:value]){
+                color = [UIColor blackColor];
+            } else {
+                color = [WXConvert UIColor:value];
+            }
+            if (color) {
+                self.textColor = color;
+                [self setNeedsRepaint];
+            }
         }
-        if (color) {
-            [self setNeedsRepaint];
-            CGFloat red, green, blue, alpha;
-            [color getRed:&red green:&green blue:&blue alpha:&alpha];
-            _color[0] = red;
-            _color[1] = green;
-            _color[2] = blue;
-            _color[3] = alpha;
+        if (self.textColor == nil) {
+            self.textColor = [UIColor blackColor];
         }
-    }
+    } while (0);
 
-    if (_fontFamily && !_observerIconfont) {
+    do {
+        UIColor* color = nil;
+        id value = styles[@"weexDarkSchemeColor"];
+        if (value) {
+            if([WXUtility isBlankString:value]){
+                color = [UIColor blackColor];
+            } else {
+                color = [WXConvert UIColor:value];
+            }
+            if (color) {
+                self.darkSchemeTextColor = color;
+                [self setNeedsRepaint];
+            }
+        }
+    } while (0);
+    
+    do {
+        UIColor* color = nil;
+        id value = styles[@"weexLightSchemeColor"];
+        if (value) {
+            if([WXUtility isBlankString:value]){
+                color = [UIColor blackColor];
+            } else {
+                color = [WXConvert UIColor:value];
+            }
+            if (color) {
+                self.lightSchemeTextColor = color;
+                [self setNeedsRepaint];
+            }
+        }
+    } while (0);
+    
+    if (self.fontFamily && !_observerIconfont) {
         // notification received when custom icon font file download finish
         [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(repaintText:) name:WX_ICONFONT_DOWNLOAD_NOTIFICATION object:nil];
         _observerIconfont = YES;
@@ -368,6 +403,20 @@
     [self setNeedsRepaint];
 }
 
+- (void)schemeDidChange:(NSString*)scheme
+{
+    [self setNeedsRepaint];
+    [super schemeDidChange:scheme];
+    if (_view) {
+        [self setNeedsDisplay];
+    }
+}
+
+- (WXColorScene)colorSceneType
+{
+    return WXColorSceneText;
+}
+
 - (BOOL)needsDrawRect
 {
     return YES;
@@ -473,7 +522,7 @@
 
 - (void)repaintText:(NSNotification *)notification
 {
-    if (![_fontFamily isEqualToString:notification.userInfo[@"fontFamily"]]) {
+    if (![self.fontFamily isEqualToString:notification.userInfo[@"fontFamily"]]) {
         return;
     }
     [self setNeedsRepaint];
@@ -494,19 +543,20 @@
         string = @"";
     }
     NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString: string];
-    if (_color[0] >= 0) {
-        [attributedString addAttribute:NSForegroundColorAttributeName value:[UIColor colorWithRed:_color[0] green:_color[1] blue:_color[2] alpha:_color[3]] range:NSMakeRange(0, string.length)];
+    UIColor* textColor = [self.weexInstance chooseColor:self.textColor lightSchemeColor:self.lightSchemeTextColor darkSchemeColor:self.darkSchemeTextColor invert:self.invertForDarkScheme scene:[self colorSceneType]];
+    if (textColor) {
+        [attributedString addAttribute:NSForegroundColorAttributeName value:textColor range:NSMakeRange(0, string.length)];
     }
     
     // set font
-    UIFont *font = [WXUtility fontWithSize:_fontSize textWeight:_fontWeight textStyle:WXTextStyleNormal fontFamily:_fontFamily scaleFactor:self.weexInstance.pixelScaleFactor useCoreText:[self useCoreText]];
+    UIFont *font = [WXUtility fontWithSize:_fontSize textWeight:_fontWeight textStyle:WXTextStyleNormal fontFamily:self.fontFamily scaleFactor:self.weexInstance.pixelScaleFactor useCoreText:[self useCoreText]];
     CTFontRef ctFont;
     
     if (_fontStyle == WXTextStyleItalic) {
         CGAffineTransform matrix = CGAffineTransformMake(1, 0, tanf(16 * (CGFloat)M_PI / 180), 1, 0, 0);
-        ctFont = CTFontCreateWithName((__bridge CFStringRef)font.fontName, font.pointSize, &matrix);
+        ctFont = CTFontCreateWithFontDescriptor((__bridge CTFontDescriptorRef)font.fontDescriptor, font.pointSize, &matrix);
     }else {
-        ctFont = CTFontCreateWithName((__bridge CFStringRef)font.fontName, font.pointSize, NULL);
+        ctFont = CTFontCreateWithFontDescriptor((__bridge CTFontDescriptorRef)font.fontDescriptor, font.pointSize, NULL);
     }
     
     _fontAscender = font.ascender;
@@ -582,12 +632,13 @@
     NSMutableAttributedString *attributedString = [[NSMutableAttributedString alloc] initWithString:string];
     
     // set textColor
-    if (_color[0] >= 0) {
-        [attributedString addAttribute:NSForegroundColorAttributeName value:[UIColor colorWithRed:_color[0] green:_color[1] blue:_color[2] alpha:_color[3]] range:NSMakeRange(0, string.length)];
+    UIColor* textColor = [self.weexInstance chooseColor:self.textColor lightSchemeColor:self.lightSchemeTextColor darkSchemeColor:self.darkSchemeTextColor invert:self.invertForDarkScheme scene:[self colorSceneType]];
+    if (textColor) {
+        [attributedString addAttribute:NSForegroundColorAttributeName value:textColor range:NSMakeRange(0, string.length)];
     }
     
     // set font
-    UIFont *font = [WXUtility fontWithSize:_fontSize textWeight:_fontWeight textStyle:_fontStyle fontFamily:_fontFamily scaleFactor:self.weexInstance.pixelScaleFactor];
+    UIFont *font = [WXUtility fontWithSize:_fontSize textWeight:_fontWeight textStyle:_fontStyle fontFamily:self.fontFamily scaleFactor:self.weexInstance.pixelScaleFactor];
     if (font) {
         [attributedString addAttribute:NSFontAttributeName value:font range:NSMakeRange(0, string.length)];
     }
@@ -898,7 +949,7 @@
         CGFloat fontSize = font ? CTFontGetSize(font):32 * self.weexInstance.pixelScaleFactor;
         UIFont * uiFont = [UIFont systemFontOfSize:fontSize];
         if (uiFont) {
-            font = CTFontCreateWithName((__bridge CFStringRef)uiFont.fontName, uiFont.pointSize, NULL);
+            font = CTFontCreateWithFontDescriptor((__bridge CTFontDescriptorRef)uiFont.fontDescriptor, uiFont.pointSize, NULL);
         }
         if (font) {
             attrs[(id)kCTFontAttributeName] = (__bridge id)(font);
@@ -1109,10 +1160,15 @@
 {
     [super _resetCSSNodeStyles:styles];
     if ([styles containsObject:@"color"]) {
-        _color[0] = 0;
-        _color[1] = 0;
-        _color[2] = 0;
-        _color[3] = 1.0;
+        self.textColor = [UIColor blackColor];
+        [self setNeedsRepaint];
+    }
+    if ([styles containsObject:@"weexDarkSchemeColor"]) {
+        self.darkSchemeTextColor = nil;
+        [self setNeedsRepaint];
+    }
+    if ([styles containsObject:@"weexLightSchemeColor"]) {
+        self.lightSchemeTextColor = nil;
         [self setNeedsRepaint];
     }
     if ([styles containsObject:@"fontSize"]) {
diff --git a/ios/sdk/WeexSDK/Sources/Display/WXComponent+Display.m b/ios/sdk/WeexSDK/Sources/Display/WXComponent+Display.m
index 9acb010..2251731 100644
--- a/ios/sdk/WeexSDK/Sources/Display/WXComponent+Display.m
+++ b/ios/sdk/WeexSDK/Sources/Display/WXComponent+Display.m
@@ -20,6 +20,7 @@
 #import "WXComponent+Display.h"
 #import "WXComponent.h"
 #import "WXComponent_internal.h"
+#import "WXComponent+BoxShadow.h"
 #import "WXLayer.h"
 #import "WXAssert.h"
 #import "WXUtility.h"
@@ -28,6 +29,8 @@
 #import "UIBezierPath+Weex.h"
 #import "WXRoundedRect.h"
 #import "WXSDKInstance.h"
+#import "WXDarkSchemeProtocol.h"
+#import "WXHandlerFactory.h"
 
 #pragma clang diagnostic ignored "-Wobjc-protocol-method-implementation"
 
@@ -101,6 +104,35 @@
     WXAssertMainThread();
 }
 
+- (void)schemeDidChange:(NSString*)scheme
+{
+    WXAssertMainThread();
+    if (_view) {
+        if (![self _needsDrawBorder]) {
+            _layer.borderColor = [self.weexInstance chooseColor:_borderTopColor lightSchemeColor:_lightSchemeBorderTopColor darkSchemeColor:_darkSchemeBorderTopColor invert:self.invertForDarkScheme scene:[self colorSceneType]].CGColor;
+            _layer.backgroundColor = [self.weexInstance chooseColor:self.styleBackgroundColor lightSchemeColor:self.lightSchemeBackgroundColor darkSchemeColor:self.darkSchemeBackgroundColor invert:self.invertForDarkScheme scene:[self colorSceneType]].CGColor;
+        }
+        else {
+            [self setNeedsDisplay];
+        }
+        
+        if (_backgroundImage) {
+            [self setGradientLayer];
+        }
+        
+        WXBoxShadow* usingBoxShadow = [self _chooseBoxShadow];
+        if (usingBoxShadow) {
+            _lastBoxShadow = usingBoxShadow;
+            [self configBoxShadow:usingBoxShadow];
+        }
+    }
+}
+
+- (WXColorScene)colorSceneType
+{
+    return WXColorSceneUnknown;
+}
+
 #pragma mark Private
 
 - (WXDisplayBlock)_displayBlock
@@ -289,7 +321,7 @@
 - (void)_collectCompositingDisplayBlocks:(NSMutableArray *)displayBlocks context:(CGContextRef)context isCancelled:(BOOL(^)(void))isCancelled
 {
     // TODO: compositingChild has no chance to applyPropertiesToView, need update here?
-    UIColor *backgroundColor = _backgroundColor;
+    UIColor *backgroundColor = [self.weexInstance chooseColor:self.styleBackgroundColor lightSchemeColor:self.lightSchemeBackgroundColor darkSchemeColor:self.darkSchemeBackgroundColor invert:self.invertForDarkScheme scene:[self colorSceneType]];
     BOOL clipsToBounds = _clipToBounds;
     CGRect frame = self.calculatedFrame;
     CGRect bounds = CGRectMake(0, 0, frame.size.width, frame.size.height);
@@ -349,13 +381,21 @@
     
     CGContextSetAlpha(context, _opacity);
     // fill background color
-    if (_backgroundColor && CGColorGetAlpha(_backgroundColor.CGColor) > 0) {
-        CGContextSetFillColorWithColor(context, _backgroundColor.CGColor);
-        UIBezierPath *bezierPath = [UIBezierPath wx_bezierPathWithRoundedRect:rect topLeft:topLeft topRight:topRight bottomLeft:bottomLeft bottomRight:bottomRight];
-        [bezierPath fill];
-        WXPerformBlockOnMainThread(^{
-            _view.backgroundColor = UIColor.clearColor;
-        });
+    UIColor* bgColor = [self.weexInstance chooseColor:self.styleBackgroundColor lightSchemeColor:self.lightSchemeBackgroundColor darkSchemeColor:self.darkSchemeBackgroundColor invert:self.invertForDarkScheme scene:[self colorSceneType]];
+    
+    if (bgColor && [bgColor respondsToSelector:@selector(CGColor)]) {
+        if (CGColorGetAlpha(bgColor.CGColor) > 0) {
+            CGContextSetFillColorWithColor(context, bgColor.CGColor);
+            UIBezierPath *bezierPath = [UIBezierPath wx_bezierPathWithRoundedRect:rect topLeft:topLeft topRight:topRight bottomLeft:bottomLeft bottomRight:bottomRight];
+            [bezierPath fill];
+            __weak WXComponent* wself = self;
+            WXPerformBlockOnMainThread(^{
+                __strong WXComponent* sself = wself;
+                if (sself) {
+                    sself->_view.backgroundColor = UIColor.clearColor;
+                }
+            });
+        }
     }
     // Top
     if (_borderTopWidth > 0) {
@@ -367,7 +407,8 @@
             CGContextSetLineDash(context, 0, 0, 0);
         }
         CGContextSetLineWidth(context, _borderTopWidth);
-        CGContextSetStrokeColorWithColor(context, _borderTopColor.CGColor);
+        CGContextSetStrokeColorWithColor(context,
+                                         [self.weexInstance chooseColor:_borderTopColor lightSchemeColor:_lightSchemeBorderTopColor darkSchemeColor:_darkSchemeBorderTopColor invert:self.invertForDarkScheme scene:[self colorSceneType]].CGColor);
         CGContextAddArc(context, size.width-topRight, topRight, topRight-_borderTopWidth/2, -M_PI_4+(_borderRightWidth>0?0:M_PI_4), -M_PI_2, 1);
         CGContextMoveToPoint(context, size.width-topRight, _borderTopWidth/2);
         CGContextAddLineToPoint(context, topLeft, _borderTopWidth/2);
@@ -388,7 +429,8 @@
             CGContextSetLineDash(context, 0, 0, 0);
         }
         CGContextSetLineWidth(context, _borderLeftWidth);
-        CGContextSetStrokeColorWithColor(context, _borderLeftColor.CGColor);
+        CGContextSetStrokeColorWithColor(context,
+                                         [self.weexInstance chooseColor:_borderLeftColor lightSchemeColor:_lightSchemeBorderLeftColor darkSchemeColor:_darkSchemeBorderLeftColor invert:self.invertForDarkScheme scene:[self colorSceneType]].CGColor);
         CGContextAddArc(context, topLeft, topLeft, topLeft-_borderLeftWidth/2, -M_PI, -M_PI_2-M_PI_4+(_borderTopWidth > 0?0:M_PI_4), 0);
         CGContextMoveToPoint(context, _borderLeftWidth/2, topLeft);
         CGContextAddLineToPoint(context, _borderLeftWidth/2, size.height-bottomLeft);
@@ -409,7 +451,8 @@
             CGContextSetLineDash(context, 0, 0, 0);
         }
         CGContextSetLineWidth(context, _borderBottomWidth);
-        CGContextSetStrokeColorWithColor(context, _borderBottomColor.CGColor);
+        CGContextSetStrokeColorWithColor(context,
+                                         [self.weexInstance chooseColor:_borderBottomColor lightSchemeColor:_lightSchemeBorderBottomColor darkSchemeColor:_darkSchemeBorderBottomColor invert:self.invertForDarkScheme scene:[self colorSceneType]].CGColor);
         CGContextAddArc(context, bottomLeft, size.height-bottomLeft, bottomLeft-_borderBottomWidth/2, M_PI-M_PI_4+(_borderLeftWidth>0?0:M_PI_4), M_PI_2, 1);
         CGContextMoveToPoint(context, bottomLeft, size.height-_borderBottomWidth/2);
         CGContextAddLineToPoint(context, size.width-bottomRight, size.height-_borderBottomWidth/2);
@@ -430,7 +473,8 @@
             CGContextSetLineDash(context, 0, 0, 0);
         }
         CGContextSetLineWidth(context, _borderRightWidth);
-        CGContextSetStrokeColorWithColor(context, _borderRightColor.CGColor);
+        CGContextSetStrokeColorWithColor(context,
+                                         [self.weexInstance chooseColor:_borderRightColor lightSchemeColor:_lightSchemeBorderRightColor darkSchemeColor:_darkSchemeBorderRightColor invert:self.invertForDarkScheme scene:[self colorSceneType]].CGColor);
         CGContextAddArc(context, size.width-bottomRight, size.height-bottomRight, bottomRight-_borderRightWidth/2, M_PI_4+(_borderBottomWidth>0?0:M_PI_4), 0, 1);
         CGContextMoveToPoint(context, size.width-_borderRightWidth/2, size.height-bottomRight);
         CGContextAddLineToPoint(context, size.width-_borderRightWidth/2, topRight);
@@ -486,7 +530,17 @@
     if (!radiusEqual) {
         return YES;
     }
-    BOOL colorEqual = [_borderTopColor isEqual:_borderRightColor] && [_borderRightColor isEqual:_borderBottomColor] && [_borderBottomColor isEqual:_borderLeftColor];
+    
+    BOOL invert = self.invertForDarkScheme;
+    WXColorScene scene = [self colorSceneType];
+    UIColor* usingBorderTopColor = [self.weexInstance chooseColor:_borderTopColor lightSchemeColor:_lightSchemeBorderTopColor darkSchemeColor:_darkSchemeBorderTopColor invert:invert scene:scene];
+    UIColor* usingBorderRightColor = [self.weexInstance chooseColor:_borderRightColor lightSchemeColor:_lightSchemeBorderRightColor darkSchemeColor:_darkSchemeBorderRightColor invert:invert scene:scene];
+    UIColor* usingBorderBottomColor = [self.weexInstance chooseColor:_borderBottomColor lightSchemeColor:_lightSchemeBorderBottomColor darkSchemeColor:_darkSchemeBorderBottomColor invert:invert scene:scene];
+    UIColor* usingBorderLeftColor = [self.weexInstance chooseColor:_borderLeftColor lightSchemeColor:_lightSchemeBorderLeftColor darkSchemeColor:_darkSchemeBorderLeftColor invert:invert scene:scene];
+    
+    BOOL colorEqual = [usingBorderTopColor isEqual:usingBorderRightColor] &&
+        [usingBorderRightColor isEqual:usingBorderBottomColor] &&
+        [usingBorderBottomColor isEqual:usingBorderLeftColor];
     if (!colorEqual) {
         return YES;
     }
@@ -579,6 +633,58 @@
     
     WX_CHECK_BORDER_PROP(Style, Top, Left, Bottom, Right, WXBorderStyle)
     WX_CHECK_BORDER_PROP(Color, Top, Left, Bottom, Right, UIColor)
+    do {
+        BOOL needsDisplay = NO;
+        if (styles[@"weexDarkSchemeBorderColor"]) {
+            _darkSchemeBorderTopColor = _darkSchemeBorderLeftColor = _darkSchemeBorderRightColor = _darkSchemeBorderBottomColor = [WXConvert UIColor:styles[@"weexDarkSchemeBorderColor"]];
+            needsDisplay = YES;
+        }
+        if (styles[@"weexDarkSchemeBorderTopColor"]) {
+            _darkSchemeBorderTopColor = [WXConvert UIColor:styles[@"weexDarkSchemeBorderTopColor"]];
+            needsDisplay = YES;
+        }
+        if (styles[@"weexDarkSchemeBorderLeftColor"]) {
+            _darkSchemeBorderLeftColor = [WXConvert UIColor:styles[@"weexDarkSchemeBorderLeftColor"]];
+            needsDisplay = YES;
+        }
+        if (styles[@"weexDarkSchemeBorderRightColor"]) {
+            _darkSchemeBorderRightColor = [WXConvert UIColor:styles[@"weexDarkSchemeBorderRightColor"]];
+            needsDisplay = YES;
+        }
+        if (styles[@"weexDarkSchemeBorderBottomColor"]) {
+            _darkSchemeBorderBottomColor = [WXConvert UIColor:styles[@"weexDarkSchemeBorderBottomColor"]];
+            needsDisplay = YES;
+        }
+        if (needsDisplay && updating) {
+            [self setNeedsDisplay];
+        }
+    } while (0);
+    do {
+        BOOL needsDisplay = NO;
+        if (styles[@"weexLightSchemeBorderColor"]) {
+            _lightSchemeBorderTopColor = _lightSchemeBorderLeftColor = _lightSchemeBorderRightColor = _lightSchemeBorderBottomColor = [WXConvert UIColor:styles[@"weexLightSchemeBorderColor"]];
+            needsDisplay = YES;
+        }
+        if (styles[@"weexLightSchemeBorderTopColor"]) {
+            _lightSchemeBorderTopColor = [WXConvert UIColor:styles[@"weexLightSchemeBorderTopColor"]];
+            needsDisplay = YES;
+        }
+        if (styles[@"weexLightSchemeBorderLeftColor"]) {
+            _lightSchemeBorderLeftColor = [WXConvert UIColor:styles[@"weexLightSchemeBorderLeftColor"]];
+            needsDisplay = YES;
+        }
+        if (styles[@"weexLightSchemeBorderRightColor"]) {
+            _lightSchemeBorderRightColor = [WXConvert UIColor:styles[@"weexLightSchemeBorderRightColor"]];
+            needsDisplay = YES;
+        }
+        if (styles[@"weexLightSchemeBorderBottomColor"]) {
+            _lightSchemeBorderBottomColor = [WXConvert UIColor:styles[@"weexLightSchemeBorderBottomColor"]];
+            needsDisplay = YES;
+        }
+        if (needsDisplay && updating) {
+            [self setNeedsDisplay];
+        }
+    } while (0);
     WX_CHECK_BORDER_PROP_PIXEL(Width, Top, Left, Bottom, Right)
     WX_CHECK_BORDER_PROP_PIXEL(Radius, TopLeft, TopRight, BottomLeft, BottomRight)
 
@@ -592,9 +698,9 @@
         } else if (!nowNeedsDrawBorder) {
             [self _resetNativeBorderRadius];
             _layer.borderWidth = _borderTopWidth;
-            _layer.borderColor = _borderTopColor.CGColor;
+            _layer.borderColor = [self.weexInstance chooseColor:_borderTopColor lightSchemeColor:_lightSchemeBorderTopColor darkSchemeColor:_darkSchemeBorderTopColor invert:self.invertForDarkScheme scene:[self colorSceneType]].CGColor;
             if ((_transition.transitionOptions & WXTransitionOptionsBackgroundColor) != WXTransitionOptionsBackgroundColor ) {
-                _layer.backgroundColor = _backgroundColor.CGColor;
+                _layer.backgroundColor = [self.weexInstance chooseColor:self.styleBackgroundColor lightSchemeColor:self.lightSchemeBackgroundColor darkSchemeColor:self.darkSchemeBackgroundColor invert:self.invertForDarkScheme scene:[self colorSceneType]].CGColor;
             }
         }
     }
@@ -606,7 +712,8 @@
     WXRoundedRect *borderRect = [[WXRoundedRect alloc] initWithRect:rect topLeft:_borderTopLeftRadius topRight:_borderTopRightRadius bottomLeft:_borderBottomLeftRadius bottomRight:_borderBottomRightRadius];
     WXRadii *radii = borderRect.radii;
     BOOL hasBorderRadius = [radii hasBorderRadius];
-    return (!hasBorderRadius) && _opacity == 1.0 && CGColorGetAlpha(_backgroundColor.CGColor) == 1.0 && [self _needsDrawBorder];
+    UIColor* currentBgColor = [self.weexInstance chooseColor:self.styleBackgroundColor lightSchemeColor:self.lightSchemeBackgroundColor darkSchemeColor:self.darkSchemeBackgroundColor invert:self.invertForDarkScheme scene:[self colorSceneType]];
+    return (!hasBorderRadius) && _opacity == 1.0 && CGColorGetAlpha(currentBgColor.CGColor) == 1.0 && [self _needsDrawBorder];
 }
 
 - (CAShapeLayer *)drawBorderRadiusMaskLayer:(CGRect)rect
@@ -627,6 +734,24 @@
     return _borderTopLeftRadius > 0.001 || _borderTopRightRadius > 0.001 || _borderBottomLeftRadius > 0.001 || _borderBottomLeftRadius > 0.001;
 }
 
+- (WXBoxShadow*)_chooseBoxShadow
+{
+    if ([self.weexInstance isDarkScheme]) {
+        if (_darkSchemeBoxShadow) {
+            return _darkSchemeBoxShadow;
+        }
+        else {
+            return _boxShadow;
+        }
+    }
+    else if (_lightSchemeBoxShadow) {
+        return _lightSchemeBoxShadow;
+    }
+    else {
+        return _boxShadow;
+    }
+}
+
 #pragma mark - Deprecated
 
 - (WXDisplayBlock)displayBlock
diff --git a/ios/sdk/WeexSDK/Sources/Engine/WXSDKEngine.m b/ios/sdk/WeexSDK/Sources/Engine/WXSDKEngine.m
index ad181ac..993e427 100644
--- a/ios/sdk/WeexSDK/Sources/Engine/WXSDKEngine.m
+++ b/ios/sdk/WeexSDK/Sources/Engine/WXSDKEngine.m
@@ -29,6 +29,7 @@
 #import "WXNavigationDefaultImpl.h"
 #import "WXURLRewriteDefaultImpl.h"
 #import "WXJSFrameworkLoadDefaultImpl.h"
+#import "WXDarkSchemeDefaultImpl.h"
 
 #import "WXSDKManager.h"
 #import "WXSDKError.h"
@@ -42,6 +43,7 @@
 #import "WXConfigCenterProtocol.h"
 #import "WXComponent+Layout.h"
 #import "WXCoreBridge.h"
+#import "WXDarkSchemeModule.h"
 
 @implementation WXSDKEngine
 
@@ -68,6 +70,7 @@
     [self registerModule:@"webSocket" withClass:NSClassFromString(@"WXWebSocketModule")];
     [self registerModule:@"voice-over" withClass:NSClassFromString(@"WXVoiceOverModule")];
     [self registerModule:@"sdk-console-log" withClass:NSClassFromString(@"WXConsoleLogModule")];
+    [self registerModule:@"dark-scheme" withClass:NSClassFromString(@"WXDarkSchemeModule")];
 }
 
 + (void)registerModule:(NSString *)name withClass:(Class)clazz
@@ -205,6 +208,7 @@
     [self registerHandler:[WXNavigationDefaultImpl new] withProtocol:@protocol(WXNavigationProtocol)];
     [self registerHandler:[WXURLRewriteDefaultImpl new] withProtocol:@protocol(WXURLRewriteProtocol)];
     [self registerHandler:[WXJSFrameworkLoadDefaultImpl new] withProtocol:@protocol(WXJSFrameworkLoadProtocol)];
+    [self registerHandler:[WXDarkSchemeDefaultImpl new] withProtocol:@protocol(WXDarkSchemeProtocol)];
 }
 
 + (void)registerHandler:(id)handler withProtocol:(Protocol *)protocol
@@ -225,6 +229,12 @@
 
 + (void)initSDKEnvironment
 {
+    if (@available(iOS 13.0, *)) {
+    }
+    else {
+        [WXUtility setDarkSchemeSupportEnable:NO];
+    }
+    
     NSString *fileName = @"weex-main-jsfm";
     NSString *filePath = [[NSBundle bundleForClass:self] pathForResource:fileName ofType:@"js"];
 	if (filePath == nil) {
diff --git a/ios/sdk/WeexSDK/Sources/Engine/WXSDKError.h b/ios/sdk/WeexSDK/Sources/Engine/WXSDKError.h
index b628b06..7523cf9 100644
--- a/ios/sdk/WeexSDK/Sources/Engine/WXSDKError.h
+++ b/ios/sdk/WeexSDK/Sources/Engine/WXSDKError.h
@@ -88,6 +88,7 @@
     WX_KEY_EXCEPTION_JS_DOWNLOAD =-9200,
     WX_KEY_EXCEPTION_DOM = -9300,
     WX_KEY_EXCEPTION_WXBRIDGE=-9400,
+    WX_KEY_EXCEPTION_JS_THREAD_BLOCK=-9401,
     
     // The following error codes have a remapped value defined in WXSDKUniversalErrCode
     WX_KEY_EXCEPTION_DEGRADE = -9500,
@@ -106,8 +107,8 @@
     WX_KEY_EXCEPTION_EMPTY_SCREEN_JS = -9700,
     WX_KEY_EXCEPTION_EMPTY_SCREEN_NATIVE = -9701,
     
-    WX_KEY_EXCEPTION_TOO_MANY_TIMERS = -9800,
     WX_KEY_EXCEPTION_NO_BUNDLE_TYPE = -9801,
+    WX_KEY_EXCEPTION_INVALID_JSON_OBJECT = -9802,
     
     WX_KEY_EXCEPTION_HERON_ERROR = -9900,
     WX_KEY_EXCEPTION_HERON_RENDER_ERROR = -9901,
diff --git a/ios/sdk/WeexSDK/Sources/Engine/WXSDKError.m b/ios/sdk/WeexSDK/Sources/Engine/WXSDKError.m
index 07ccbe1..755cdd1 100644
--- a/ios/sdk/WeexSDK/Sources/Engine/WXSDKError.m
+++ b/ios/sdk/WeexSDK/Sources/Engine/WXSDKError.m
@@ -88,6 +88,7 @@
                 @(WX_KEY_EXCEPTION_JS_DOWNLOAD):@{ERROR_TYPE:@(WX_DOWN_LOAD_ERROR),ERROR_GROUP:@(WX_NATIVE)},
                 @(WX_KEY_EXCEPTION_DOM):@{ERROR_TYPE:@(WX_NATIVE_ERROR),ERROR_GROUP:@(WX_NATIVE)},
                 @(WX_KEY_EXCEPTION_WXBRIDGE):@{ERROR_TYPE:@(WX_JS_ERROR),ERROR_GROUP:@(WX_JS)},
+                @(WX_KEY_EXCEPTION_JS_THREAD_BLOCK):@{ERROR_TYPE:@(WX_JS_ERROR),ERROR_GROUP:@(WX_JS)},
                 
                 @(WX_KEY_EXCEPTION_DEGRADE):@{ERROR_TYPE:@(WX_DEGRADE_ERROR),ERROR_GROUP:@(WX_NATIVE),ERROR_ALIAS:@(WX_UNI_KEY_EXCEPTION_DEGRADE)},
                 @(WX_KEY_EXCEPTION_DEGRADE_CHECK_CONTENT_LENGTH_FAILED):@{ERROR_TYPE:@(WX_DEGRADE_ERROR),ERROR_GROUP:@(WX_NET),ERROR_ALIAS:@(WX_UNI_KEY_EXCEPTION_DEGRADE_CHECK_CONTENT_LENGTH_FAILED)},
@@ -103,9 +104,10 @@
                 @(WX_KEY_EXCEPTION_EMPTY_SCREEN_JS):@{ERROR_TYPE:@(WX_RENDER_ERROR),ERROR_GROUP:@(WX_JS)},
                 @(WX_KEY_EXCEPTION_EMPTY_SCREEN_NATIVE):@{ERROR_TYPE:@(WX_RENDER_ERROR),ERROR_GROUP:@(WX_NATIVE)},
                 
-                @(WX_KEY_EXCEPTION_TOO_MANY_TIMERS):@{ERROR_TYPE:@(WX_NATIVE_ERROR),ERROR_GROUP:@(WX_NATIVE)},
                 @(WX_KEY_EXCEPTION_NO_BUNDLE_TYPE):@{ERROR_TYPE:@(WX_JS_ERROR),ERROR_GROUP:@(WX_JS)},
                 
+                @(WX_KEY_EXCEPTION_INVALID_JSON_OBJECT):@{ERROR_TYPE:@(WX_JS_ERROR),ERROR_GROUP:@(WX_JS)},
+                
                 @(WX_KEY_EXCEPTION_HERON_ERROR):@{ERROR_TYPE:@(WX_NATIVE_ERROR),ERROR_GROUP:@(WX_NATIVE)},
                 @(WX_KEY_EXCEPTION_HERON_RENDER_ERROR):@{ERROR_TYPE:@(WX_RENDER_ERROR),ERROR_GROUP:@(WX_NATIVE)},
                 };
diff --git a/ios/sdk/WeexSDK/Sources/Handler/WXDarkSchemeDefaultImpl.h b/ios/sdk/WeexSDK/Sources/Handler/WXDarkSchemeDefaultImpl.h
new file mode 100644
index 0000000..1bc1d2e
--- /dev/null
+++ b/ios/sdk/WeexSDK/Sources/Handler/WXDarkSchemeDefaultImpl.h
@@ -0,0 +1,32 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+#import <Foundation/Foundation.h>
+#import <WeexSDK/WXDarkSchemeProtocol.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+/* By default, this implementation class do basic invert of UIColor of RGBA color space.
+ You should implementation your own handler to better handle dark scheme in your application.
+ */
+@interface WXDarkSchemeDefaultImpl : NSObject <WXDarkSchemeProtocol>
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/ios/sdk/WeexSDK/Sources/Handler/WXDarkSchemeDefaultImpl.m b/ios/sdk/WeexSDK/Sources/Handler/WXDarkSchemeDefaultImpl.m
new file mode 100644
index 0000000..ccae67b
--- /dev/null
+++ b/ios/sdk/WeexSDK/Sources/Handler/WXDarkSchemeDefaultImpl.m
@@ -0,0 +1,43 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+#import "WXDarkSchemeDefaultImpl.h"
+
+@implementation WXDarkSchemeDefaultImpl
+
+- (BOOL)defaultInvertValueForRootComponent
+{
+    return NO;
+}
+
+- (void)configureView:(UIView *)view ofComponent:(WXComponent *)component
+{
+    // Nothing
+}
+
+- (UIColor *_Nullable)getInvertedColorFor:(UIColor *_Nonnull)color ofScene:(WXColorScene)scene withDefault:(UIColor *_Nullable)defaultColor
+{
+    CGFloat red, blue, green, alpha;
+    if ([color getRed:&red green:&green blue:&blue alpha:&alpha]) {
+        return [UIColor colorWithRed:1 - red green:1 - green blue:1 - blue alpha:alpha];
+    }
+    return color;
+}
+
+@end
diff --git a/ios/sdk/WeexSDK/Sources/Layout/WXComponent+Layout.mm b/ios/sdk/WeexSDK/Sources/Layout/WXComponent+Layout.mm
index a56cd64..fd5eb88 100644
--- a/ios/sdk/WeexSDK/Sources/Layout/WXComponent+Layout.mm
+++ b/ios/sdk/WeexSDK/Sources/Layout/WXComponent+Layout.mm
@@ -135,13 +135,14 @@
                 strongSelf.layer.transform = CATransform3DIdentity;
             }
             
+            WXBoxShadow* usingBoxShadow = [strongSelf _chooseBoxShadow];            
             if (!CGRectEqualToRect(strongSelf.view.frame,strongSelf.calculatedFrame)) {
                 strongSelf.view.frame = strongSelf.calculatedFrame;
                 strongSelf->_absolutePosition = CGPointMake(NAN, NAN);
-                [strongSelf configBoxShadow:strongSelf->_boxShadow];
+                [strongSelf configBoxShadow:usingBoxShadow];
             } else {
-                if (![strongSelf equalBoxShadow:strongSelf->_boxShadow withBoxShadow:strongSelf->_lastBoxShadow]) {
-                    [strongSelf configBoxShadow:strongSelf->_boxShadow];
+                if (![strongSelf equalBoxShadow:usingBoxShadow withBoxShadow:strongSelf->_lastBoxShadow]) {
+                    [strongSelf configBoxShadow:usingBoxShadow];
                 }
             }
             
diff --git a/ios/sdk/WeexSDK/Sources/Loader/WXResourceLoader.m b/ios/sdk/WeexSDK/Sources/Loader/WXResourceLoader.m
index 9015625..8423f78 100644
--- a/ios/sdk/WeexSDK/Sources/Loader/WXResourceLoader.m
+++ b/ios/sdk/WeexSDK/Sources/Loader/WXResourceLoader.m
@@ -140,14 +140,7 @@
     WXLogDebug(@"request:%@ didReceiveResponse:%@ ", request, response);
     
     _response = response;
-    id<WXConfigCenterProtocol> configCenter = [WXSDKEngine handlerForProtocol:@protocol(WXConfigCenterProtocol)];
-    if ([configCenter respondsToSelector:@selector(configForKey:defaultValue:isDefault:)]) {
-        BOOL isDefault;
-        BOOL clearResponseData = [[configCenter configForKey:@"iOS_weex_ext_config.clearResponseDataWhenDidReceiveResponse" defaultValue:@(NO) isDefault:&isDefault] boolValue];
-        if(clearResponseData) {
-            _data = nil;
-        }
-    }
+    _data = nil;
     
     if (self.onResponseReceived) {
         self.onResponseReceived(response);
diff --git a/ios/sdk/WeexSDK/Sources/Manager/WXBridgeManager.h b/ios/sdk/WeexSDK/Sources/Manager/WXBridgeManager.h
index 3b1d2a4..5fc9c54 100644
--- a/ios/sdk/WeexSDK/Sources/Manager/WXBridgeManager.h
+++ b/ios/sdk/WeexSDK/Sources/Manager/WXBridgeManager.h
@@ -45,6 +45,10 @@
  **/
 @property (nonatomic, weak, readonly) WXSDKInstance *topInstance;
 
+@property (nonatomic, strong) NSMutableDictionary *lastMethodInfo;
+
++ (instancetype)sharedManager;
+
 /**
  *  Create Instance Method
  *  @param instance  :   instance id
@@ -246,6 +250,8 @@
 
 - (void)executeJSTaskQueue;
 
+- (void)checkJSThread;
+
 @end
 
 NS_ASSUME_NONNULL_END
diff --git a/ios/sdk/WeexSDK/Sources/Manager/WXBridgeManager.m b/ios/sdk/WeexSDK/Sources/Manager/WXBridgeManager.m
index ff89cfc..4f6a3f2 100644
--- a/ios/sdk/WeexSDK/Sources/Manager/WXBridgeManager.m
+++ b/ios/sdk/WeexSDK/Sources/Manager/WXBridgeManager.m
@@ -37,6 +37,9 @@
 #import "WXDataRenderHandler.h"
 #import "WXHandlerFactory.h"
 #import "WXUtility.h"
+#import "WXExceptionUtils.h"
+#import "WXSDKEngine.h"
+#import "WXConfigCenterProtocol.h"
 
 @interface WXBridgeManager ()
 
@@ -46,6 +49,7 @@
 @property (nonatomic, strong) WXBridgeContext *backupBridgeCtx;
 @property (nonatomic, strong) WXThreadSafeMutableArray *instanceIdStack;
 @property (nonatomic, strong) NSMutableArray* jsTaskQueue;
+@property (nonatomic, strong) NSTimer *timer;
 
 @end
 
@@ -71,10 +75,20 @@
         _bridgeCtx = [[WXBridgeContext alloc] init];
         _supportMultiJSThread = NO;
         _jsTaskQueue = [NSMutableArray array];
+        _timer = nil;
+        _lastMethodInfo = [NSMutableDictionary dictionary];
     }
     return self;
 }
 
+- (WXBridgeContext *)bridgeCtx {
+    if (_bridgeCtx) {
+        return _bridgeCtx;
+    }
+    _bridgeCtx = [[WXBridgeContext alloc] init];
+    return _bridgeCtx;
+}
+
 - (WXBridgeContext *)backupBridgeCtx {
     if (_backupBridgeCtx) {
         return _backupBridgeCtx;
@@ -120,7 +134,7 @@
         [WXBridgeThread setQualityOfService:[[NSThread mainThread] qualityOfService]];
         [WXBridgeThread start];
     });
-    
+
     return WXBridgeThread;
 }
 
@@ -778,6 +792,42 @@
     }, instanceId);
 }
 
+#pragma mark JS Thread Check
+- (void)checkJSThread {
+    if (!_timer) {
+        id configCenter = [WXSDKEngine handlerForProtocol:@protocol(WXConfigCenterProtocol)];
+        if ([configCenter respondsToSelector:@selector(configForKey:defaultValue:isDefault:)]) {
+            BOOL enableCheckJSThread = [[configCenter configForKey:@"iOS_weex_ext_config.enable_check_js_thread" defaultValue:@(YES) isDefault:NULL] boolValue];
+            if (enableCheckJSThread) {
+                _timer = [NSTimer scheduledTimerWithTimeInterval:5.0f target:self selector:@selector(_postTaskToBridgeThread) userInfo:nil repeats:YES];
+            }
+        }
+    }
+}
+
+- (void)_postTaskToBridgeThread {
+    __block BOOL taskFinished = NO;
+    WXPerformBlockOnBridgeThread(^{
+        taskFinished = YES;
+    });
+
+    __weak typeof(self) weakSelf = self;
+    dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(5 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
+        if (!weakSelf) {
+            return;
+        }
+        if (!taskFinished) {
+            WXSDKErrCode errorCode = WX_KEY_EXCEPTION_JS_THREAD_BLOCK;
+            WXSDKInstance* instance = weakSelf.topInstance;
+            if (!instance) {
+                return;
+            }
+            NSString *instanceId = instance.instanceId;
+            [WXExceptionUtils commitCriticalExceptionRT:instanceId errCode:[NSString stringWithFormat:@"%d", errorCode] function:@"" exception:@"JS Thread is block" extParams:weakSelf.lastMethodInfo];
+        }
+    });
+}
+
 #pragma mark - Deprecated
 
 - (void)executeJsMethod:(WXCallJSMethod *)method
diff --git a/ios/sdk/WeexSDK/Sources/Manager/WXComponentManager.mm b/ios/sdk/WeexSDK/Sources/Manager/WXComponentManager.mm
index f4b29a8..6fa35be 100644
--- a/ios/sdk/WeexSDK/Sources/Manager/WXComponentManager.mm
+++ b/ios/sdk/WeexSDK/Sources/Manager/WXComponentManager.mm
@@ -42,6 +42,8 @@
 #import "WXComponent_performance.h"
 #import "WXAnalyzerCenter.h"
 #import "WXDisplayLinkManager.h"
+#import "WXDarkSchemeProtocol.h"
+#import "WXSDKInstance_private.h"
 
 static NSThread *WXComponentThread;
 
@@ -261,6 +263,21 @@
     
     _rootComponent = [self _buildComponent:ref type:type supercomponent:nil styles:styles attributes:attributes events:events renderObject:renderObject];
     
+    if ([WXUtility isDarkSchemeSupportEnabled]) {
+        if (attributes[@"invertForDarkScheme"] == nil) {
+            WXAutoInvertingBehavior invertingBehavior = _weexInstance.autoInvertingBehavior;
+            if (invertingBehavior == WXAutoInvertingBehaviorDefault) {
+                _rootComponent.invertForDarkScheme = [[WXSDKInstance darkSchemeColorHandler] defaultInvertValueForRootComponent];
+            }
+            else if (invertingBehavior == WXAutoInvertingBehaviorAlways) {
+                _rootComponent.invertForDarkScheme = YES;
+            }
+            else {
+                _rootComponent.invertForDarkScheme = NO;
+            }
+        }
+    }
+    
     CGSize size = _weexInstance.frame.size;
     [WXCoreBridge setDefaultDimensionIntoRoot:_weexInstance.instanceId
                                         width:size.width height:size.height
@@ -327,6 +344,11 @@
         }
     }
     
+    // Not explicitly declare "invertForDarkScheme", inherit
+    if (attributes[@"invertForDarkScheme"] == nil) {
+        component.invertForDarkScheme = supercomponent.invertForDarkScheme;
+    }
+    
 #ifdef DEBUG
     WXLogDebug(@"flexLayout -> _recursivelyAddComponent : super:(%@,%@):[%f,%f] ,child:(%@,%@):[%f,%f],childClass:%@",
                supercomponent.type,
@@ -919,6 +941,9 @@
     [self _addUITask:^{
         UIView *rootView = instance.rootView;
         [instance.performance onInstanceRenderSuccess:instance];
+        if (instance.wlasmRender) {
+            [instance.apmInstance forceSetInteractionTime:[WXUtility getUnixFixTimeMillis]];
+        }
         if (instance.renderFinish) {
             instance.renderFinish(rootView);
         }
diff --git a/ios/sdk/WeexSDK/Sources/Manager/WXSDKManager.m b/ios/sdk/WeexSDK/Sources/Manager/WXSDKManager.m
index de71a29..9d16d1c 100644
--- a/ios/sdk/WeexSDK/Sources/Manager/WXSDKManager.m
+++ b/ios/sdk/WeexSDK/Sources/Manager/WXSDKManager.m
@@ -47,7 +47,7 @@
 - (instancetype)init
 {
     if (self = [super init]){
-        _bridgeMgr = [[WXBridgeManager alloc] init];
+        _bridgeMgr = [WXBridgeManager sharedManager];
     }
     return self;
 }
@@ -57,7 +57,7 @@
     WXBridgeManager* result = [self sharedInstance].bridgeMgr;
     if (result == nil) {
         // devtool may invoke "unload" and set bridgeMgr to nil
-        result = [[WXBridgeManager alloc] init];
+        result = [WXBridgeManager sharedManager];
         [self sharedInstance].bridgeMgr = result;
     }
     return result;
diff --git a/ios/sdk/WeexSDK/Sources/Model/WXComponent.h b/ios/sdk/WeexSDK/Sources/Model/WXComponent.h
index 0528b1d..54ba69e 100644
--- a/ios/sdk/WeexSDK/Sources/Model/WXComponent.h
+++ b/ios/sdk/WeexSDK/Sources/Model/WXComponent.h
@@ -32,6 +32,12 @@
     WXComponentUpdateStylesCallback
 } WXComponentCallbackType;
 
+typedef enum : NSUInteger {
+    WXColorSceneBackground,
+    WXColorSceneText,
+    WXColorSceneUnknown,
+} WXColorScene;
+
 /**
  * @abstract the component callback , result can be string or dictionary.
  * @discussion callback data to js, the id of callback function will be removed to save memory.
@@ -364,6 +370,8 @@
 /// @name Display
 ///--------------------------------------
 
+@property (nonatomic, assign) BOOL invertForDarkScheme;
+
 @property (nonatomic, assign) WXDisplayType displayType;
 
 /**
@@ -379,6 +387,16 @@
 - (BOOL)needsDrawRect;
 
 /**
+ * @abstract Fired on instance scheme did changed.
+ */
+- (void)schemeDidChange:(NSString*)scheme;
+
+/**
+ * @abstract Hint used for better do color invert in dark mode.
+ */
+- (WXColorScene)colorSceneType;
+
+/**
  * @abstract Draws the component’s image within the passed-in rectangle.
  * @parameter rect The rectangle which is the entire visible bounds of your component. 
  * @return A UIImage containing the contents of the current bitmap graphics context.
diff --git a/ios/sdk/WeexSDK/Sources/Model/WXComponent.mm b/ios/sdk/WeexSDK/Sources/Model/WXComponent.mm
index a60251c..cb6251c 100644
--- a/ios/sdk/WeexSDK/Sources/Model/WXComponent.mm
+++ b/ios/sdk/WeexSDK/Sources/Model/WXComponent.mm
@@ -42,6 +42,7 @@
 #import "WXSDKInstance_performance.h"
 #import "WXComponent_performance.h"
 #import "WXCoreBridge.h"
+#import "WXDarkSchemeProtocol.h"
 
 #pragma clang diagnostic ignored "-Wincomplete-implementation"
 #pragma clang diagnostic ignored "-Wobjc-protocol-method-implementation"
@@ -70,6 +71,9 @@
 }
 
 @synthesize transform = _transform;
+@synthesize styleBackgroundColor = _styleBackgroundColor;
+@synthesize darkSchemeBackgroundColor = _darkSchemeBackgroundColor;
+@synthesize lightSchemeBackgroundColor = _lightSchemeBackgroundColor;
 
 #pragma mark Life Cycle
 
@@ -103,6 +107,7 @@
         _eventPenetrationEnabled = NO;
         _accessibilityHintContent = nil;
         _cancelsTouchesInView = YES;
+        _invertForDarkScheme = NO;
         
         _async = NO;
         
@@ -121,6 +126,10 @@
             }
         }
         
+        if (attributes[@"invertForDarkScheme"]) {
+            _invertForDarkScheme = [WXConvert BOOL:attributes[@"invertForDarkScheme"]];
+        }
+        
         if (attributes[@"userInteractionEnabled"]) {
             _userInteractionEnabled = [WXConvert BOOL:attributes[@"userInteractionEnabled"]];
         }
@@ -379,6 +388,12 @@
         [self viewWillLoad];
         
         _view = [self loadView];
+        
+        // Provide a chance for dark scheme handler to process the view
+        if ([WXUtility isDarkSchemeSupportEnabled]) {
+            [[WXSDKInstance darkSchemeColorHandler] configureView:_view ofComponent:self];
+        }
+        
 #ifdef DEBUG
         WXLogDebug(@"flexLayout -> loadView:addr-(%p),componentRef-(%@)",_view,self.ref);
 #endif
@@ -387,11 +402,37 @@
         _view.hidden = _visibility == WXVisibilityShow ? NO : YES;
         _view.clipsToBounds = _clipToBounds;
         if (![self _needsDrawBorder]) {
-            _layer.borderColor = _borderTopColor.CGColor;
+            _layer.borderColor = [self.weexInstance chooseColor:_borderTopColor lightSchemeColor:_lightSchemeBorderTopColor darkSchemeColor:_darkSchemeBorderTopColor invert:_invertForDarkScheme scene:[self colorSceneType]].CGColor;
             _layer.borderWidth = _borderTopWidth;
             [self _resetNativeBorderRadius];
             _layer.opacity = _opacity;
-            _view.backgroundColor = _backgroundColor;
+            
+            /* Also set background color to view to fix that problem that system may
+             set dynamic color to UITableView. Without these codes, event if we set
+             clear color to layer, the table view could not be transparent. */
+            if ([WXUtility isDarkSchemeSupportEnabled]) {
+                UIColor* choosedColor = [self.weexInstance chooseColor:self.styleBackgroundColor lightSchemeColor:self.lightSchemeBackgroundColor darkSchemeColor:self.darkSchemeBackgroundColor invert:_invertForDarkScheme scene:[self colorSceneType]];
+                if (choosedColor == [UIColor clearColor]) {
+                    _view.backgroundColor = choosedColor;
+                }
+                _layer.backgroundColor = choosedColor.CGColor;
+            }
+            else {
+                /* On iOS10, there is an annoying problem that if we only
+                 set backgroundColor to layer(not to view), for UIScrollView
+                 the background color would be black. So we have to set
+                 background color to UIView itself on iOS10(or lower).
+                 
+                 For iOS13, we have SDK which hooked setBackgroundColor
+                 of UIView to support autoinverting(no in WeexSDK).
+                 But that SDK would finally set a UIDynamicColor to view.
+                 Weex can handle dark mode, so we don't want background
+                 color of a UIView in Weex page to be set to UIDynamicColor.
+                 So in code above, we only set color to layer but which
+                 also caused the black problem that on iOS10.
+                 */
+                _view.backgroundColor = self.styleBackgroundColor;
+            }
         }
 
         if (_backgroundImage) {
@@ -404,8 +445,10 @@
         
         [self _adjustForRTL];
         
-        if (_boxShadow) {
-            [self configBoxShadow:_boxShadow];
+        WXBoxShadow* usingBoxShadow = [self _chooseBoxShadow];        
+        if (usingBoxShadow) {
+            _lastBoxShadow = usingBoxShadow;
+            [self configBoxShadow:usingBoxShadow];
         }
         
         _view.wx_component = self;
@@ -844,7 +887,25 @@
     if (CGRectEqualToRect(self.view.frame, CGRectZero)) {
         return;
     }
-    NSDictionary * linearGradient = [WXUtility linearGradientWithBackgroundImage:_backgroundImage];
+    
+    NSString* styleValue = nil;
+    BOOL isDark = [self.weexInstance isDarkScheme];
+    if (isDark) {
+        if (_darkSchemeBackgroundImage) {
+            styleValue = _darkSchemeBackgroundImage;
+        }
+        else {
+            styleValue = _backgroundImage;
+        }
+    }
+    else if (_lightSchemeBackgroundImage) {
+        styleValue = _lightSchemeBackgroundImage;
+    }
+    else {
+        styleValue = _backgroundImage;
+    }
+    
+    NSDictionary * linearGradient = [WXUtility linearGradientWithBackgroundImage:styleValue];
     if (!linearGradient) {
         return ;
     }
@@ -853,12 +914,13 @@
     dispatch_async(dispatch_get_main_queue(), ^{
         __strong typeof(self) strongSelf = weakSelf;
         if(strongSelf) {
+            // No need to auto-invert linear-gradient colors. We only allows using 'dark-scheme-background-image' style.
             UIColor * startColor = (UIColor*)linearGradient[@"startColor"];
             UIColor * endColor = (UIColor*)linearGradient[@"endColor"];
             CAGradientLayer * gradientLayer = [WXUtility gradientLayerFromColors:@[startColor, endColor] locations:nil frame:strongSelf.view.bounds gradientType:(WXGradientType)[linearGradient[@"gradientType"] integerValue]];
             if (gradientLayer) {
-                _backgroundColor = [UIColor colorWithPatternImage:[strongSelf imageFromLayer:gradientLayer]];
-                strongSelf.view.backgroundColor = _backgroundColor;
+                strongSelf.styleBackgroundColor = [UIColor colorWithPatternImage:[strongSelf imageFromLayer:gradientLayer]];
+                strongSelf.view.backgroundColor = strongSelf.styleBackgroundColor;
                 [strongSelf setNeedsDisplay];
             }
         }
diff --git a/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance.h b/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance.h
index c6cf521..e7d4fb1 100644
--- a/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance.h
+++ b/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance.h
@@ -26,6 +26,8 @@
 #import <WeexSDK/WXApmForInstance.h>
 #import <WeexSDK/WXComponentManager.h>
 
+@protocol WXDarkSchemeProtocol;
+
 NS_ASSUME_NONNULL_BEGIN
 
 extern NSString *const bundleUrlOptionKey;
@@ -447,6 +449,57 @@
  */
 + (NSDictionary*)lastPageInfo;
 
+#pragma mark - Scheme Support
+
+typedef enum : NSUInteger {
+    WXAutoInvertingBehaviorDefault,
+    WXAutoInvertingBehaviorAlways,
+    WXAutoInvertingBehaviorNever,
+} WXAutoInvertingBehavior;
+
+/**
+ Set auto-inverting behavior for dark scheme.
+    WXAutoInvertingBehaviorDefault: Use components attribute and
+        defaultInvertValueForRootComponent of WXDarkSchemeProtocol.
+    WXAutoInvertingBehaviorAlways: Always set 'autoInvertForDarkScheme' as
+        true for root component.
+    WXAutoInvertingBehaviorNever: Always set 'autoInvertForDarkScheme' as
+        false for root component.
+ 
+ This function should be called before rendering URL.
+
+ @return Handler instance.
+*/
+- (void)setAutoInvertingBehavior:(WXAutoInvertingBehavior)behavior;
+
+/**
+ Handler for handling color invert.
+
+ @return Handler instance.
+ */
++ (id<WXDarkSchemeProtocol>)darkSchemeColorHandler;
+
+/**
+ Return true if current is dark scheme for this instance.
+ */
+- (BOOL)isDarkScheme;
+
+/**
+ Get/set interface style of current instance.
+ */
+- (NSString*)currentSchemeName;
+- (void)setCurrentSchemeName:(NSString*)name;
+
+/**
+ Choose final color between original color and dark-mode one.
+ Also considering invert.
+ */
+- (UIColor*)chooseColor:(UIColor*)originalColor
+       lightSchemeColor:(UIColor*)lightColor
+        darkSchemeColor:(UIColor*)darkColor
+                 invert:(BOOL)invert
+                  scene:(WXColorScene)scene;
+
 /** 
  * Deprecated 
  */
diff --git a/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance.m b/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance.m
index 1a09028..d033379 100644
--- a/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance.m
+++ b/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance.m
@@ -49,8 +49,11 @@
 #import "WXJSCoreBridge.h"
 #import "WXSDKInstance_performance.h"
 #import "WXPageEventNotifyEvent.h"
+#import "WXConvertUtility.h"
 #import "WXCoreBridge.h"
-#import <WeexSDK/WXDataRenderHandler.h>
+#import "WXDataRenderHandler.h"
+#import "WXDarkSchemeProtocol.h"
+#import "WXDarkSchemeModule.h"
 
 #define WEEX_LITE_URL_SUFFIX           @"wlasm"
 #define WEEX_RENDER_TYPE_PLATFORM       @"platform"
@@ -101,6 +104,20 @@
 {
     self = [super init];
     if (self) {
+        if ([WXUtility isDarkSchemeSupportEnabled]) {
+            self.schemeName = [WXUtility isSystemInDarkScheme] ? @"dark" : @"light";
+        }
+        else {
+            self.schemeName = @"light";
+        }
+        
+        // Update scheme value in JS environment.
+        if (([WXUtility isEnvironmentUsingDarkScheme] && [self.schemeName isEqualToString:@"light"]) ||
+            (![WXUtility isEnvironmentUsingDarkScheme] && [self.schemeName isEqualToString:@"dark"])) {
+            [[WXBridgeManager sharedManager] resetEnvironment];
+        }
+        
+        _autoInvertingBehavior = WXAutoInvertingBehaviorDefault;
         _renderType = renderType;
         _appearState = YES;
         
@@ -537,9 +554,6 @@
     if (!self.userInfo[@"jsMainBundleStringContentLength"]) {
         self.userInfo[@"jsMainBundleStringContentLength"] = @([mainBundleString length]);
     }
-    if (!self.userInfo[@"jsMainBundleStringContentLength"]) {
-        self.userInfo[@"jsMainBundleStringContentMd5"] = [WXUtility md5:mainBundleString];
-    }
     
     id<WXPageEventNotifyEventProtocol> pageEvent = [WXSDKEngine handlerForProtocol:@protocol(WXPageEventNotifyEventProtocol)];
     if ([pageEvent respondsToSelector:@selector(pageStart:)]) {
@@ -599,6 +613,23 @@
     if ([configCenter respondsToSelector:@selector(configForKey:defaultValue:isDefault:)]) {		
         BOOL enableRTLLayoutDirection = [[configCenter configForKey:@"iOS_weex_ext_config.enableRTLLayoutDirection" defaultValue:@(YES) isDefault:NULL] boolValue];
         [WXUtility setEnableRTLLayoutDirection:enableRTLLayoutDirection];
+        
+        BOOL isIOS13 = [[[UIDevice currentDevice] systemVersion] integerValue] == 13;
+        BOOL useMRCForInvalidJSONObject = [[configCenter configForKey:@"iOS_weex_ext_config.useMRCForInvalidJSONObject" defaultValue:@(YES) isDefault:NULL] boolValue];
+        BOOL alwaysUseMRCForObjectToWeexCore = [[configCenter configForKey:@"iOS_weex_ext_config.alwaysUseMRC" defaultValue:@(NO) isDefault:NULL] boolValue];
+        ConvertSwitches(isIOS13, useMRCForInvalidJSONObject, alwaysUseMRCForObjectToWeexCore);
+        
+        BOOL isDarkSchemeSupportEnabled = [[configCenter configForKey:@"iOS_weex_ext_config.supportDarkScheme" defaultValue:@(YES) isDefault:NULL] boolValue];
+        if (@available(iOS 13.0, *)) {
+        }
+        else {
+            isDarkSchemeSupportEnabled = NO;
+        }
+        [WXUtility setDarkSchemeSupportEnable:isDarkSchemeSupportEnabled];
+    }
+    else {
+        BOOL isIOS13 = [[[UIDevice currentDevice] systemVersion] integerValue] == 13;
+        ConvertSwitches(isIOS13, YES, NO);
     }
     return NO;
 }
@@ -949,7 +980,7 @@
 }
     
 - (BOOL)wlasmRender {
-    if ([_options[@"WLASM_RENDER"] boolValue]) {
+    if ([_options[@"WLASM_RENDER"] boolValue] || [_scriptURL.pathExtension isEqualToString:@"wlasm"] || [_scriptURL.pathExtension isEqualToString:@"wlm"]) {
         return YES;
     }
     return NO;
@@ -1162,6 +1193,112 @@
     return result;
 }
 
+- (void)setAutoInvertingBehavior:(WXAutoInvertingBehavior)behavior
+{
+    _autoInvertingBehavior = behavior;
+}
+
++ (id<WXDarkSchemeProtocol>)darkSchemeColorHandler
+{
+    static id<WXDarkSchemeProtocol> colorHandler;
+    static dispatch_once_t onceToken;
+    dispatch_once(&onceToken, ^{
+        colorHandler = [WXHandlerFactory handlerForProtocol:@protocol(WXDarkSchemeProtocol)];
+    });
+    return colorHandler;
+}
+
+- (NSString*)currentSchemeName
+{
+    return self.schemeName;
+}
+
+- (BOOL)isDarkScheme
+{
+    return [self.schemeName isEqualToString:@"dark"];
+}
+
+- (void)setCurrentSchemeName:(NSString*)name
+{
+    if (![WXUtility isDarkSchemeSupportEnabled]) {
+        self.schemeName = @"light";
+        return;
+    }
+    
+    if (name && ![name isEqualToString:self.schemeName]) {
+        self.schemeName = name;
+        
+        if (self.isCustomRenderType) {
+            return;
+        }
+        
+        WXDarkSchemeModule* darkSchemeModule = [self moduleForClass:[WXDarkSchemeModule class]];
+        [darkSchemeModule onInstanceSchemeChanged];
+        
+        // Recursively visit all components and notify that scheme had changed.
+        __weak WXSDKInstance* weakSelf = self;
+        WXPerformBlockOnComponentThread(^{
+            __strong WXSDKInstance* strongSelf = weakSelf;
+            if (strongSelf == nil) {
+                return;
+            }
+            
+            if (!strongSelf->_componentManager.isValid) {
+                return;
+            }
+            
+            [strongSelf->_componentManager enumerateComponentsUsingBlock:^(WXComponent * _Nonnull component, BOOL * _Nonnull stop) {
+                __weak WXComponent* wcomp = component;
+                WXPerformBlockOnMainThread(^{
+                    __strong WXComponent* scomp = wcomp;
+                    if (scomp) {
+                        [scomp schemeDidChange:name];
+                    }
+                });
+            }];
+        });
+        
+        [[WXSDKManager bridgeMgr] fireEvent:_instanceId
+                                        ref:WX_SDK_ROOT_REF
+                                       type:@"schemechange"
+                                     params:@{@"scheme": self.schemeName?:@"light"}
+                                 domChanges:nil];
+    }
+}
+
+- (UIColor*)chooseColor:(UIColor*)originalColor
+       lightSchemeColor:(UIColor*)lightColor
+        darkSchemeColor:(UIColor*)darkColor
+                 invert:(BOOL)invert
+                  scene:(WXColorScene)scene
+{
+    if (![WXUtility isDarkSchemeSupportEnabled]) {
+        return originalColor;
+    }
+    
+    if ([self isDarkScheme]) {
+        if (darkColor) {
+            return darkColor;
+        }
+        else if (invert) {
+            // Invert originalColor
+            if (originalColor == [UIColor clearColor]) {
+                return originalColor;
+            }
+            return [[WXSDKInstance darkSchemeColorHandler] getInvertedColorFor:originalColor ofScene:scene withDefault:originalColor];
+        }
+        else {
+            return originalColor;
+        }
+    }
+    else if (lightColor) {
+        return lightColor;
+    }
+    else {
+        return originalColor;
+    }
+}
+
 @end
 
 @implementation WXSDKInstance (Deprecated)
diff --git a/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance_private.h b/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance_private.h
index 25680da..30cd209 100644
--- a/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance_private.h
+++ b/ios/sdk/WeexSDK/Sources/Model/WXSDKInstance_private.h
@@ -39,6 +39,9 @@
 @property (nonatomic, strong) NSString *createInstanceContextResult;
 @property (nonatomic, strong) NSString *executeRaxApiResult;
 
+@property (nonatomic, assign) WXAutoInvertingBehavior autoInvertingBehavior;
+@property (atomic, strong) NSString* schemeName;
+
 - (void)addModuleEventObservers:(NSString*)event callback:(NSString*)callbackId option:(NSDictionary*)option moduleClassName:(NSString*)moduleClassName;
 - (void)_addModuleEventObserversWithModuleMethod:(WXModuleMethod*)method;
 - (void)removeModuleEventObserver:(NSString*)event moduleClassName:(NSString*)moduleClassName;
diff --git a/ios/sdk/WeexSDK/Sources/Module/WXAnimationModule.m b/ios/sdk/WeexSDK/Sources/Module/WXAnimationModule.m
index 8ee1591..147ec6e 100644
--- a/ios/sdk/WeexSDK/Sources/Module/WXAnimationModule.m
+++ b/ios/sdk/WeexSDK/Sources/Module/WXAnimationModule.m
@@ -26,6 +26,7 @@
 #import "WXLength.h"
 #import "WXTransition.h"
 #import "WXComponent+Layout.h"
+#import "WXDarkSchemeProtocol.h"
 
 @interface WXAnimationInfo : NSObject<NSCopying>
 
@@ -207,7 +208,38 @@
     }
     CAMediaTimingFunction *timingFunction = [WXConvert CAMediaTimingFunction:args[@"timingFunction"]];
     NSDictionary *styles = args[@"styles"];
+    NSDictionary* componentRawStyles = target.styles;
+    
+    BOOL isDarkScheme = [target.weexInstance isDarkScheme];
+    BOOL updatingDarkSchemeBackgroundColor = styles[@"weexDarkSchemeBackgroundColor"] != nil;
+    BOOL updatingLightSchemeBackgroundColor = styles[@"weexLightSchemeBackgroundColor"] != nil;
+    
     for (NSString *property in styles) {
+        if ([property isEqualToString:@"backgroundColor"]) {
+            if (isDarkScheme && (updatingDarkSchemeBackgroundColor ||
+                                componentRawStyles[@"weexDarkSchemeBackgroundColor"] != nil)) {
+                /* Updating "darkSchemeBackgroundColor" in dark mode,
+                 or this component has dark bg color explicitly defined in styels.
+                 We ignore transition animation for "backgroundColor" */
+                continue;
+            }
+            else if (!isDarkScheme && (updatingLightSchemeBackgroundColor ||
+                                      componentRawStyles[@"weexLightSchemeBackgroundColor"] != nil)) {
+                continue;
+            }
+        }
+        else if ([property isEqualToString:@"weexDarkSchemeBackgroundColor"]) {
+            if (!isDarkScheme) {
+                /* Do not do animation for "darkSchemeBackgroundColor" in light mode. */
+                continue;
+            }
+        }
+        else if ([property isEqualToString:@"weexLightSchemeBackgroundColor"]){
+            if (isDarkScheme) {
+                continue;
+            }
+        }
+        
         WXAnimationInfo *info = [WXAnimationInfo new];
         info.duration = duration;
         info.delay = delay;
@@ -287,10 +319,18 @@
                 [infos addObject:newInfo];
             }
             target.transform = wxTransform;
-        } else if ([property isEqualToString:@"backgroundColor"]) {
+        } else if ([property isEqualToString:@"backgroundColor"] ||
+                   [property isEqualToString:@"weexDarkSchemeBackgroundColor"] ||
+                   [property isEqualToString:@"weexLightSchemeBackgroundColor"]) {
             info.propertyName = @"backgroundColor";
             info.fromValue = (__bridge id)(layer.backgroundColor);
-            info.toValue = (__bridge id)[WXConvert CGColor:value];
+            UIColor* toColor = [WXConvert UIColor:value];
+            if ([target.weexInstance isDarkScheme] && target.invertForDarkScheme &&
+                [property isEqualToString:@"backgroundColor"]) {
+                // Invert color
+                toColor = [[WXSDKInstance darkSchemeColorHandler] getInvertedColorFor:toColor ofScene:[target colorSceneType] withDefault:toColor];
+            }
+            info.toValue = (__bridge id)([toColor CGColor]);
             [infos addObject:info];
         } else if ([property isEqualToString:@"opacity"]) {
             info.propertyName = @"opacity";
diff --git a/ios/sdk/WeexSDK/Sources/Module/WXClipboardModule.m b/ios/sdk/WeexSDK/Sources/Module/WXClipboardModule.m
index 7b7fcb1..c07d364 100644
--- a/ios/sdk/WeexSDK/Sources/Module/WXClipboardModule.m
+++ b/ios/sdk/WeexSDK/Sources/Module/WXClipboardModule.m
@@ -24,8 +24,8 @@
 WX_EXPORT_METHOD(@selector(setString:))
 WX_EXPORT_METHOD(@selector(getString:))
 
-- (dispatch_queue_t)targetExecuteQueue {
-    return dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
+- (NSThread *)targetExecuteThread {
+    return [NSThread mainThread];
 }
 
 - (void)setString:(NSString *)content
@@ -37,9 +37,10 @@
 - (void)getString:(WXModuleKeepAliveCallback)callback{
     UIPasteboard *clipboard = [UIPasteboard generalPasteboard];
     NSDictionary *result = [@{} mutableCopy];
-    if(clipboard.string)
+    NSString* content = [clipboard string];
+    if(content)
     {
-        [result setValue:clipboard.string forKey:@"data"];
+        [result setValue:content forKey:@"data"];
         [result setValue:@"success" forKey:@"result"];
     }else
     {
diff --git a/ios/sdk/WeexSDK/Sources/Module/WXDarkSchemeModule.h b/ios/sdk/WeexSDK/Sources/Module/WXDarkSchemeModule.h
new file mode 100644
index 0000000..fce05b4
--- /dev/null
+++ b/ios/sdk/WeexSDK/Sources/Module/WXDarkSchemeModule.h
@@ -0,0 +1,27 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+#import <Foundation/Foundation.h>
+#import "WXModuleProtocol.h"
+
+@interface WXDarkSchemeModule : NSObject <WXModuleProtocol>
+
+- (void)onInstanceSchemeChanged;
+
+@end
diff --git a/ios/sdk/WeexSDK/Sources/Module/WXDarkSchemeModule.m b/ios/sdk/WeexSDK/Sources/Module/WXDarkSchemeModule.m
new file mode 100644
index 0000000..7cf14d1
--- /dev/null
+++ b/ios/sdk/WeexSDK/Sources/Module/WXDarkSchemeModule.m
@@ -0,0 +1,58 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+#import "WXDarkSchemeModule.h"
+#import "WXSDKInstance_private.h"
+
+@implementation WXDarkSchemeModule
+{
+    WXModuleKeepAliveCallback _schemeChangedCallback;
+}
+
+@synthesize weexInstance;
+
+WX_EXPORT_METHOD_SYNC(@selector(getCurrentScheme))
+WX_EXPORT_METHOD(@selector(registerSchemeChangeListener:))
+WX_EXPORT_METHOD(@selector(unregisterSchemeChangeListener))
+
+- (NSString*)getCurrentScheme
+{
+    return [self.weexInstance isDarkScheme] ? @"dark" : @"light";
+}
+
+- (void)registerSchemeChangeListener:(WXModuleKeepAliveCallback)callback
+{
+    _schemeChangedCallback = callback;
+}
+
+- (void)onInstanceSchemeChanged
+{
+    if (_schemeChangedCallback) {
+        _schemeChangedCallback(@{@"instanceId": self.weexInstance.instanceId?:@"",
+                                 @"scheme": self.weexInstance.schemeName?:@"light"},
+                               YES);
+    }
+}
+
+- (void)unregisterSchemeChangeListener
+{
+    _schemeChangedCallback = nil;
+}
+
+@end
diff --git a/ios/sdk/WeexSDK/Sources/Module/WXModalUIModule.m b/ios/sdk/WeexSDK/Sources/Module/WXModalUIModule.m
index 408898e..48a3f4d 100644
--- a/ios/sdk/WeexSDK/Sources/Module/WXModalUIModule.m
+++ b/ios/sdk/WeexSDK/Sources/Module/WXModalUIModule.m
@@ -44,7 +44,6 @@
 
 @interface WXToastManager : NSObject
 
-@property (strong, nonatomic) NSMutableArray<WXToastInfo *> *toastQueue;
 @property (strong, nonatomic) UIView *toastingView;
 
 + (WXToastManager *)sharedManager;
@@ -58,7 +57,6 @@
     static dispatch_once_t onceToken;
     dispatch_once(&onceToken, ^{
         shareInstance = [[WXToastManager alloc] init];
-        shareInstance.toastQueue = [NSMutableArray new];
     });
     return shareInstance;
 }
@@ -122,16 +120,13 @@
         superView =  self.weexInstance.rootView;
     }
     UIView *toastView = [self toastViewForMessage:message superView:superView];
-    WXToastInfo *info = [WXToastInfo new];
-    info.instance = self.weexInstance;
-    info.toastView = toastView;
-    info.superView = superView;
-    info.duration = duration;
-    [[WXToastManager sharedManager].toastQueue addObject:info];
     
-    if (![WXToastManager sharedManager].toastingView) {
-        [self showToast:toastView superView:superView duration:duration];
+    UIView* toastingView = [WXToastManager sharedManager].toastingView;
+    if (toastingView) {
+        [toastingView removeFromSuperview];
+        [WXToastManager sharedManager].toastingView = nil;
     }
+    [self showToast:toastView superView:superView duration:duration];
 }
 
 - (UIView *)toastViewForMessage:(NSString *)message superView:(UIView *)superView
@@ -156,7 +151,10 @@
                                     )];
     
     CGPoint point = CGPointZero;
-    UIWindow *window = [[[UIApplication sharedApplication] windows] objectAtIndex:0];
+    UIWindow* window = [UIApplication sharedApplication].delegate.window;
+    if (window == NULL) {
+        window = [[[UIApplication sharedApplication] windows] firstObject];
+    }
     
     // adjust to screen orientation
     UIInterfaceOrientation orientation = (UIInterfaceOrientation)[[UIApplication sharedApplication] statusBarOrientation];
@@ -191,7 +189,7 @@
     
     [toastView addSubview:messageLabel];
     toastView.layer.cornerRadius = 7;
-    toastView.backgroundColor=[UIColor colorWithWhite:0 alpha:0.7];
+    toastView.backgroundColor = [UIColor colorWithWhite:0 alpha:0.7];
     
     return toastView;
 }
@@ -204,7 +202,6 @@
     
     [WXToastManager sharedManager].toastingView = toastView;
     [superView addSubview:toastView];
-    __weak typeof(self) weakSelf = self;
     [UIView animateWithDuration:0.2 delay:duration options:UIViewAnimationOptionCurveEaseInOut animations:^{
         toastView.transform = CGAffineTransformConcat(toastView.transform, CGAffineTransformMakeScale(0.8, 0.8)) ;
     } completion:^(BOOL finished) {
@@ -212,24 +209,8 @@
             toastView.alpha = 0;
         } completion:^(BOOL finished){
             [toastView removeFromSuperview];
-            [WXToastManager sharedManager].toastingView = nil;
-            
-            NSMutableArray *queue = [WXToastManager sharedManager].toastQueue;
-            if (queue.count > 0) {
-                [queue removeObjectAtIndex:0];
-                
-                // remove invalid toasts
-                for (NSInteger i = [queue count] - 1; i >= 0; i --) {
-                    WXToastInfo *info = queue[i];
-                    if (info.instance == nil) {
-                        [queue removeObjectAtIndex:i];
-                    }
-                }
-                
-                if (queue.count > 0) {
-                    WXToastInfo *info = [queue firstObject];
-                    [weakSelf showToast:info.toastView superView:info.superView duration:info.duration];
-                }
+            if ([WXToastManager sharedManager].toastingView == toastView) {
+                [WXToastManager sharedManager].toastingView = nil;
             }
         }];
     }];
diff --git a/ios/sdk/WeexSDK/Sources/Module/WXTimerModule.m b/ios/sdk/WeexSDK/Sources/Module/WXTimerModule.m
index e6c158f..2a50189 100644
--- a/ios/sdk/WeexSDK/Sources/Module/WXTimerModule.m
+++ b/ios/sdk/WeexSDK/Sources/Module/WXTimerModule.m
@@ -77,7 +77,6 @@
 
 @implementation WXTimerModule
 {
-    BOOL _tooManyTimersReported;
     NSMutableDictionary *_timers;
 }
 
@@ -162,6 +161,12 @@
 
 - (void)createTimerWithCallback:(NSString *)callbackID time:(NSTimeInterval)milliseconds target:(id)target selector:(SEL)selector shouldRepeat:(BOOL)shouldRepeat {
     
+    WXAssert(!isnan(milliseconds), @"Timer interval is NAN.");
+    if (isnan(milliseconds)) { //!OCLint
+        WXLogError(@"Create timer with NAN interval.");
+        return;
+    }
+    
     NSTimer *timer = [NSTimer scheduledTimerWithTimeInterval:milliseconds/1000.0f target:target selector:selector userInfo:nil repeats:shouldRepeat];
     [[NSRunLoop mainRunLoop] addTimer:timer forMode:NSRunLoopCommonModes];
     
@@ -178,14 +183,6 @@
                 }
             }
             [_timers removeObjectsForKeys:invalidTimerIds];
-            
-            // If alive timer count still exceeds 30, we report once for this page.
-            if ([_timers count] > 30) {
-                if (!_tooManyTimersReported) {
-                    [WXExceptionUtils commitCriticalExceptionRT:self.weexInstance.instanceId errCode:[NSString stringWithFormat:@"%d", WX_KEY_EXCEPTION_TOO_MANY_TIMERS] function:@"" exception:@"Too many timers." extParams:nil];
-                    _tooManyTimersReported = YES;
-                }
-            }
         }
     }
 }
diff --git a/ios/sdk/WeexSDK/Sources/Module/WXTransition.mm b/ios/sdk/WeexSDK/Sources/Module/WXTransition.mm
index 8bb616d..7613e9e 100644
--- a/ios/sdk/WeexSDK/Sources/Module/WXTransition.mm
+++ b/ios/sdk/WeexSDK/Sources/Module/WXTransition.mm
@@ -30,6 +30,7 @@
 #import "WXAssert.h"
 #import "WXSDKInstance_private.h"
 #import "WXLength.h"
+#import "WXDarkSchemeProtocol.h"
 
 @implementation WXTransitionInfo
 @end
@@ -82,6 +83,8 @@
                                                            @"bottom": @(WXTransitionOptionsBottom),
                                                            @"top": @(WXTransitionOptionsTop),
                                                            @"backgroundColor": @(WXTransitionOptionsBackgroundColor),
+                                                           @"weexDarkSchemeBackgroundColor": @(WXTransitionOptionsBackgroundColor),
+                                                           @"weexLightSchemeBackgroundColor": @(WXTransitionOptionsBackgroundColor),
                                                            @"transform": @(WXTransitionOptionsTransform),
                                                            @"opacity": @(WXTransitionOptionsOpacity)
                                                            };
@@ -106,24 +109,66 @@
     _filterStyles = _filterStyles ?:[NSMutableDictionary new];
     _oldFilterStyles = _oldFilterStyles ?: [NSMutableDictionary new];
     NSMutableDictionary *futileStyles = [NSMutableDictionary new];
+    NSDictionary* componentRawStyles = targetComponent.styles;
+    
+    BOOL isDarkScheme = [targetComponent.weexInstance isDarkScheme];
+    BOOL updatingDarkSchemeBackgroundColor = styles[@"weexDarkSchemeBackgroundColor"] != nil;
+    BOOL updatingLightSchemeBackgroundColor = styles[@"weexLightSchemeBackgroundColor"] != nil;
     
     for (NSString *key in styles) {
         if (self.transitionOptions & [self transitionOptionsFromString:key]) {
+            if ([key isEqualToString:@"backgroundColor"]) {
+                if (isDarkScheme && (updatingDarkSchemeBackgroundColor ||
+                                    componentRawStyles[@"weexDarkSchemeBackgroundColor"] != nil)) {
+                    /* Updating "darkSchemeBackgroundColor" in dark mode,
+                     or this component has dark bg color explicitly defined in styels.
+                     We ignore transition animation for "backgroundColor" */
+                    [futileStyles setObject:styles[key] forKey:key];
+                    continue;
+                }
+                else if (!isDarkScheme && (updatingLightSchemeBackgroundColor ||
+                                          componentRawStyles[@"weexLightSchemeBackgroundColor"] != nil)) {
+                    [futileStyles setObject:styles[key] forKey:key];
+                    continue;
+                }
+            }
+            else if ([key isEqualToString:@"weexDarkSchemeBackgroundColor"]) {
+                if (!isDarkScheme) {
+                    /* Do not do animation for "darkSchemeBackgroundColor" in light mode. */
+                    [futileStyles setObject:styles[key] forKey:key];
+                    continue;
+                }
+            }
+            else if ([key isEqualToString:@"weexLightSchemeBackgroundColor"]){
+                if (isDarkScheme) {
+                    [futileStyles setObject:styles[key] forKey:key];
+                    continue;
+                }
+            }
+            
             [_filterStyles setObject:styles[key] forKey:key];
             if (![key isEqualToString:@"transform"]) {
                 if (!isRunning) {
-                    /* style value may not be in component.styles, so we must get
-                     value from layout and convert it to style value. */
-                    id styleValue = targetComponent.styles[key];
-                    if (styleValue == nil) {
+                    // Get animation 'from' value from raw styles.
+                    id styleValue = componentRawStyles[key];
+                    if ([key isEqualToString:@"backgroundColor"] ||
+                        [key isEqualToString:@"weexDarkSchemeBackgroundColor"] ||
+                        [key isEqualToString:@"weexLightSchemeBackgroundColor"]) {
+                        if (styleValue == nil) {
+                            // background color is transparent by default.
+                            styleValue = @"transparent";
+                        }
+                    }
+                    else if (styleValue == nil) {
+                        /* Flex styles may not be in component.styles, so we must get
+                         value from layout and convert it to style value. */
                         styleValue = [targetComponent convertLayoutValueToStyleValue:key];
                     }
                     [_oldFilterStyles setObject:styleValue forKey:key];
                 }
             }
         }
-        else
-        {
+        else {
             [futileStyles setObject:styles[key] forKey:key];
         }
     }
@@ -131,7 +176,7 @@
 
     _targetComponent = targetComponent;
     NSMutableDictionary *componentStyles = [NSMutableDictionary dictionaryWithDictionary:styles];
-    [componentStyles addEntriesFromDictionary:targetComponent.styles];
+    [componentStyles addEntriesFromDictionary:componentRawStyles];
 
     _transitionDuration = componentStyles[kWXTransitionDuration] ? [WXConvert CGFloat:componentStyles[kWXTransitionDuration]] : 0;
     _transitionDelay = componentStyles[kWXTransitionDelay] ? [WXConvert CGFloat:componentStyles[kWXTransitionDelay]] : 0;
@@ -200,10 +245,22 @@
         if (!_propertyArray) {
             _propertyArray = [NSMutableArray new];
         }
-        if ([singleProperty isEqualToString:@"backgroundColor"]) {
+        if ([singleProperty isEqualToString:@"backgroundColor"] ||
+            [singleProperty isEqualToString:@"weexDarkSchemeBackgroundColor"] ||
+            [singleProperty isEqualToString:@"weexLightSchemeBackgroundColor"]) {
+            UIColor* fromColor = [WXConvert UIColor:_oldFilterStyles[singleProperty]];
+            UIColor* toColor = [WXConvert UIColor:_filterStyles[singleProperty]];
+            if ([_targetComponent.weexInstance isDarkScheme] &&
+                _targetComponent.invertForDarkScheme &&
+                [singleProperty isEqualToString:@"backgroundColor"]) {
+                // Invert color
+                fromColor = [[WXSDKInstance darkSchemeColorHandler] getInvertedColorFor:fromColor ofScene:[_targetComponent colorSceneType] withDefault:fromColor];
+                toColor = [[WXSDKInstance darkSchemeColorHandler] getInvertedColorFor:toColor ofScene:[_targetComponent colorSceneType] withDefault:toColor];
+            }
+            
             WXTransitionInfo *info = [WXTransitionInfo new];
-            info.fromValue = [self _dealWithColor:[WXConvert UIColor:_oldFilterStyles[singleProperty]]];
-            info.toValue = [self _dealWithColor:[WXConvert UIColor:_filterStyles[singleProperty]]];
+            info.fromValue = [self _dealWithColor:fromColor];
+            info.toValue = [self _dealWithColor:toColor];
             info.perValue = [self _calculatePerColorRGB1:info.toValue RGB2:info.fromValue];
             info.propertyName = singleProperty;
             [_propertyArray addObject:info];
@@ -337,6 +394,7 @@
                                @([info.fromValue[3] floatValue] + [info.perValue[3] floatValue] * per)];
             UIColor *color = [UIColor colorWithRed:[array[0] floatValue] green:[array[1] floatValue] blue:[array[2] floatValue] alpha:[array[3] floatValue]];
             WXPerformBlockOnMainThread(^{
+                // Here we do not need to consider about dark mode.
                 _targetComponent.view.backgroundColor = color;
                 [_targetComponent.view setNeedsDisplay];
             });
diff --git a/ios/sdk/WeexSDK/Sources/Protocol/WXDarkSchemeProtocol.h b/ios/sdk/WeexSDK/Sources/Protocol/WXDarkSchemeProtocol.h
new file mode 100644
index 0000000..0689bd4
--- /dev/null
+++ b/ios/sdk/WeexSDK/Sources/Protocol/WXDarkSchemeProtocol.h
@@ -0,0 +1,49 @@
+/*
+ * 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
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * 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.
+ */
+
+#import <WeexSDK/WXModuleProtocol.h>
+
+NS_ASSUME_NONNULL_BEGIN
+
+@protocol WXDarkSchemeProtocol <WXModuleProtocol>
+
+/**
+ Return YES so that Weex root component will be enabled for 'invertForDarkScheme' property.
+*/
+- (BOOL)defaultInvertValueForRootComponent;
+
+/**
+After any view of Weex component is created. Callback dark scheme handler to provide a
+ chance to configure the view.
+*/
+- (void)configureView:(UIView*_Nonnull)view ofComponent:(WXComponent*_Nonnull)component;
+
+/**
+ Get inverted color in dark mode for input color with scene hint.
+
+ @param color Input color.
+ @param scene Scene indicating the color usage.
+ @param defaultColor If no inverted one matches, return the default color.
+ @return Inverted color.
+ */
+- (UIColor *_Nullable)getInvertedColorFor:(UIColor *_Nonnull)color ofScene:(WXColorScene)scene withDefault:(UIColor *_Nullable)defaultColor;
+
+@end
+
+NS_ASSUME_NONNULL_END
diff --git a/ios/sdk/WeexSDK/Sources/Protocol/WXDestroyProtocol.h b/ios/sdk/WeexSDK/Sources/Protocol/WXDestroyProtocol.h
deleted file mode 100644
index 1875e79..0000000
--- a/ios/sdk/WeexSDK/Sources/Protocol/WXDestroyProtocol.h
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * 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
- * 
- *   http://www.apache.org/licenses/LICENSE-2.0
- * 
- * 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.
- */
-
-#import <Foundation/Foundation.h>
-
-@protocol WXDestroyProtocol <NSObject>
-
-/**
- *  @abstract execute unload function before dealloc
- */
-- (void)unload;
-
-@end
diff --git a/ios/sdk/WeexSDK/Sources/Utility/WXConvertUtility.h b/ios/sdk/WeexSDK/Sources/Utility/WXConvertUtility.h
index a5e64f5..2cd8f9b 100644
--- a/ios/sdk/WeexSDK/Sources/Utility/WXConvertUtility.h
+++ b/ios/sdk/WeexSDK/Sources/Utility/WXConvertUtility.h
@@ -47,6 +47,14 @@
 
 void ConvertToCString(id _Nonnull obj, void (^ _Nonnull callback)(const char* _Nullable));
 
+extern "C" {
+    void SetConvertCurrentPage(NSString* _Nonnull pageId);
+    void ConvertSwitches(BOOL isIOS13, BOOL invalidJSONObjectUseMRC, BOOL alwaysUseMRC);
+}
+
+#else
+void SetConvertCurrentPage(NSString* _Nonnull pageId);
+void ConvertSwitches(BOOL isIOS13, BOOL invalidJSONObjectUseMRC, BOOL alwaysUseMRC);
 #endif
 
 #endif
diff --git a/ios/sdk/WeexSDK/Sources/Utility/WXConvertUtility.mm b/ios/sdk/WeexSDK/Sources/Utility/WXConvertUtility.mm
index bec9105..65d035d 100644
--- a/ios/sdk/WeexSDK/Sources/Utility/WXConvertUtility.mm
+++ b/ios/sdk/WeexSDK/Sources/Utility/WXConvertUtility.mm
@@ -20,10 +20,32 @@
 #import "WXConvertUtility.h"
 #import "WXLog.h"
 #import "WXAssert.h"
+#import "WXExceptionUtils.h"
+#import "WXSDKError.h"
+
 #include <vector>
 #include <string>
 
 static NSString* const JSONSTRING_SUFFIX = @"\t\n\t\r";
+static NSString* const OBJC_MRC_SUFFIX = @"\t\t\n\r";
+
+static BOOL bIsIOS13 = NO;
+static BOOL bUseMRCForInvalidJSONObject = NO;
+static BOOL bAlwaysUseMRC = NO;
+
+static NSString* sCurrentPage = nil;
+
+void SetConvertCurrentPage(NSString* pageId)
+{
+    sCurrentPage = pageId;
+}
+
+void ConvertSwitches(BOOL isIOS13, BOOL invalidJSONObjectUseMRC, BOOL alwaysUseMRC)
+{
+    bIsIOS13 = isIOS13;
+    bUseMRCForInvalidJSONObject = invalidJSONObjectUseMRC;
+    bAlwaysUseMRC = alwaysUseMRC;
+}
 
 #if 0
 
@@ -78,6 +100,28 @@
             _detectObjectRecursion(object, nodes);
 #endif
             
+            if (bAlwaysUseMRC) {
+                return [NSString stringWithFormat:@"%p%@", (__bridge_retained void*)object, OBJC_MRC_SUFFIX];
+            }
+            
+            if (bIsIOS13) {
+                if (![NSJSONSerialization isValidJSONObject:object]) {
+                    [WXExceptionUtils commitCriticalExceptionRT:sCurrentPage
+                                                        errCode:[NSString stringWithFormat:@"%d", WX_KEY_EXCEPTION_INVALID_JSON_OBJECT]
+                                                       function:@""
+                                                      exception:@"Invalid JSON object."
+                                                      extParams:nil];
+                    
+                    // Report for instance.
+                    if (bUseMRCForInvalidJSONObject) {
+                        return [NSString stringWithFormat:@"%p%@", (__bridge_retained void*)object, OBJC_MRC_SUFFIX];
+                    }
+                    else {
+                        return nil;
+                    }
+                }
+            }
+            
             NSError *error = nil;
             NSData *data = [NSJSONSerialization dataWithJSONObject:object
                                                            options:0
@@ -126,6 +170,15 @@
             WXAssert(NO, @"Fail to convert json to object. %@", exception);
         }
     }
+    else if ([s hasSuffix:OBJC_MRC_SUFFIX]) {
+        NSScanner* scanner = [NSScanner scannerWithString:s];
+        unsigned long long address = 0;
+        [scanner scanHexLongLong:&address];
+        if (address != 0) {
+            return (__bridge_transfer id)((void*)address);
+        }
+    }
+    
     return s; // return s instead
 }
 
diff --git a/ios/sdk/WeexSDK/Sources/Utility/WXDefine.h b/ios/sdk/WeexSDK/Sources/Utility/WXDefine.h
index a9b9dcf..c687ab0 100644
--- a/ios/sdk/WeexSDK/Sources/Utility/WXDefine.h
+++ b/ios/sdk/WeexSDK/Sources/Utility/WXDefine.h
@@ -20,7 +20,7 @@
 #ifndef __WX_DEFINE_H__
 #define __WX_DEFINE_H__
 
-#define WX_SDK_VERSION @"0.24.0"
+#define WX_SDK_VERSION @"0.28.0"
 
 #if defined(__cplusplus)
 #define WX_EXTERN extern "C" __attribute__((visibility("default")))
diff --git a/ios/sdk/WeexSDK/Sources/Utility/WXUtility.h b/ios/sdk/WeexSDK/Sources/Utility/WXUtility.h
index 61eeccd..91d3365 100644
--- a/ios/sdk/WeexSDK/Sources/Utility/WXUtility.h
+++ b/ios/sdk/WeexSDK/Sources/Utility/WXUtility.h
@@ -131,12 +131,22 @@
 + (void)performBlock:(void (^_Nonnull)(void))block onThread:(NSThread *_Nonnull)thread;
 
 /**
+ * @abstract Check if system is in dark mode.
+ *
+ * @return Boolean
+ *
+ */
++ (BOOL)isSystemInDarkScheme;
+
+/**
  * @abstract Returns the environment of current application, you can get some necessary properties such as appVersion、sdkVersion、appName etc.
  *
  * @return A dictionary object which contains these properties.
  *
  */
 + (NSDictionary *_Nonnull)getEnvironment;
++ (NSDictionary *_Nonnull)getEnvironmentForJSContext;
++ (BOOL)isEnvironmentUsingDarkScheme;
 
 + (NSDictionary *_Nonnull)getDebugEnvironment;
 
@@ -502,10 +512,20 @@
  */
 + (NSData *_Nonnull)base64DictToData:(NSDictionary *_Nullable)base64Dict;
 
+/**
+*  @abstract Switch for RTL.
+*
+*/
 + (void)setEnableRTLLayoutDirection:(BOOL)value;
-
 + (BOOL)enableRTLLayoutDirection;
 
+/**
+*  @abstract Switch for dark mode support.
+*
+*/
++ (void)setDarkSchemeSupportEnable:(BOOL)value;
++ (BOOL)isDarkSchemeSupportEnabled;
+
 + (long) getUnixFixTimeMillis;
 
 + (NSArray<NSString *> *_Nullable)extractPropertyNamesOfJSValueObject:(JSValue *_Nullable)jsvalue;
diff --git a/ios/sdk/WeexSDK/Sources/Utility/WXUtility.m b/ios/sdk/WeexSDK/Sources/Utility/WXUtility.m
index 6ec4223..3e2eb17 100644
--- a/ios/sdk/WeexSDK/Sources/Utility/WXUtility.m
+++ b/ios/sdk/WeexSDK/Sources/Utility/WXUtility.m
@@ -43,6 +43,7 @@
 #define KEY_USERNAME_PASSWORD  @"com.taobao.Weex.weex123456"
 
 static BOOL enableRTLLayoutDirection = YES;
+static BOOL isDarkSchemeSupportEnabled = YES;
 
 void WXPerformBlockOnMainThread(void (^ _Nonnull block)(void))
 {
@@ -163,8 +164,29 @@
     return [UIView userInterfaceLayoutDirectionForSemanticContentAttribute:UISemanticContentAttributeUnspecified] == UIUserInterfaceLayoutDirectionRightToLeft ? WXLayoutDirectionRTL : WXLayoutDirectionLTR;
 }
 
++ (BOOL)isSystemInDarkScheme
+{
+    if (@available(iOS 13.0, *)) {
+        __block BOOL result = NO;
+        WXPerformBlockSyncOnMainThread(^{
+#ifdef __IPHONE_13_0
+            if ([UITraitCollection currentTraitCollection].userInterfaceStyle == UIUserInterfaceStyleDark) {
+                result = YES;
+            }
+#endif
+        });
+        return result;
+    }
+    return NO;
+}
+
 + (NSDictionary *)getEnvironment
 {
+    NSString* currentScheme = @"light";
+    if ([WXUtility isDarkSchemeSupportEnabled]) {
+        currentScheme = [self isSystemInDarkScheme] ? @"dark" : @"light";
+    }
+    
     NSString *platform = @"iOS";
     NSString *sysVersion = [[UIDevice currentDevice] systemVersion] ?: @"";
     NSString *weexVersion = WX_SDK_VERSION;
@@ -187,7 +209,8 @@
                                     @"deviceWidth":@(deviceWidth * scale),
                                     @"deviceHeight":@(deviceHeight * scale),
                                     @"scale":@(scale),
-                                    @"layoutDirection": [self getEnvLayoutDirection] == WXLayoutDirectionRTL ? @"rtl" : @"ltr"
+                                    @"layoutDirection": [self getEnvLayoutDirection] == WXLayoutDirectionRTL ? @"rtl" : @"ltr",
+                                    @"scheme": currentScheme
                                 }];
     
     if ([[[UIDevice currentDevice] systemVersion] integerValue] >= 11) {
@@ -211,6 +234,20 @@
     return data;
 }
 
+static BOOL gIsEnvironmentUsingDarkScheme = NO;
+
++ (NSDictionary *_Nonnull)getEnvironmentForJSContext
+{
+    NSDictionary* result = [self getEnvironment];
+    gIsEnvironmentUsingDarkScheme = [result[@"scheme"] isEqualToString:@"dark"];
+    return result;
+}
+
++ (BOOL)isEnvironmentUsingDarkScheme
+{
+    return gIsEnvironmentUsingDarkScheme;
+}
+
 + (NSDictionary *)getDebugEnvironment {
     NSString *platform = @"iOS";
     NSString *weexVersion = [WXSDKEngine SDKEngineVersion];
@@ -793,6 +830,18 @@
     return enableRTLLayoutDirection;
 }
 
+#pragma mark - Dark scheme
+
++ (void)setDarkSchemeSupportEnable:(BOOL)value
+{
+    isDarkSchemeSupportEnabled = value;
+}
+
++ (BOOL)isDarkSchemeSupportEnabled
+{
+    return isDarkSchemeSupportEnabled;
+}
+
 #pragma mark - get deviceID
 + (NSString *)getDeviceID {
     NSMutableDictionary *usernamepasswordKVPairs = (NSMutableDictionary *)[self load:KEY_USERNAME_PASSWORD];
diff --git a/ios/sdk/WeexSDK/Sources/Utility/WXVersion.m b/ios/sdk/WeexSDK/Sources/Utility/WXVersion.m
index b283b3a..002b48b 100644
--- a/ios/sdk/WeexSDK/Sources/Utility/WXVersion.m
+++ b/ios/sdk/WeexSDK/Sources/Utility/WXVersion.m
@@ -1,29 +1,27 @@
 /*
- * 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
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * 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.
+* 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
+*
+*   http://www.apache.org/licenses/LICENSE-2.0
+*
+* 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.
  */
 
 #import "WXVersion.h"
 #import "WXDefine.h"
 
-
-static const char* WeexSDKBuildTime = "2019-08-26 08:28:24 UTC";
-static const unsigned long WeexSDKBuildTimestamp = 1566808104;
-
+static const char* WeexSDKBuildTime = "2019-10-09 13:07:35 UTC";
+static const unsigned long WeexSDKBuildTimestamp = 1570626455;
 
 NSString* GetWeexSDKVersion(void)
 {
diff --git a/ios/sdk/WeexSDK/Sources/View/WXComponent+ViewManagement.mm b/ios/sdk/WeexSDK/Sources/View/WXComponent+ViewManagement.mm
index 3d97548..4d058ef 100644
--- a/ios/sdk/WeexSDK/Sources/View/WXComponent+ViewManagement.mm
+++ b/ios/sdk/WeexSDK/Sources/View/WXComponent+ViewManagement.mm
@@ -67,6 +67,22 @@
     }\
 } while(0);
 
+#define WX_BOARD_RADIUS_DARK_SCHEME_COLOR_RESET_ALL(key)\
+do {\
+    if (styles && [styles containsObject:@#key]) {\
+        _darkSchemeBorderTopColor = _darkSchemeBorderLeftColor = _darkSchemeBorderRightColor = _darkSchemeBorderBottomColor = [UIColor blackColor];\
+        [self setNeedsDisplay];\
+    }\
+} while(0);
+
+#define WX_BOARD_RADIUS_LIGHT_SCHEME_COLOR_RESET_ALL(key)\
+do {\
+    if (styles && [styles containsObject:@#key]) {\
+        _lightSchemeBorderTopColor = _lightSchemeBorderLeftColor = _lightSchemeBorderRightColor = _lightSchemeBorderBottomColor = [UIColor blackColor];\
+        [self setNeedsDisplay];\
+    }\
+} while(0);
+
 #define WX_BOARD_COLOR_RESET(key)\
 do {\
     if (styles && [styles containsObject:@#key]) {\
@@ -174,8 +190,16 @@
 
 - (void)_initViewPropertyWithStyles:(NSDictionary *)styles
 {
-    _backgroundColor = styles[@"backgroundColor"] ? [WXConvert UIColor:styles[@"backgroundColor"]] : [UIColor clearColor];
+    self.styleBackgroundColor = styles[@"backgroundColor"] ? [WXConvert UIColor:styles[@"backgroundColor"]] : [UIColor clearColor];
+    if (styles[@"weexDarkSchemeBackgroundColor"]) {
+        self.darkSchemeBackgroundColor = [WXConvert UIColor:styles[@"weexDarkSchemeBackgroundColor"]];
+    }
+    if (styles[@"weexLightSchemeBackgroundColor"]) {
+        self.lightSchemeBackgroundColor = [WXConvert UIColor:styles[@"weexLightSchemeBackgroundColor"]];
+    }
     _backgroundImage = styles[@"backgroundImage"] ? [WXConvert NSString:styles[@"backgroundImage"]]: nil;
+    _darkSchemeBackgroundImage = styles[@"weexDarkSchemeBackgroundImage"] ? [WXConvert NSString:styles[@"weexDarkSchemeBackgroundImage"]] : nil;
+    _lightSchemeBackgroundImage = styles[@"weexLightSchemeBackgroundImage"] ? [WXConvert NSString:styles[@"weexLightSchemeBackgroundImage"]] : nil;
     _opacity = styles[@"opacity"] ? [WXConvert CGFloat:styles[@"opacity"]] : 1.0;
     _clipToBounds = styles[@"overflow"] ? [WXConvert WXClipType:styles[@"overflow"]] : NO;
     _visibility = styles[@"visibility"] ? [WXConvert WXVisibility:styles[@"visibility"]] : WXVisibilityShow;
@@ -184,8 +208,11 @@
     [[WXTransform alloc] initWithCSSValue:[WXConvert NSString:styles[@"transform"]] origin:[WXConvert NSString:styles[@"transformOrigin"]] instance:self.weexInstance] :
     [[WXTransform alloc] initWithCSSValue:nil origin:nil instance:self.weexInstance];
     _boxShadow = styles[@"boxShadow"]?[WXConvert WXBoxShadow:styles[@"boxShadow"] scaleFactor:self.weexInstance.pixelScaleFactor]:nil;
-    if (_boxShadow) {
-        _lastBoxShadow = _boxShadow;
+    if (styles[@"weexDarkSchemeBoxShadow"]) {
+        _darkSchemeBoxShadow = [WXConvert WXBoxShadow:styles[@"weexDarkSchemeBoxShadow"] scaleFactor:self.weexInstance.pixelScaleFactor];
+    }
+    if (styles[@"weexLightSchemeBoxShadow"]) {
+        _lightSchemeBoxShadow = [WXConvert WXBoxShadow:styles[@"weexLightSchemeBoxShadow"] scaleFactor:self.weexInstance.pixelScaleFactor];
     }
 }
 
@@ -193,7 +220,13 @@
 {
     WX_CHECK_COMPONENT_TYPE(self.componentType)
     if (styles[@"backgroundColor"]) {
-        _backgroundColor = [WXConvert UIColor:styles[@"backgroundColor"]];
+        self.styleBackgroundColor = [WXConvert UIColor:styles[@"backgroundColor"]];
+    }
+    if (styles[@"weexDarkSchemeBackgroundColor"]) {
+        self.darkSchemeBackgroundColor = [WXConvert UIColor:styles[@"weexDarkSchemeBackgroundColor"]];
+    }
+    if (styles[@"weexLightSchemeBackgroundColor"]) {
+        self.lightSchemeBackgroundColor = [WXConvert UIColor:styles[@"weexLightSchemeBackgroundColor"]];
     }
     if (styles[@"opacity"]) {
         _opacity = [WXConvert CGFloat:styles[@"opacity"]];
@@ -204,20 +237,53 @@
 {
     WX_CHECK_COMPONENT_TYPE(self.componentType)
     if (styles[@"boxShadow"]) {
-        _lastBoxShadow = _boxShadow;
         _boxShadow = styles[@"boxShadow"]?[WXConvert WXBoxShadow:styles[@"boxShadow"] scaleFactor:self.weexInstance.pixelScaleFactor]:nil;
-        [self configBoxShadow:_boxShadow];
+    }
+    if (styles[@"weexDarkSchemeBoxShadow"]) {
+        _darkSchemeBoxShadow = [WXConvert WXBoxShadow:styles[@"weexDarkSchemeBoxShadow"] scaleFactor:self.weexInstance.pixelScaleFactor];
+    }
+    if (styles[@"weexLightSchemeBoxShadow"]) {
+        _lightSchemeBoxShadow = [WXConvert WXBoxShadow:styles[@"weexLightSchemeBoxShadow"] scaleFactor:self.weexInstance.pixelScaleFactor];
+    }
+    if (styles[@"boxShadow"] || styles[@"weexDarkSchemeBoxShadow"] || styles[@"weexLightSchemeBoxShadow"]) {
+        WXBoxShadow* usingBoxShadow = [self _chooseBoxShadow];
+        if (usingBoxShadow) {
+            _lastBoxShadow = usingBoxShadow;
+            [self configBoxShadow:usingBoxShadow];
+        }
         [self setNeedsDisplay];
     }
     
     if (styles[@"backgroundColor"]) {
-        _backgroundColor = [WXConvert UIColor:styles[@"backgroundColor"]];
+        self.styleBackgroundColor = [WXConvert UIColor:styles[@"backgroundColor"]];
+        [self setNeedsDisplay];
+    }
+    
+    if (styles[@"weexDarkSchemeBackgroundColor"]) {
+        self.darkSchemeBackgroundColor = [WXConvert UIColor:styles[@"weexDarkSchemeBackgroundColor"]];
+        [self setNeedsDisplay];
+    }
+    
+    if (styles[@"weexLightSchemeBackgroundColor"]) {
+        self.lightSchemeBackgroundColor = [WXConvert UIColor:styles[@"weexLightSchemeBackgroundColor"]];
         [self setNeedsDisplay];
     }
     
     if (styles[@"backgroundImage"]) {
-        _backgroundImage = styles[@"backgroundImage"] ? [WXConvert NSString:styles[@"backgroundImage"]]: nil;
-        if (_backgroundImage) {
+        _backgroundImage = [WXConvert NSString:styles[@"backgroundImage"]];
+    }
+    
+    if (styles[@"weexDarkSchemeBackgroundImage"]) {
+        _darkSchemeBackgroundImage = [WXConvert NSString:styles[@"weexDarkSchemeBackgroundImage"]];
+    }
+    if (styles[@"weexLightSchemeBackgroundImage"]) {
+        _lightSchemeBackgroundImage = [WXConvert NSString:styles[@"weexLightSchemeBackgroundImage"]];
+    }
+    
+    if (styles[@"backgroundImage"] ||
+        styles[@"weexDarkSchemeBackgroundImage"] ||
+        styles[@"weexLightSchemeBackgroundImage"]) {
+        if (_backgroundImage || _darkSchemeBackgroundImage || _lightSchemeBackgroundImage) {
             [self setGradientLayer];
         }
     }
@@ -302,21 +368,61 @@
     WX_BOARD_COLOR_RESET(borderLeftColor);
     WX_BOARD_COLOR_RESET(borderRightColor);
     WX_BOARD_COLOR_RESET(borderBottomColor);
+    
+    WX_BOARD_RADIUS_DARK_SCHEME_COLOR_RESET_ALL(darkSchemeBorderColor);
+    WX_BOARD_COLOR_RESET(darkSchemeBorderTopColor);
+    WX_BOARD_COLOR_RESET(darkSchemeBorderLeftColor);
+    WX_BOARD_COLOR_RESET(darkSchemeBorderRightColor);
+    WX_BOARD_COLOR_RESET(darkSchemeBorderBottomColor);
+    
+    WX_BOARD_RADIUS_LIGHT_SCHEME_COLOR_RESET_ALL(lightSchemeBorderColor);
+    WX_BOARD_COLOR_RESET(lightSchemeBorderTopColor);
+    WX_BOARD_COLOR_RESET(lightSchemeBorderLeftColor);
+    WX_BOARD_COLOR_RESET(lightSchemeBorderRightColor);
+    WX_BOARD_COLOR_RESET(lightSchemeBorderBottomColor);
 }
 
 - (void)_resetStyles:(NSArray *)styles
 {
     if (styles && [styles containsObject:@"backgroundColor"]) {
-        _backgroundColor = [UIColor clearColor];
+        self.styleBackgroundColor = [UIColor clearColor];
         [self setNeedsDisplay];
     }
+    if (styles && [styles containsObject:@"weexDarkSchemeBackgroundColor"]) {
+        self.darkSchemeBackgroundColor = nil;
+        [self setNeedsDisplay];
+    }
+    if (styles && [styles containsObject:@"weexLightSchemeBackgroundColor"]) {
+        self.lightSchemeBackgroundColor = nil;
+        [self setNeedsDisplay];
+    }
+    
     if (styles && [styles containsObject:@"boxShadow"]) {
         _lastBoxShadow = _boxShadow;
         _boxShadow = nil;
         [self setNeedsDisplay];
     }
+    if (styles && [styles containsObject:@"weexDarkSchemeBoxShadow"]) {
+        _darkSchemeBoxShadow = nil;
+        [self setNeedsDisplay];
+    }
+    if (styles && [styles containsObject:@"weexLightSchemeBoxShadow"]) {
+        _lightSchemeBoxShadow = nil;
+        [self setNeedsDisplay];
+    }
+    
     if (styles && [styles containsObject:@"backgroundImage"]) {
         _backgroundImage = nil;
+    }
+    if (styles && [styles containsObject:@"weexDarkSchemeBackgroundImage"]) {
+        _darkSchemeBackgroundImage = nil;
+    }
+    if (styles && [styles containsObject:@"weexLightSchemeBackgroundImage"]) {
+        _lightSchemeBackgroundImage = nil;
+    }
+    if (styles && ([styles containsObject:@"backgroundImage"] ||
+                   [styles containsObject:@"weexDarkSchemeBackgroundImage"] ||
+                   [styles containsObject:@"weexLightSchemeBackgroundImage"])) {
         [self setGradientLayer];
     }
     
diff --git a/ios/sdk/WeexSDK/Sources/View/WXRootView.m b/ios/sdk/WeexSDK/Sources/View/WXRootView.m
index 3cc8a36..8651ec6 100644
--- a/ios/sdk/WeexSDK/Sources/View/WXRootView.m
+++ b/ios/sdk/WeexSDK/Sources/View/WXRootView.m
@@ -21,8 +21,14 @@
 #import "WXSDKInstance.h"
 #import "WXPageEventNotifyEvent.h"
 #import "WXSDKEngine.h"
+#import "WXUtility.h"
+#import "WXBridgeManager.h"
 
 @interface WXRootView()
+{
+    BOOL _hasFirstTraitCollectionChange;
+    BOOL _allowFirstTraitCollectionChange;
+}
 
 @property (nonatomic, assign) BOOL mHasEvent;
 
@@ -59,4 +65,50 @@
     return _mHasEvent;
 }
 
+- (void)checkUpdateEnvironment:(NSInteger)currentStyle
+{
+    if (@available(iOS 13.0, *)) {
+        if (([WXUtility isEnvironmentUsingDarkScheme] && (UIUserInterfaceStyle)currentStyle == UIUserInterfaceStyleLight) ||
+            (![WXUtility isEnvironmentUsingDarkScheme] && (UIUserInterfaceStyle)currentStyle == UIUserInterfaceStyleDark)) {
+            // Update scheme value in JS environment.
+            [WXUtility getEnvironmentForJSContext]; // Update gIsEnvironmentUsingDarkScheme
+            [[WXBridgeManager sharedManager] resetEnvironment];
+        }
+    }
+}
+
+- (void)traitCollectionDidChange:(UITraitCollection *)previousTraitCollection
+{
+    [super traitCollectionDidChange:previousTraitCollection];
+    
+    if (@available(iOS 13.0, *)) {
+        // When entering background system may call back change twice.. We ignore the first one.
+        UIUserInterfaceStyle currentStyle = self.traitCollection.userInterfaceStyle;
+        if (currentStyle != previousTraitCollection.userInterfaceStyle) {
+            if (_hasFirstTraitCollectionChange) {
+                _allowFirstTraitCollectionChange = NO;
+                [self checkUpdateEnvironment:(NSInteger)currentStyle];
+                [self.instance setCurrentSchemeName:currentStyle == UIUserInterfaceStyleDark ? @"dark" : @"light"];
+            }
+            else {
+                __weak WXRootView* weakSelf = self;
+                _hasFirstTraitCollectionChange = YES;
+                _allowFirstTraitCollectionChange = YES;
+                dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.2 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
+                    __strong WXRootView* strongSelf = weakSelf;
+                    if (strongSelf) {
+                        if (strongSelf->_allowFirstTraitCollectionChange) {
+                            if (strongSelf.instance) {
+                                [self checkUpdateEnvironment:(NSInteger)currentStyle];
+                                [strongSelf.instance setCurrentSchemeName:currentStyle == UIUserInterfaceStyleDark ? @"dark" : @"light"];
+                            }
+                        }
+                        strongSelf->_hasFirstTraitCollectionChange = NO;
+                    }
+                });
+            }
+        }
+    }
+}
+
 @end
diff --git a/ios/sdk/WeexSDK/Sources/WeexSDK.h b/ios/sdk/WeexSDK/Sources/WeexSDK.h
index 8e5f6f4..05807f0 100644
--- a/ios/sdk/WeexSDK/Sources/WeexSDK.h
+++ b/ios/sdk/WeexSDK/Sources/WeexSDK.h
@@ -73,6 +73,7 @@
 #import <WeexSDK/WXDefine.h>
 #import <WeexSDK/WXDebugTool.h>
 #import <WeexSDK/WXDataRenderHandler.h>
+#import <WeexSDK/WXDarkSchemeProtocol.h>
 #import <WeexSDK/WXConvertUtility.h>
 #import <WeexSDK/WXConvert.h>
 #import <WeexSDK/WXConfigCenterProtocol.h>
diff --git a/package-lock.json b/package-lock.json
index a16a0f3..3d9777a 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -4,11 +4,121 @@
   "lockfileVersion": 1,
   "requires": true,
   "dependencies": {
+    "@babel/polyfill": {
+      "version": "7.6.0",
+      "resolved": "https://registry.npmjs.org/@babel/polyfill/-/polyfill-7.6.0.tgz",
+      "integrity": "sha512-q5BZJI0n/B10VaQQvln1IlDK3BTBJFbADx7tv+oXDPIDZuTo37H5Adb9jhlXm/fEN4Y7/64qD9mnrJJG7rmaTw==",
+      "dev": true,
+      "requires": {
+        "core-js": "^2.6.5",
+        "regenerator-runtime": "^0.13.2"
+      },
+      "dependencies": {
+        "core-js": {
+          "version": "2.6.10",
+          "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.6.10.tgz",
+          "integrity": "sha512-I39t74+4t+zau64EN1fE5v2W31Adtc/REhzWN+gWRRXg6WH5qAsZm62DHpQ1+Yhe4047T55jvzz7MUqF/dBBlA==",
+          "dev": true
+        },
+        "regenerator-runtime": {
+          "version": "0.13.3",
+          "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.3.tgz",
+          "integrity": "sha512-naKIZz2GQ8JWh///G7L3X6LaQUAMp2lvb1rvwwsURe/VXwD6VMfr+/1NuNw3ag8v2kY1aQ/go5SNn79O9JU7yw==",
+          "dev": true
+        }
+      }
+    },
+    "@octokit/endpoint": {
+      "version": "5.5.0",
+      "resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-5.5.0.tgz",
+      "integrity": "sha512-TXYS6zXeBImNB9BVj+LneMDqXX+H0exkOpyXobvp92O3B1348QsKnNioISFKgOMsb3ibZvQGwCdpiwQd3KAjIA==",
+      "dev": true,
+      "requires": {
+        "@octokit/types": "^1.0.0",
+        "is-plain-object": "^3.0.0",
+        "universal-user-agent": "^4.0.0"
+      }
+    },
+    "@octokit/request": {
+      "version": "5.3.0",
+      "resolved": "https://registry.npmjs.org/@octokit/request/-/request-5.3.0.tgz",
+      "integrity": "sha512-mMIeNrtYyNEIYNsKivDyUAukBkw0M5ckyJX56xoFRXSasDPCloIXaQOnaKNopzQ8dIOvpdq1ma8gmrS+h6O2OQ==",
+      "dev": true,
+      "requires": {
+        "@octokit/endpoint": "^5.5.0",
+        "@octokit/request-error": "^1.0.1",
+        "@octokit/types": "^1.0.0",
+        "deprecation": "^2.0.0",
+        "is-plain-object": "^3.0.0",
+        "node-fetch": "^2.3.0",
+        "once": "^1.4.0",
+        "universal-user-agent": "^4.0.0"
+      },
+      "dependencies": {
+        "node-fetch": {
+          "version": "2.6.0",
+          "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.0.tgz",
+          "integrity": "sha512-8dG4H5ujfvFiqDmVu9fQ5bOHUC15JMjMY/Zumv26oOvvVJjM67KF8koCWIabKQ1GJIa9r2mMZscBq/TbdOcmNA==",
+          "dev": true
+        }
+      }
+    },
+    "@octokit/request-error": {
+      "version": "1.0.4",
+      "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-1.0.4.tgz",
+      "integrity": "sha512-L4JaJDXn8SGT+5G0uX79rZLv0MNJmfGa4vb4vy1NnpjSnWDLJRy6m90udGwvMmavwsStgbv2QNkPzzTCMmL+ig==",
+      "dev": true,
+      "requires": {
+        "deprecation": "^2.0.0",
+        "once": "^1.4.0"
+      }
+    },
+    "@octokit/rest": {
+      "version": "16.34.1",
+      "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-16.34.1.tgz",
+      "integrity": "sha512-JUoS12cdktf1fv86rgrjC/RvYLuL+o7p57W7zX1x7ANFJ7OvdV8emvUNkFlcidEaOkYrxK3SoWgQFt3FhNmabA==",
+      "dev": true,
+      "requires": {
+        "@octokit/request": "^5.2.0",
+        "@octokit/request-error": "^1.0.2",
+        "atob-lite": "^2.0.0",
+        "before-after-hook": "^2.0.0",
+        "btoa-lite": "^1.0.0",
+        "deprecation": "^2.0.0",
+        "lodash.get": "^4.4.2",
+        "lodash.set": "^4.3.2",
+        "lodash.uniq": "^4.5.0",
+        "octokit-pagination-methods": "^1.1.0",
+        "once": "^1.4.0",
+        "universal-user-agent": "^4.0.0"
+      }
+    },
+    "@octokit/types": {
+      "version": "1.1.0",
+      "resolved": "https://registry.npmjs.org/@octokit/types/-/types-1.1.0.tgz",
+      "integrity": "sha512-t4ZD74UnNVMq6kZBDZceflRKK3q4o5PoCKMAGht0RK84W57tqonqKL3vCxJHtbGExdan9RwV8r7VJBZxIM1O7Q==",
+      "dev": true,
+      "requires": {
+        "@types/node": "^12.11.1"
+      }
+    },
+    "@types/node": {
+      "version": "12.12.3",
+      "resolved": "https://registry.npmjs.org/@types/node/-/node-12.12.3.tgz",
+      "integrity": "sha512-opgSsy+cEF9N8MgaVPnWVtdJ3o4mV2aMHvDq7thkQUFt0EuOHJon4rQpJfhjmNHB+ikl0Cd6WhWIErOyQ+f7tw==",
+      "dev": true
+    },
     "@weex-project/downgrade": {
       "version": "1.1.0",
       "resolved": "https://registry.npmjs.org/@weex-project/downgrade/-/downgrade-1.1.0.tgz",
       "integrity": "sha512-hMWmH/k4xL8f4BPWPi+Bi4p+ufn2xR4cgqGQcjof/CMZHWFATjSPeQmNzjVFz3zUTSt3iXlE482KDrIKaGpjsw=="
     },
+    "@zeit/schemas": {
+      "version": "1.1.2",
+      "resolved": "https://registry.npmjs.org/@zeit/schemas/-/schemas-1.1.2.tgz",
+      "integrity": "sha512-1KCchM412X/6h1b5XAU3CUe2Teu7duHa6ECkQVa27PmD4UWzciB3oAlElDv4uqAKJFfwprG1eeqwjtmGIQcJcg==",
+      "dev": true
+    },
     "JSONStream": {
       "version": "1.3.3",
       "resolved": "https://registry.npmjs.org/JSONStream/-/JSONStream-1.3.3.tgz",
@@ -19,23 +129,28 @@
         "through": ">=2.2.7 <3"
       }
     },
-    "abab": {
-      "version": "1.0.4",
-      "resolved": "https://registry.npmjs.org/abab/-/abab-1.0.4.tgz",
-      "integrity": "sha1-X6rZwsB/YN12dw9xzwJbYqY8/U4=",
-      "dev": true
-    },
     "abbrev": {
       "version": "1.0.9",
       "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.0.9.tgz",
       "integrity": "sha1-kbR5JYinc4wl813W9jdSovh3YTU=",
       "dev": true
     },
-    "acorn": {
-      "version": "4.0.13",
-      "resolved": "https://registry.npmjs.org/acorn/-/acorn-4.0.13.tgz",
-      "integrity": "sha1-EFSVrlNh1pe9GVyCUZLhrX8lN4c=",
-      "dev": true
+    "abort-controller": {
+      "version": "3.0.0",
+      "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz",
+      "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==",
+      "dev": true,
+      "requires": {
+        "event-target-shim": "^5.0.0"
+      },
+      "dependencies": {
+        "event-target-shim": {
+          "version": "5.0.1",
+          "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz",
+          "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==",
+          "dev": true
+        }
+      }
     },
     "acorn-dynamic-import": {
       "version": "3.0.0",
@@ -60,15 +175,6 @@
       "integrity": "sha1-zGyYKYkfmpduMn+CM7B6sBV9iVo=",
       "dev": true
     },
-    "acorn-globals": {
-      "version": "3.1.0",
-      "resolved": "https://registry.npmjs.org/acorn-globals/-/acorn-globals-3.1.0.tgz",
-      "integrity": "sha1-/YJw9x+7SZawBPqIDuXUZXOnMb8=",
-      "dev": true,
-      "requires": {
-        "acorn": "^4.0.4"
-      }
-    },
     "acorn-jsx": {
       "version": "3.0.1",
       "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-3.0.1.tgz",
@@ -158,9 +264,9 @@
       }
     },
     "ajv-keywords": {
-      "version": "1.5.1",
-      "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-1.5.1.tgz",
-      "integrity": "sha1-MU3QpLM2j609/NxU7eYXG4htrzw=",
+      "version": "2.1.1",
+      "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-2.1.1.tgz",
+      "integrity": "sha1-YXmX/F9gV2iUxDX5QNgZ4TW4B2I=",
       "dev": true
     },
     "align-text": {
@@ -196,9 +302,9 @@
       }
     },
     "ansi-escapes": {
-      "version": "1.4.0",
-      "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-1.4.0.tgz",
-      "integrity": "sha1-06ioOzGapneTZisT52HHkRQiMG4=",
+      "version": "3.2.0",
+      "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.2.0.tgz",
+      "integrity": "sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ==",
       "dev": true
     },
     "ansi-red": {
@@ -301,6 +407,12 @@
         }
       }
     },
+    "arg": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/arg/-/arg-2.0.0.tgz",
+      "integrity": "sha512-XxNTUzKnz1ctK3ZIcI2XUPlD96wbHP2nGqkPKpvk/HNRlPveYrXIVSTk9m3LcqOgDPg3B1nMvdV/K8wZd7PG4w==",
+      "dev": true
+    },
     "argparse": {
       "version": "1.0.10",
       "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz",
@@ -331,12 +443,6 @@
       "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=",
       "dev": true
     },
-    "array-equal": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/array-equal/-/array-equal-1.0.0.tgz",
-      "integrity": "sha1-jCpe8kcv2ep0KwTHenUJO6J1fJM=",
-      "dev": true
-    },
     "array-filter": {
       "version": "0.0.1",
       "resolved": "https://registry.npmjs.org/array-filter/-/array-filter-0.0.1.tgz",
@@ -459,6 +565,15 @@
       "integrity": "sha1-GdOGodntxufByF04iu28xW0zYC0=",
       "dev": true
     },
+    "async-retry": {
+      "version": "1.2.3",
+      "resolved": "https://registry.npmjs.org/async-retry/-/async-retry-1.2.3.tgz",
+      "integrity": "sha512-tfDb02Th6CE6pJUF2gjW5ZVjsgwlucVXOEQMvEX9JgSJMs9gAX+Nz3xRuJBKuUYjTSYORqvDBORdAQ3LU59g7Q==",
+      "dev": true,
+      "requires": {
+        "retry": "0.12.0"
+      }
+    },
     "asynckit": {
       "version": "0.4.0",
       "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz",
@@ -470,6 +585,12 @@
       "integrity": "sha1-ri1acpR38onWDdf5amMUoi3Wwio=",
       "dev": true
     },
+    "atob-lite": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/atob-lite/-/atob-lite-2.0.0.tgz",
+      "integrity": "sha1-D+9a1G8b16hQLGVyfwNn1e5D1pY=",
+      "dev": true
+    },
     "autoprefixer": {
       "version": "6.7.7",
       "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-6.7.7.tgz",
@@ -706,17 +827,6 @@
         }
       }
     },
-    "babel-jest": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/babel-jest/-/babel-jest-19.0.0.tgz",
-      "integrity": "sha1-WTI87ZmjqE01naIZyogQdP/Gzj8=",
-      "dev": true,
-      "requires": {
-        "babel-core": "^6.0.0",
-        "babel-plugin-istanbul": "^4.0.0",
-        "babel-preset-jest": "^19.0.0"
-      }
-    },
     "babel-loader": {
       "version": "6.4.1",
       "resolved": "https://registry.npmjs.org/babel-loader/-/babel-loader-6.4.1.tgz",
@@ -757,41 +867,6 @@
         "babel-template": "^6.8.0"
       }
     },
-    "babel-plugin-istanbul": {
-      "version": "4.1.6",
-      "resolved": "https://registry.npmjs.org/babel-plugin-istanbul/-/babel-plugin-istanbul-4.1.6.tgz",
-      "integrity": "sha512-PWP9FQ1AhZhS01T/4qLSKoHGY/xvkZdVBGlKM/HuxxS3+sC66HhTNR7+MpbO/so/cz/wY94MeSWJuP1hXIPfwQ==",
-      "dev": true,
-      "requires": {
-        "babel-plugin-syntax-object-rest-spread": "^6.13.0",
-        "find-up": "^2.1.0",
-        "istanbul-lib-instrument": "^1.10.1",
-        "test-exclude": "^4.2.1"
-      },
-      "dependencies": {
-        "find-up": {
-          "version": "2.1.0",
-          "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz",
-          "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=",
-          "dev": true,
-          "requires": {
-            "locate-path": "^2.0.0"
-          }
-        }
-      }
-    },
-    "babel-plugin-jest-hoist": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/babel-plugin-jest-hoist/-/babel-plugin-jest-hoist-19.0.0.tgz",
-      "integrity": "sha1-SuKgTqYSpuc2UfP95SwXiZEwS+o=",
-      "dev": true
-    },
-    "babel-plugin-syntax-object-rest-spread": {
-      "version": "6.13.0",
-      "resolved": "https://registry.npmjs.org/babel-plugin-syntax-object-rest-spread/-/babel-plugin-syntax-object-rest-spread-6.13.0.tgz",
-      "integrity": "sha1-/WU28rzhODb/o6VFjEkDpZe7O/U=",
-      "dev": true
-    },
     "babel-plugin-transform-es2015-arrow-functions": {
       "version": "6.22.0",
       "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-arrow-functions/-/babel-plugin-transform-es2015-arrow-functions-6.22.0.tgz",
@@ -1054,25 +1129,6 @@
         "babel-types": "^6.24.1"
       }
     },
-    "babel-polyfill": {
-      "version": "6.26.0",
-      "resolved": "https://registry.npmjs.org/babel-polyfill/-/babel-polyfill-6.26.0.tgz",
-      "integrity": "sha1-N5k3q8Z9eJWXCtxiHyhM2WbPIVM=",
-      "dev": true,
-      "requires": {
-        "babel-runtime": "^6.26.0",
-        "core-js": "^2.5.0",
-        "regenerator-runtime": "^0.10.5"
-      },
-      "dependencies": {
-        "regenerator-runtime": {
-          "version": "0.10.5",
-          "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.10.5.tgz",
-          "integrity": "sha1-M2w+/BIgrc7dosn6tntaeVWjNlg=",
-          "dev": true
-        }
-      }
-    },
     "babel-preset-es2015": {
       "version": "6.24.1",
       "resolved": "https://registry.npmjs.org/babel-preset-es2015/-/babel-preset-es2015-6.24.1.tgz",
@@ -1105,15 +1161,6 @@
         "babel-plugin-transform-regenerator": "^6.24.1"
       }
     },
-    "babel-preset-jest": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/babel-preset-jest/-/babel-preset-jest-19.0.0.tgz",
-      "integrity": "sha1-ItZyAdAjJKGVgRKI6zgpS7PKw5Y=",
-      "dev": true,
-      "requires": {
-        "babel-plugin-jest-hoist": "^19.0.0"
-      }
-    },
     "babel-register": {
       "version": "6.26.0",
       "resolved": "https://registry.npmjs.org/babel-register/-/babel-register-6.26.0.tgz",
@@ -1208,12 +1255,6 @@
         "pascalcase": "^0.1.1"
       },
       "dependencies": {
-        "component-emitter": {
-          "version": "1.2.1",
-          "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz",
-          "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=",
-          "dev": true
-        },
         "define-property": {
           "version": "1.0.0",
           "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz",
@@ -1281,6 +1322,12 @@
         "tweetnacl": "^0.14.3"
       }
     },
+    "before-after-hook": {
+      "version": "2.1.0",
+      "resolved": "https://registry.npmjs.org/before-after-hook/-/before-after-hook-2.1.0.tgz",
+      "integrity": "sha512-IWIbu7pMqyw3EAJHzzHbWa85b6oud/yfKYg5rqB5hNE8CeMi3nX+2C2sj0HswfblST86hpVEOAb9x34NZd6P7A==",
+      "dev": true
+    },
     "big.js": {
       "version": "3.2.0",
       "resolved": "https://registry.npmjs.org/big.js/-/big.js-3.2.0.tgz",
@@ -1593,14 +1640,11 @@
         "electron-to-chromium": "^1.2.7"
       }
     },
-    "bser": {
-      "version": "2.0.0",
-      "resolved": "https://registry.npmjs.org/bser/-/bser-2.0.0.tgz",
-      "integrity": "sha1-mseNPtXZFYBP2HrLFYvHlxR6Fxk=",
-      "dev": true,
-      "requires": {
-        "node-int64": "^0.4.0"
-      }
+    "btoa-lite": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/btoa-lite/-/btoa-lite-1.0.0.tgz",
+      "integrity": "sha1-M3dm2hWAEhD92VbCLpxokaudAzc=",
+      "dev": true
     },
     "buble": {
       "version": "0.18.0",
@@ -1701,18 +1745,18 @@
       "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=",
       "dev": true
     },
+    "buffer-equal-constant-time": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/buffer-equal-constant-time/-/buffer-equal-constant-time-1.0.1.tgz",
+      "integrity": "sha1-+OcRMvf/5uAaXJaXpMbz5I1cyBk=",
+      "dev": true
+    },
     "buffer-from": {
       "version": "1.1.0",
       "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.0.tgz",
       "integrity": "sha512-c5mRlguI/Pe2dSZmpER62rSCu0ryKmWddzRYsuXc50U2/g8jMOulc31VZMa4mYx31U5xsmSOpDCgH88Vl9cDGQ==",
       "dev": true
     },
-    "builtin-modules": {
-      "version": "1.1.1",
-      "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz",
-      "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=",
-      "dev": true
-    },
     "builtin-status-codes": {
       "version": "3.0.0",
       "resolved": "https://registry.npmjs.org/builtin-status-codes/-/builtin-status-codes-3.0.0.tgz",
@@ -1720,9 +1764,9 @@
       "dev": true
     },
     "bytes": {
-      "version": "0.1.0",
-      "resolved": "https://registry.npmjs.org/bytes/-/bytes-0.1.0.tgz",
-      "integrity": "sha1-xXSBIigSbWNp0VdpJahXnbP45aI=",
+      "version": "3.0.0",
+      "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz",
+      "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=",
       "dev": true
     },
     "cache-base": {
@@ -1742,12 +1786,6 @@
         "unset-value": "^1.0.0"
       },
       "dependencies": {
-        "component-emitter": {
-          "version": "1.2.1",
-          "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz",
-          "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=",
-          "dev": true
-        },
         "isobject": {
           "version": "3.0.1",
           "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz",
@@ -1757,9 +1795,9 @@
       }
     },
     "cached-path-relative": {
-      "version": "1.0.1",
-      "resolved": "https://registry.npmjs.org/cached-path-relative/-/cached-path-relative-1.0.1.tgz",
-      "integrity": "sha1-0JxLUoAKpMB44t2BqGmqyQ0uVOc=",
+      "version": "1.0.2",
+      "resolved": "https://registry.npmjs.org/cached-path-relative/-/cached-path-relative-1.0.2.tgz",
+      "integrity": "sha512-5r2GqsoEb4qMTTN9J+WzXfjov+hjxT+j3u5K+kIVNIwAd99DLCJE9pBIMP1qVeybV6JiijL385Oz0DcYxfbOIg==",
       "dev": true
     },
     "caller-path": {
@@ -1941,12 +1979,12 @@
       }
     },
     "cli-cursor": {
-      "version": "1.0.2",
-      "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz",
-      "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=",
+      "version": "2.1.0",
+      "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz",
+      "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=",
       "dev": true,
       "requires": {
-        "restore-cursor": "^1.0.1"
+        "restore-cursor": "^2.0.0"
       }
     },
     "cli-width": {
@@ -1994,12 +2032,6 @@
         "q": "^1.1.2"
       }
     },
-    "code-point-at": {
-      "version": "1.1.0",
-      "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz",
-      "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=",
-      "dev": true
-    },
     "collection-visit": {
       "version": "1.0.0",
       "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz",
@@ -2108,6 +2140,12 @@
       "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=",
       "dev": true
     },
+    "component-emitter": {
+      "version": "1.3.0",
+      "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.3.0.tgz",
+      "integrity": "sha512-Rd3se6QB+sO1TwqZjscQrurpEPIfO0/yYnSin6Q/rD3mOutHvUrCAhJub3r90uNb+SESBuE0QYoB90YdfatsRg==",
+      "dev": true
+    },
     "compress-commons": {
       "version": "0.2.9",
       "resolved": "https://registry.npmjs.org/compress-commons/-/compress-commons-0.2.9.tgz",
@@ -2200,30 +2238,6 @@
         "proto-list": "~1.2.1"
       }
     },
-    "connect": {
-      "version": "2.3.9",
-      "resolved": "https://registry.npmjs.org/connect/-/connect-2.3.9.tgz",
-      "integrity": "sha1-TSbdxIXDLloc8bNYVII7RyDSWlI=",
-      "dev": true,
-      "requires": {
-        "bytes": "0.1.0",
-        "cookie": "0.0.4",
-        "crc": "0.2.0",
-        "debug": "*",
-        "formidable": "1.0.11",
-        "fresh": "0.1.0",
-        "qs": "0.4.2",
-        "send": "0.0.3"
-      },
-      "dependencies": {
-        "qs": {
-          "version": "0.4.2",
-          "resolved": "https://registry.npmjs.org/qs/-/qs-0.4.2.tgz",
-          "integrity": "sha1-PKxMhh43GoycR3CsI82o3mObjl8=",
-          "dev": true
-        }
-      }
-    },
     "console-browserify": {
       "version": "1.1.0",
       "resolved": "https://registry.npmjs.org/console-browserify/-/console-browserify-1.1.0.tgz",
@@ -2248,24 +2262,12 @@
       "integrity": "sha1-wguW2MYXdIqvHBYCF2DNJ/y4y3U=",
       "dev": true
     },
-    "content-type-parser": {
-      "version": "1.0.2",
-      "resolved": "https://registry.npmjs.org/content-type-parser/-/content-type-parser-1.0.2.tgz",
-      "integrity": "sha512-lM4l4CnMEwOLHAHr/P6MEZwZFPJFtAAKgL6pogbXmVZggIqXhdB6RbBtPOTsw2FcXwYhehRGERJmRrjOiIB8pQ==",
-      "dev": true
-    },
     "convert-source-map": {
       "version": "1.5.1",
       "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.5.1.tgz",
       "integrity": "sha1-uCeAl7m8IpNl3lxiz1/K7YtVmeU=",
       "dev": true
     },
-    "cookie": {
-      "version": "0.0.4",
-      "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.0.4.tgz",
-      "integrity": "sha1-VFa9R67iZm6sl26oCmEFlASD/pg=",
-      "dev": true
-    },
     "copy-descriptor": {
       "version": "0.1.1",
       "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz",
@@ -2321,12 +2323,6 @@
         }
       }
     },
-    "crc": {
-      "version": "0.2.0",
-      "resolved": "https://registry.npmjs.org/crc/-/crc-0.2.0.tgz",
-      "integrity": "sha1-9Ehrm/ChLfg8P8oU4x4DD9q9lFQ=",
-      "dev": true
-    },
     "crc32-stream": {
       "version": "0.3.4",
       "resolved": "https://registry.npmjs.org/crc32-stream/-/crc32-stream-0.3.4.tgz",
@@ -2450,12 +2446,6 @@
         }
       }
     },
-    "css-parse": {
-      "version": "1.7.0",
-      "resolved": "https://registry.npmjs.org/css-parse/-/css-parse-1.7.0.tgz",
-      "integrity": "sha1-Mh9s9zeCpv91ERE5D8BeLGV9jJs=",
-      "dev": true
-    },
     "css-selector-tokenizer": {
       "version": "0.7.0",
       "resolved": "https://registry.npmjs.org/css-selector-tokenizer/-/css-selector-tokenizer-0.7.0.tgz",
@@ -2536,60 +2526,464 @@
         "source-map": "^0.5.3"
       }
     },
-    "cssom": {
-      "version": "0.3.4",
-      "resolved": "https://registry.npmjs.org/cssom/-/cssom-0.3.4.tgz",
-      "integrity": "sha512-+7prCSORpXNeR4/fUP3rL+TzqtiFfhMvTd7uEqMdgPvLPt4+uzFUeufx5RHjGTACCargg/DiEt/moMQmvnfkog==",
-      "dev": true
-    },
-    "cssstyle": {
-      "version": "0.2.37",
-      "resolved": "https://registry.npmjs.org/cssstyle/-/cssstyle-0.2.37.tgz",
-      "integrity": "sha1-VBCXI0yyUTyDzu06zdwn/yeYfVQ=",
-      "dev": true,
-      "requires": {
-        "cssom": "0.3.x"
-      }
-    },
     "ctype": {
       "version": "0.5.3",
       "resolved": "https://registry.npmjs.org/ctype/-/ctype-0.5.3.tgz",
       "integrity": "sha1-gsGMJGH3QRTvFsE1IkrQuRRMoS8=",
       "dev": true
     },
-    "d": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/d/-/d-1.0.0.tgz",
-      "integrity": "sha1-dUu1v+VUUdpppYuU1F9MWwRi1Y8=",
-      "dev": true,
-      "requires": {
-        "es5-ext": "^0.10.9"
-      }
-    },
     "danger": {
-      "version": "0.18.0",
-      "resolved": "https://registry.npmjs.org/danger/-/danger-0.18.0.tgz",
-      "integrity": "sha1-grwMNUa4EyvmGqvM7X+vjqubgZI=",
+      "version": "9.2.2",
+      "resolved": "https://registry.npmjs.org/danger/-/danger-9.2.2.tgz",
+      "integrity": "sha512-tDLIFYa1KzU7HJIvn6FEurFWqn36cFPVBLvKrUqbRxJOCPONWNvpRRbHKj3HmNPEQf5bVls78V/FZz8iRs4Qlg==",
       "dev": true,
       "requires": {
-        "babel-polyfill": "^6.20.0",
-        "chalk": "^1.1.1",
-        "commander": "^2.9.0",
-        "debug": "^2.6.0",
-        "github": "^9.2.0",
-        "jest-config": "^19.0.2",
-        "jest-environment-node": "^19.0.2",
-        "jest-runtime": "^19.0.2",
-        "jsome": "^2.3.25",
+        "@babel/polyfill": "^7.2.5",
+        "@octokit/rest": "^16.14.1",
+        "async-retry": "1.2.3",
+        "chalk": "^2.3.0",
+        "commander": "^2.18.0",
+        "debug": "^4.1.1",
+        "get-stdin": "^6.0.0",
+        "gitlab": "^10.0.1",
+        "http-proxy-agent": "^2.1.0",
+        "https-proxy-agent": "^2.2.1",
+        "hyperlinker": "^1.0.0",
+        "json5": "^2.1.0",
         "jsonpointer": "^4.0.1",
+        "jsonwebtoken": "^8.4.0",
         "lodash.find": "^4.6.0",
         "lodash.includes": "^4.3.0",
-        "lodash.isobject": "^2.4.1",
+        "lodash.isobject": "^3.0.2",
         "lodash.keys": "^4.0.8",
-        "node-fetch": "^1.6.3",
-        "parse-diff": "^0.4.0",
-        "rfc6902": "^1.3.0",
-        "voca": "^1.2.0"
+        "lodash.mapvalues": "^4.6.0",
+        "lodash.memoize": "^4.1.2",
+        "memfs-or-file-map-to-github-branch": "^1.1.0",
+        "micromatch": "^3.1.10",
+        "node-cleanup": "^2.1.2",
+        "node-fetch": "^2.3.0",
+        "override-require": "^1.1.1",
+        "p-limit": "^2.1.0",
+        "parse-diff": "^0.5.1",
+        "parse-git-config": "^2.0.3",
+        "parse-github-url": "^1.0.2",
+        "parse-link-header": "^1.0.1",
+        "pinpoint": "^1.1.0",
+        "prettyjson": "^1.2.1",
+        "readline-sync": "^1.4.9",
+        "require-from-string": "^2.0.2",
+        "rfc6902": "^3.0.1",
+        "supports-hyperlinks": "^1.0.1"
+      },
+      "dependencies": {
+        "agent-base": {
+          "version": "4.3.0",
+          "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz",
+          "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==",
+          "dev": true,
+          "requires": {
+            "es6-promisify": "^5.0.0"
+          }
+        },
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
+          "dev": true,
+          "requires": {
+            "color-convert": "^1.9.0"
+          }
+        },
+        "arr-diff": {
+          "version": "4.0.0",
+          "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz",
+          "integrity": "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=",
+          "dev": true
+        },
+        "array-unique": {
+          "version": "0.3.2",
+          "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz",
+          "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=",
+          "dev": true
+        },
+        "braces": {
+          "version": "2.3.2",
+          "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz",
+          "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==",
+          "dev": true,
+          "requires": {
+            "arr-flatten": "^1.1.0",
+            "array-unique": "^0.3.2",
+            "extend-shallow": "^2.0.1",
+            "fill-range": "^4.0.0",
+            "isobject": "^3.0.1",
+            "repeat-element": "^1.1.2",
+            "snapdragon": "^0.8.1",
+            "snapdragon-node": "^2.0.1",
+            "split-string": "^3.0.2",
+            "to-regex": "^3.0.1"
+          },
+          "dependencies": {
+            "extend-shallow": {
+              "version": "2.0.1",
+              "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
+              "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
+              "dev": true,
+              "requires": {
+                "is-extendable": "^0.1.0"
+              }
+            }
+          }
+        },
+        "chalk": {
+          "version": "2.4.2",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
+          "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "commander": {
+          "version": "2.20.3",
+          "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz",
+          "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==",
+          "dev": true
+        },
+        "debug": {
+          "version": "4.1.1",
+          "resolved": "https://registry.npmjs.org/debug/-/debug-4.1.1.tgz",
+          "integrity": "sha512-pYAIzeRo8J6KPEaJ0VWOh5Pzkbw/RetuzehGM7QRRX5he4fPHx2rdKMB256ehJCkX+XRQm16eZLqLNS8RSZXZw==",
+          "dev": true,
+          "requires": {
+            "ms": "^2.1.1"
+          }
+        },
+        "expand-brackets": {
+          "version": "2.1.4",
+          "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz",
+          "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=",
+          "dev": true,
+          "requires": {
+            "debug": "^2.3.3",
+            "define-property": "^0.2.5",
+            "extend-shallow": "^2.0.1",
+            "posix-character-classes": "^0.1.0",
+            "regex-not": "^1.0.0",
+            "snapdragon": "^0.8.1",
+            "to-regex": "^3.0.1"
+          },
+          "dependencies": {
+            "debug": {
+              "version": "2.6.9",
+              "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz",
+              "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==",
+              "dev": true,
+              "requires": {
+                "ms": "2.0.0"
+              }
+            },
+            "define-property": {
+              "version": "0.2.5",
+              "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz",
+              "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=",
+              "dev": true,
+              "requires": {
+                "is-descriptor": "^0.1.0"
+              }
+            },
+            "extend-shallow": {
+              "version": "2.0.1",
+              "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
+              "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
+              "dev": true,
+              "requires": {
+                "is-extendable": "^0.1.0"
+              }
+            },
+            "is-accessor-descriptor": {
+              "version": "0.1.6",
+              "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz",
+              "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=",
+              "dev": true,
+              "requires": {
+                "kind-of": "^3.0.2"
+              },
+              "dependencies": {
+                "kind-of": {
+                  "version": "3.2.2",
+                  "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
+                  "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
+                  "dev": true,
+                  "requires": {
+                    "is-buffer": "^1.1.5"
+                  }
+                }
+              }
+            },
+            "is-data-descriptor": {
+              "version": "0.1.4",
+              "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz",
+              "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=",
+              "dev": true,
+              "requires": {
+                "kind-of": "^3.0.2"
+              },
+              "dependencies": {
+                "kind-of": {
+                  "version": "3.2.2",
+                  "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
+                  "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
+                  "dev": true,
+                  "requires": {
+                    "is-buffer": "^1.1.5"
+                  }
+                }
+              }
+            },
+            "is-descriptor": {
+              "version": "0.1.6",
+              "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz",
+              "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==",
+              "dev": true,
+              "requires": {
+                "is-accessor-descriptor": "^0.1.6",
+                "is-data-descriptor": "^0.1.4",
+                "kind-of": "^5.0.0"
+              }
+            },
+            "kind-of": {
+              "version": "5.1.0",
+              "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz",
+              "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==",
+              "dev": true
+            },
+            "ms": {
+              "version": "2.0.0",
+              "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz",
+              "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=",
+              "dev": true
+            }
+          }
+        },
+        "extglob": {
+          "version": "2.0.4",
+          "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz",
+          "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==",
+          "dev": true,
+          "requires": {
+            "array-unique": "^0.3.2",
+            "define-property": "^1.0.0",
+            "expand-brackets": "^2.1.4",
+            "extend-shallow": "^2.0.1",
+            "fragment-cache": "^0.2.1",
+            "regex-not": "^1.0.0",
+            "snapdragon": "^0.8.1",
+            "to-regex": "^3.0.1"
+          },
+          "dependencies": {
+            "define-property": {
+              "version": "1.0.0",
+              "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz",
+              "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=",
+              "dev": true,
+              "requires": {
+                "is-descriptor": "^1.0.0"
+              }
+            },
+            "extend-shallow": {
+              "version": "2.0.1",
+              "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
+              "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
+              "dev": true,
+              "requires": {
+                "is-extendable": "^0.1.0"
+              }
+            }
+          }
+        },
+        "fill-range": {
+          "version": "4.0.0",
+          "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz",
+          "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=",
+          "dev": true,
+          "requires": {
+            "extend-shallow": "^2.0.1",
+            "is-number": "^3.0.0",
+            "repeat-string": "^1.6.1",
+            "to-regex-range": "^2.1.0"
+          },
+          "dependencies": {
+            "extend-shallow": {
+              "version": "2.0.1",
+              "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
+              "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
+              "dev": true,
+              "requires": {
+                "is-extendable": "^0.1.0"
+              }
+            }
+          }
+        },
+        "has-flag": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+          "dev": true
+        },
+        "https-proxy-agent": {
+          "version": "2.2.4",
+          "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-2.2.4.tgz",
+          "integrity": "sha512-OmvfoQ53WLjtA9HeYP9RNrWMJzzAz1JGaSFr1nijg0PVR1JaD/xbJq1mdEIIlxGpXp9eSe/O2LgU9DJmTPd0Eg==",
+          "dev": true,
+          "requires": {
+            "agent-base": "^4.3.0",
+            "debug": "^3.1.0"
+          },
+          "dependencies": {
+            "debug": {
+              "version": "3.2.6",
+              "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz",
+              "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==",
+              "dev": true,
+              "requires": {
+                "ms": "^2.1.1"
+              }
+            }
+          }
+        },
+        "is-accessor-descriptor": {
+          "version": "1.0.0",
+          "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz",
+          "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==",
+          "dev": true,
+          "requires": {
+            "kind-of": "^6.0.0"
+          }
+        },
+        "is-data-descriptor": {
+          "version": "1.0.0",
+          "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz",
+          "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==",
+          "dev": true,
+          "requires": {
+            "kind-of": "^6.0.0"
+          }
+        },
+        "is-descriptor": {
+          "version": "1.0.2",
+          "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz",
+          "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==",
+          "dev": true,
+          "requires": {
+            "is-accessor-descriptor": "^1.0.0",
+            "is-data-descriptor": "^1.0.0",
+            "kind-of": "^6.0.2"
+          }
+        },
+        "is-number": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz",
+          "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=",
+          "dev": true,
+          "requires": {
+            "kind-of": "^3.0.2"
+          },
+          "dependencies": {
+            "kind-of": {
+              "version": "3.2.2",
+              "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
+              "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
+              "dev": true,
+              "requires": {
+                "is-buffer": "^1.1.5"
+              }
+            }
+          }
+        },
+        "isobject": {
+          "version": "3.0.1",
+          "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz",
+          "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=",
+          "dev": true
+        },
+        "json5": {
+          "version": "2.1.1",
+          "resolved": "https://registry.npmjs.org/json5/-/json5-2.1.1.tgz",
+          "integrity": "sha512-l+3HXD0GEI3huGq1njuqtzYK8OYJyXMkOLtQ53pjWh89tvWS2h6l+1zMkYWqlb57+SiQodKZyvMEFb2X+KrFhQ==",
+          "dev": true,
+          "requires": {
+            "minimist": "^1.2.0"
+          }
+        },
+        "kind-of": {
+          "version": "6.0.2",
+          "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz",
+          "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==",
+          "dev": true
+        },
+        "micromatch": {
+          "version": "3.1.10",
+          "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz",
+          "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==",
+          "dev": true,
+          "requires": {
+            "arr-diff": "^4.0.0",
+            "array-unique": "^0.3.2",
+            "braces": "^2.3.1",
+            "define-property": "^2.0.2",
+            "extend-shallow": "^3.0.2",
+            "extglob": "^2.0.4",
+            "fragment-cache": "^0.2.1",
+            "kind-of": "^6.0.2",
+            "nanomatch": "^1.2.9",
+            "object.pick": "^1.3.0",
+            "regex-not": "^1.0.0",
+            "snapdragon": "^0.8.1",
+            "to-regex": "^3.0.2"
+          }
+        },
+        "minimist": {
+          "version": "1.2.0",
+          "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz",
+          "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=",
+          "dev": true
+        },
+        "ms": {
+          "version": "2.1.2",
+          "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz",
+          "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==",
+          "dev": true
+        },
+        "node-fetch": {
+          "version": "2.6.0",
+          "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.0.tgz",
+          "integrity": "sha512-8dG4H5ujfvFiqDmVu9fQ5bOHUC15JMjMY/Zumv26oOvvVJjM67KF8koCWIabKQ1GJIa9r2mMZscBq/TbdOcmNA==",
+          "dev": true
+        },
+        "parse-diff": {
+          "version": "0.5.1",
+          "resolved": "https://registry.npmjs.org/parse-diff/-/parse-diff-0.5.1.tgz",
+          "integrity": "sha512-/qXjo9x/pFa5bVk/ZXaJD0yr3Tf3Yp6MWWMr4vnUmumDrE0yoE6YDH2A8vmcCD/Ko3tW2o0X+zGYh2zMLXshsg==",
+          "dev": true
+        },
+        "require-from-string": {
+          "version": "2.0.2",
+          "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz",
+          "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==",
+          "dev": true
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          }
+        }
       }
     },
     "dashdash": {
@@ -2669,6 +3063,12 @@
         }
       }
     },
+    "deep-extend": {
+      "version": "0.6.0",
+      "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz",
+      "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==",
+      "dev": true
+    },
     "deep-is": {
       "version": "0.1.3",
       "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz",
@@ -2753,6 +3153,12 @@
       "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz",
       "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk="
     },
+    "deprecation": {
+      "version": "2.3.1",
+      "resolved": "https://registry.npmjs.org/deprecation/-/deprecation-2.3.1.tgz",
+      "integrity": "sha512-xmHIy4F3scKVwMsQ4WnVaS8bHOx0DmVwRywosKhaILI0ywMDWPtBSku2HNxRvF7jtwDRsoEwYQSfbxj8b7RlJQ==",
+      "dev": true
+    },
     "deps-sort": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/deps-sort/-/deps-sort-2.0.0.tgz",
@@ -2809,21 +3215,12 @@
       "dev": true
     },
     "doctrine": {
-      "version": "1.5.0",
-      "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-1.5.0.tgz",
-      "integrity": "sha1-N53Ocw9hZvds76TmcHoVmwLFpvo=",
+      "version": "2.1.0",
+      "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz",
+      "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==",
       "dev": true,
       "requires": {
-        "esutils": "^2.0.2",
-        "isarray": "^1.0.0"
-      },
-      "dependencies": {
-        "isarray": {
-          "version": "1.0.0",
-          "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz",
-          "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=",
-          "dev": true
-        }
+        "esutils": "^2.0.2"
       }
     },
     "domain-browser": {
@@ -2906,6 +3303,15 @@
         "jsbn": "~0.1.0"
       }
     },
+    "ecdsa-sig-formatter": {
+      "version": "1.0.11",
+      "resolved": "https://registry.npmjs.org/ecdsa-sig-formatter/-/ecdsa-sig-formatter-1.0.11.tgz",
+      "integrity": "sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==",
+      "dev": true,
+      "requires": {
+        "safe-buffer": "^5.0.1"
+      }
+    },
     "ecstatic": {
       "version": "1.4.1",
       "resolved": "https://registry.npmjs.org/ecstatic/-/ecstatic-1.4.1.tgz",
@@ -3017,81 +3423,19 @@
         "is-arrayish": "^0.2.1"
       }
     },
-    "es5-ext": {
-      "version": "0.10.45",
-      "resolved": "https://registry.npmjs.org/es5-ext/-/es5-ext-0.10.45.tgz",
-      "integrity": "sha512-FkfM6Vxxfmztilbxxz5UKSD4ICMf5tSpRFtDNtkAhOxZ0EKtX6qwmXNyH/sFyIbX2P/nU5AMiA9jilWsUGJzCQ==",
-      "dev": true,
-      "requires": {
-        "es6-iterator": "~2.0.3",
-        "es6-symbol": "~3.1.1",
-        "next-tick": "1"
-      }
-    },
-    "es6-iterator": {
-      "version": "2.0.3",
-      "resolved": "https://registry.npmjs.org/es6-iterator/-/es6-iterator-2.0.3.tgz",
-      "integrity": "sha1-p96IkUGgWpSwhUQDstCg+/qY87c=",
-      "dev": true,
-      "requires": {
-        "d": "1",
-        "es5-ext": "^0.10.35",
-        "es6-symbol": "^3.1.1"
-      }
-    },
-    "es6-map": {
-      "version": "0.1.5",
-      "resolved": "https://registry.npmjs.org/es6-map/-/es6-map-0.1.5.tgz",
-      "integrity": "sha1-kTbgUD3MBqMBaQ8LsU/042TpSfA=",
-      "dev": true,
-      "requires": {
-        "d": "1",
-        "es5-ext": "~0.10.14",
-        "es6-iterator": "~2.0.1",
-        "es6-set": "~0.1.5",
-        "es6-symbol": "~3.1.1",
-        "event-emitter": "~0.3.5"
-      }
-    },
     "es6-promise": {
       "version": "4.2.4",
       "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.4.tgz",
       "integrity": "sha512-/NdNZVJg+uZgtm9eS3O6lrOLYmQag2DjdEXuPaHlZ6RuVqgqaVZfgYCepEIKsLqwdQArOPtC3XzRLqGGfT8KQQ==",
       "dev": true
     },
-    "es6-set": {
-      "version": "0.1.5",
-      "resolved": "https://registry.npmjs.org/es6-set/-/es6-set-0.1.5.tgz",
-      "integrity": "sha1-0rPsXU2ADO2BjbU40ol02wpzzLE=",
+    "es6-promisify": {
+      "version": "5.0.0",
+      "resolved": "https://registry.npmjs.org/es6-promisify/-/es6-promisify-5.0.0.tgz",
+      "integrity": "sha1-UQnWLz5W6pZ8S2NQWu8IKRyKUgM=",
       "dev": true,
       "requires": {
-        "d": "1",
-        "es5-ext": "~0.10.14",
-        "es6-iterator": "~2.0.1",
-        "es6-symbol": "3.1.1",
-        "event-emitter": "~0.3.5"
-      }
-    },
-    "es6-symbol": {
-      "version": "3.1.1",
-      "resolved": "https://registry.npmjs.org/es6-symbol/-/es6-symbol-3.1.1.tgz",
-      "integrity": "sha1-vwDvT9q2uhtG7Le2KbTH7VcVzHc=",
-      "dev": true,
-      "requires": {
-        "d": "1",
-        "es5-ext": "~0.10.14"
-      }
-    },
-    "es6-weak-map": {
-      "version": "2.0.2",
-      "resolved": "https://registry.npmjs.org/es6-weak-map/-/es6-weak-map-2.0.2.tgz",
-      "integrity": "sha1-XjqzIlH/0VOKH45f+hNXdy+S2W8=",
-      "dev": true,
-      "requires": {
-        "d": "1",
-        "es5-ext": "^0.10.14",
-        "es6-iterator": "^2.0.1",
-        "es6-symbol": "^3.1.1"
+        "es6-promise": "^4.0.3"
       }
     },
     "escape-string-regexp": {
@@ -3125,77 +3469,101 @@
         }
       }
     },
-    "escope": {
-      "version": "3.6.0",
-      "resolved": "https://registry.npmjs.org/escope/-/escope-3.6.0.tgz",
-      "integrity": "sha1-4Bl16BJ4GhY6ba392AOY3GTIicM=",
-      "dev": true,
-      "requires": {
-        "es6-map": "^0.1.3",
-        "es6-weak-map": "^2.0.1",
-        "esrecurse": "^4.1.0",
-        "estraverse": "^4.1.1"
-      },
-      "dependencies": {
-        "estraverse": {
-          "version": "4.2.0",
-          "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz",
-          "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=",
-          "dev": true
-        }
-      }
-    },
     "eslint": {
-      "version": "2.13.1",
-      "resolved": "https://registry.npmjs.org/eslint/-/eslint-2.13.1.tgz",
-      "integrity": "sha1-5MyPoPAJ+4KaquI4VaKTYL4fbBE=",
+      "version": "4.18.2",
+      "resolved": "https://registry.npmjs.org/eslint/-/eslint-4.18.2.tgz",
+      "integrity": "sha512-qy4i3wODqKMYfz9LUI8N2qYDkHkoieTbiHpMrYUI/WbjhXJQr7lI4VngixTgaG+yHX+NBCv7nW4hA0ShbvaNKw==",
       "dev": true,
       "requires": {
-        "chalk": "^1.1.3",
-        "concat-stream": "^1.4.6",
-        "debug": "^2.1.1",
-        "doctrine": "^1.2.2",
-        "es6-map": "^0.1.3",
-        "escope": "^3.6.0",
-        "espree": "^3.1.6",
-        "estraverse": "^4.2.0",
+        "ajv": "^5.3.0",
+        "babel-code-frame": "^6.22.0",
+        "chalk": "^2.1.0",
+        "concat-stream": "^1.6.0",
+        "cross-spawn": "^5.1.0",
+        "debug": "^3.1.0",
+        "doctrine": "^2.1.0",
+        "eslint-scope": "^3.7.1",
+        "eslint-visitor-keys": "^1.0.0",
+        "espree": "^3.5.2",
+        "esquery": "^1.0.0",
         "esutils": "^2.0.2",
-        "file-entry-cache": "^1.1.1",
-        "glob": "^7.0.3",
-        "globals": "^9.2.0",
-        "ignore": "^3.1.2",
+        "file-entry-cache": "^2.0.0",
+        "functional-red-black-tree": "^1.0.1",
+        "glob": "^7.1.2",
+        "globals": "^11.0.1",
+        "ignore": "^3.3.3",
         "imurmurhash": "^0.1.4",
-        "inquirer": "^0.12.0",
-        "is-my-json-valid": "^2.10.0",
+        "inquirer": "^3.0.6",
         "is-resolvable": "^1.0.0",
-        "js-yaml": "^3.5.1",
-        "json-stable-stringify": "^1.0.0",
+        "js-yaml": "^3.9.1",
+        "json-stable-stringify-without-jsonify": "^1.0.1",
         "levn": "^0.3.0",
-        "lodash": "^4.0.0",
-        "mkdirp": "^0.5.0",
-        "optionator": "^0.8.1",
-        "path-is-absolute": "^1.0.0",
-        "path-is-inside": "^1.0.1",
-        "pluralize": "^1.2.1",
-        "progress": "^1.1.8",
-        "require-uncached": "^1.0.2",
-        "shelljs": "^0.6.0",
-        "strip-json-comments": "~1.0.1",
-        "table": "^3.7.8",
-        "text-table": "~0.2.0",
-        "user-home": "^2.0.0"
+        "lodash": "^4.17.4",
+        "minimatch": "^3.0.2",
+        "mkdirp": "^0.5.1",
+        "natural-compare": "^1.4.0",
+        "optionator": "^0.8.2",
+        "path-is-inside": "^1.0.2",
+        "pluralize": "^7.0.0",
+        "progress": "^2.0.0",
+        "require-uncached": "^1.0.3",
+        "semver": "^5.3.0",
+        "strip-ansi": "^4.0.0",
+        "strip-json-comments": "~2.0.1",
+        "table": "4.0.2",
+        "text-table": "~0.2.0"
       },
       "dependencies": {
-        "estraverse": {
-          "version": "4.2.0",
-          "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz",
-          "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=",
+        "ansi-regex": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz",
+          "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=",
           "dev": true
         },
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
+          "dev": true,
+          "requires": {
+            "color-convert": "^1.9.0"
+          }
+        },
+        "chalk": {
+          "version": "2.4.2",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
+          "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "cross-spawn": {
+          "version": "5.1.0",
+          "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz",
+          "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=",
+          "dev": true,
+          "requires": {
+            "lru-cache": "^4.0.1",
+            "shebang-command": "^1.2.0",
+            "which": "^1.2.9"
+          }
+        },
+        "debug": {
+          "version": "3.2.6",
+          "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz",
+          "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==",
+          "dev": true,
+          "requires": {
+            "ms": "^2.1.1"
+          }
+        },
         "glob": {
-          "version": "7.1.2",
-          "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz",
-          "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==",
+          "version": "7.1.5",
+          "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.5.tgz",
+          "integrity": "sha512-J9dlskqUXK1OeTOYBEn5s8aMukWMwWfs+rPTn/jn50Ux4MNXVhubL1wu/j2t+H4NVI+cXEcCaYellqaPVGXNqQ==",
           "dev": true,
           "requires": {
             "fs.realpath": "^1.0.0",
@@ -3206,11 +3574,47 @@
             "path-is-absolute": "^1.0.0"
           }
         },
-        "shelljs": {
-          "version": "0.6.1",
-          "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.6.1.tgz",
-          "integrity": "sha1-7GIRvtGSBEIIj+D3Cyg3Iy7SyKg=",
+        "globals": {
+          "version": "11.12.0",
+          "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz",
+          "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==",
           "dev": true
+        },
+        "has-flag": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+          "dev": true
+        },
+        "ms": {
+          "version": "2.1.2",
+          "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz",
+          "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==",
+          "dev": true
+        },
+        "progress": {
+          "version": "2.0.3",
+          "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz",
+          "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==",
+          "dev": true
+        },
+        "strip-ansi": {
+          "version": "4.0.0",
+          "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz",
+          "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=",
+          "dev": true,
+          "requires": {
+            "ansi-regex": "^3.0.0"
+          }
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          }
         }
       }
     },
@@ -3323,16 +3727,6 @@
       "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=",
       "dev": true
     },
-    "event-emitter": {
-      "version": "0.3.5",
-      "resolved": "https://registry.npmjs.org/event-emitter/-/event-emitter-0.3.5.tgz",
-      "integrity": "sha1-34xp7vFkeSPHFXuc6DhAYQsCzDk=",
-      "dev": true,
-      "requires": {
-        "d": "1",
-        "es5-ext": "~0.10.14"
-      }
-    },
     "event-target-shim": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-2.0.0.tgz",
@@ -3350,23 +3744,14 @@
       "integrity": "sha1-nr23Y1rQmccNzEwqH1AEKI6L2SQ=",
       "dev": true
     },
-    "exec-sh": {
-      "version": "0.2.2",
-      "resolved": "https://registry.npmjs.org/exec-sh/-/exec-sh-0.2.2.tgz",
-      "integrity": "sha512-FIUCJz1RbuS0FKTdaAafAByGS0CPvU3R0MeHxgtl+djzCc//F8HakL8GzmVNZanasTbTAY/3DRFA0KpVqj/eAw==",
-      "dev": true,
-      "requires": {
-        "merge": "^1.2.0"
-      }
-    },
     "execa": {
-      "version": "0.7.0",
-      "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz",
-      "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=",
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/execa/-/execa-1.0.0.tgz",
+      "integrity": "sha512-adbxcyWV46qiHyvSp50TKt05tB4tK3HcmF7/nxfAdhnox83seTDbwnaqKO4sXRy7roHAIFqJP/Rw/AuEbX61LA==",
       "dev": true,
       "requires": {
-        "cross-spawn": "^5.0.1",
-        "get-stream": "^3.0.0",
+        "cross-spawn": "^6.0.0",
+        "get-stream": "^4.0.0",
         "is-stream": "^1.1.0",
         "npm-run-path": "^2.0.0",
         "p-finally": "^1.0.0",
@@ -3375,24 +3760,20 @@
       },
       "dependencies": {
         "cross-spawn": {
-          "version": "5.1.0",
-          "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz",
-          "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=",
+          "version": "6.0.5",
+          "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz",
+          "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==",
           "dev": true,
           "requires": {
-            "lru-cache": "^4.0.1",
+            "nice-try": "^1.0.4",
+            "path-key": "^2.0.1",
+            "semver": "^5.5.0",
             "shebang-command": "^1.2.0",
             "which": "^1.2.9"
           }
         }
       }
     },
-    "exit-hook": {
-      "version": "1.1.1",
-      "resolved": "https://registry.npmjs.org/exit-hook/-/exit-hook-1.1.1.tgz",
-      "integrity": "sha1-8FyiM7SMBdVP/wd2XfhQfpXAL/g=",
-      "dev": true
-    },
     "expand-brackets": {
       "version": "0.1.5",
       "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz",
@@ -3411,6 +3792,15 @@
         "fill-range": "^2.1.0"
       }
     },
+    "expand-tilde": {
+      "version": "2.0.2",
+      "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-2.0.2.tgz",
+      "integrity": "sha1-l+gBqgUt8CRU3kawK/YhZCzchQI=",
+      "dev": true,
+      "requires": {
+        "homedir-polyfill": "^1.0.1"
+      }
+    },
     "extend": {
       "version": "3.0.2",
       "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz",
@@ -3434,6 +3824,21 @@
           "requires": {
             "is-plain-object": "^2.0.4"
           }
+        },
+        "is-plain-object": {
+          "version": "2.0.4",
+          "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz",
+          "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==",
+          "dev": true,
+          "requires": {
+            "isobject": "^3.0.1"
+          }
+        },
+        "isobject": {
+          "version": "3.0.1",
+          "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz",
+          "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=",
+          "dev": true
         }
       }
     },
@@ -3490,21 +3895,21 @@
       "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=",
       "dev": true
     },
+    "fast-url-parser": {
+      "version": "1.1.3",
+      "resolved": "https://registry.npmjs.org/fast-url-parser/-/fast-url-parser-1.1.3.tgz",
+      "integrity": "sha1-9K8+qfNNiicc9YrSs3WfQx8LMY0=",
+      "dev": true,
+      "requires": {
+        "punycode": "^1.3.2"
+      }
+    },
     "fastparse": {
       "version": "1.1.1",
       "resolved": "https://registry.npmjs.org/fastparse/-/fastparse-1.1.1.tgz",
       "integrity": "sha1-0eJkOzipTXWDtHkGDmxK/8lAcfg=",
       "dev": true
     },
-    "fb-watchman": {
-      "version": "2.0.0",
-      "resolved": "https://registry.npmjs.org/fb-watchman/-/fb-watchman-2.0.0.tgz",
-      "integrity": "sha1-VOmr99+i8mzZsWNsWIwa/AXeXVg=",
-      "dev": true,
-      "requires": {
-        "bser": "^2.0.0"
-      }
-    },
     "fd-slicer": {
       "version": "1.0.1",
       "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.0.1.tgz",
@@ -3515,19 +3920,18 @@
       }
     },
     "figures": {
-      "version": "1.7.0",
-      "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz",
-      "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=",
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz",
+      "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=",
       "dev": true,
       "requires": {
-        "escape-string-regexp": "^1.0.5",
-        "object-assign": "^4.1.0"
+        "escape-string-regexp": "^1.0.5"
       }
     },
     "file-entry-cache": {
-      "version": "1.3.1",
-      "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-1.3.1.tgz",
-      "integrity": "sha1-RMYepgeuS+nBQC9B9EJwy/4zT/g=",
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-2.0.0.tgz",
+      "integrity": "sha1-w5KZDD5oR4PYOLjISkXYoEhFg2E=",
       "dev": true,
       "requires": {
         "flat-cache": "^1.2.1",
@@ -3719,12 +4123,6 @@
         "samsam": "1.x"
       }
     },
-    "formidable": {
-      "version": "1.0.11",
-      "resolved": "https://registry.npmjs.org/formidable/-/formidable-1.0.11.tgz",
-      "integrity": "sha1-aPYzJaA15kS297s9ESQ7l2HeGzA=",
-      "dev": true
-    },
     "fragment-cache": {
       "version": "0.2.1",
       "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz",
@@ -3734,10 +4132,10 @@
         "map-cache": "^0.2.2"
       }
     },
-    "fresh": {
+    "fs-exists-sync": {
       "version": "0.1.0",
-      "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.1.0.tgz",
-      "integrity": "sha1-A+SwF4Qk5MLV0ZpU2IFM3JeTSFA=",
+      "resolved": "https://registry.npmjs.org/fs-exists-sync/-/fs-exists-sync-0.1.0.tgz",
+      "integrity": "sha1-mC1ok6+RjnLQjeyehnP/K1qNat0=",
       "dev": true
     },
     "fs-extra": {
@@ -3778,7 +4176,8 @@
           "version": "2.1.1",
           "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz",
           "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "aproba": {
           "version": "1.2.0",
@@ -3802,13 +4201,15 @@
           "version": "1.0.0",
           "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz",
           "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "brace-expansion": {
           "version": "1.1.11",
           "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
           "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
           "dev": true,
+          "optional": true,
           "requires": {
             "balanced-match": "^1.0.0",
             "concat-map": "0.0.1"
@@ -3825,19 +4226,22 @@
           "version": "1.1.0",
           "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz",
           "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "concat-map": {
           "version": "0.0.1",
           "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz",
           "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "console-control-strings": {
           "version": "1.1.0",
           "resolved": "https://registry.npmjs.org/console-control-strings/-/console-control-strings-1.1.0.tgz",
           "integrity": "sha1-PXz0Rk22RG6mRL9LOVB/mFEAjo4=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "core-util-is": {
           "version": "1.0.2",
@@ -3968,7 +4372,8 @@
           "version": "2.0.3",
           "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz",
           "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "ini": {
           "version": "1.3.5",
@@ -3982,6 +4387,7 @@
           "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz",
           "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=",
           "dev": true,
+          "optional": true,
           "requires": {
             "number-is-nan": "^1.0.0"
           }
@@ -3998,6 +4404,7 @@
           "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz",
           "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==",
           "dev": true,
+          "optional": true,
           "requires": {
             "brace-expansion": "^1.1.7"
           }
@@ -4006,13 +4413,15 @@
           "version": "0.0.8",
           "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz",
           "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "minipass": {
           "version": "2.2.4",
           "resolved": "https://registry.npmjs.org/minipass/-/minipass-2.2.4.tgz",
           "integrity": "sha512-hzXIWWet/BzWhYs2b+u7dRHlruXhwdgvlTMDKC6Cb1U7ps6Ac6yQlR39xsbjWJE377YTCtKwIXIpJ5oP+j5y8g==",
           "dev": true,
+          "optional": true,
           "requires": {
             "safe-buffer": "^5.1.1",
             "yallist": "^3.0.0"
@@ -4033,6 +4442,7 @@
           "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz",
           "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=",
           "dev": true,
+          "optional": true,
           "requires": {
             "minimist": "0.0.8"
           }
@@ -4121,7 +4531,8 @@
           "version": "1.0.1",
           "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz",
           "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "object-assign": {
           "version": "4.1.1",
@@ -4135,6 +4546,7 @@
           "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
           "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=",
           "dev": true,
+          "optional": true,
           "requires": {
             "wrappy": "1"
           }
@@ -4230,7 +4642,8 @@
           "version": "5.1.1",
           "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz",
           "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "safer-buffer": {
           "version": "2.1.2",
@@ -4272,6 +4685,7 @@
           "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz",
           "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=",
           "dev": true,
+          "optional": true,
           "requires": {
             "code-point-at": "^1.0.0",
             "is-fullwidth-code-point": "^1.0.0",
@@ -4293,6 +4707,7 @@
           "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz",
           "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=",
           "dev": true,
+          "optional": true,
           "requires": {
             "ansi-regex": "^2.0.0"
           }
@@ -4341,13 +4756,15 @@
           "version": "1.0.2",
           "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
           "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=",
-          "dev": true
+          "dev": true,
+          "optional": true
         },
         "yallist": {
           "version": "3.0.2",
           "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.0.2.tgz",
           "integrity": "sha1-hFK0u36Dx8GI2AQcGoN8dz1ti7k=",
-          "dev": true
+          "dev": true,
+          "optional": true
         }
       }
     },
@@ -4384,24 +4801,27 @@
       "integrity": "sha512-mBBwmeGTrxEMO4pMaaf/uUEFHnYtwr8FTe8Y/mer4rcV/bye0qGm6pw1bGZFGStxC5O76c5ZAVBGnqHmOaJpdQ==",
       "dev": true
     },
-    "get-caller-file": {
-      "version": "1.0.3",
-      "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.3.tgz",
-      "integrity": "sha512-3t6rVToeoZfYSGd8YoLFR2DJkiQrIiUrGcjvFX2mDw3bn6k2OtwHN0TNCLbBO+w8qTvimhDkv+LSscbJY1vE6w==",
-      "dev": true
-    },
     "get-func-name": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/get-func-name/-/get-func-name-2.0.0.tgz",
       "integrity": "sha1-6td0q+5y4gQJQzoGY2YCPdaIekE=",
       "dev": true
     },
-    "get-stream": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz",
-      "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=",
+    "get-stdin": {
+      "version": "6.0.0",
+      "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-6.0.0.tgz",
+      "integrity": "sha512-jp4tHawyV7+fkkSKyvjuLZswblUtz+SQKzSWnBbii16BuZksJlU1wuBYXY75r+duh/llF1ur6oNwi+2ZzjKZ7g==",
       "dev": true
     },
+    "get-stream": {
+      "version": "4.1.0",
+      "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-4.1.0.tgz",
+      "integrity": "sha512-GMat4EJ5161kIy2HevLlr4luNjBgvmj413KaQA7jt4V8B4RDsfpHk7WQ9GVqfYyyx8OS/L66Kox+rJRNklLK7w==",
+      "dev": true,
+      "requires": {
+        "pump": "^3.0.0"
+      }
+    },
     "get-value": {
       "version": "2.0.6",
       "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz",
@@ -4416,6 +4836,28 @@
         "assert-plus": "^1.0.0"
       }
     },
+    "git-config-path": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/git-config-path/-/git-config-path-1.0.1.tgz",
+      "integrity": "sha1-bTP37WPbDQ4RgTFQO6s6ykfVRmQ=",
+      "dev": true,
+      "requires": {
+        "extend-shallow": "^2.0.1",
+        "fs-exists-sync": "^0.1.0",
+        "homedir-polyfill": "^1.0.0"
+      },
+      "dependencies": {
+        "extend-shallow": {
+          "version": "2.0.1",
+          "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
+          "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
+          "dev": true,
+          "requires": {
+            "is-extendable": "^0.1.0"
+          }
+        }
+      }
+    },
     "github": {
       "version": "9.3.1",
       "resolved": "https://registry.npmjs.org/github/-/github-9.3.1.tgz",
@@ -4428,6 +4870,51 @@
         "netrc": "^0.1.4"
       }
     },
+    "gitlab": {
+      "version": "10.2.1",
+      "resolved": "https://registry.npmjs.org/gitlab/-/gitlab-10.2.1.tgz",
+      "integrity": "sha512-z+DxRF1C9uayVbocs9aJkJz+kGy14TSm1noB/rAIEBbXOkOYbjKxyuqJzt+0zeFpXFdgA0yq6DVVbvM7HIfGwg==",
+      "dev": true,
+      "requires": {
+        "form-data": "^2.5.0",
+        "humps": "^2.0.1",
+        "ky": "^0.12.0",
+        "ky-universal": "^0.3.0",
+        "li": "^1.3.0",
+        "query-string": "^6.8.2",
+        "universal-url": "^2.0.0"
+      },
+      "dependencies": {
+        "form-data": {
+          "version": "2.5.1",
+          "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.5.1.tgz",
+          "integrity": "sha512-m21N3WOmEEURgk6B9GLOE4RuWOFf28Lhh9qGYeNlGq4VDXUlJy2th2slBNU8Gp8EzloYZOibZJ7t5ecIrFSjVA==",
+          "dev": true,
+          "requires": {
+            "asynckit": "^0.4.0",
+            "combined-stream": "^1.0.6",
+            "mime-types": "^2.1.12"
+          }
+        },
+        "query-string": {
+          "version": "6.8.3",
+          "resolved": "https://registry.npmjs.org/query-string/-/query-string-6.8.3.tgz",
+          "integrity": "sha512-llcxWccnyaWlODe7A9hRjkvdCKamEKTh+wH8ITdTc3OhchaqUZteiSCX/2ablWHVrkVIe04dntnaZJ7BdyW0lQ==",
+          "dev": true,
+          "requires": {
+            "decode-uri-component": "^0.2.0",
+            "split-on-first": "^1.0.0",
+            "strict-uri-encode": "^2.0.0"
+          }
+        },
+        "strict-uri-encode": {
+          "version": "2.0.0",
+          "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-2.0.0.tgz",
+          "integrity": "sha1-ucczDHBChi9rFC3CdLvMWGbONUY=",
+          "dev": true
+        }
+      }
+    },
     "glob": {
       "version": "5.0.15",
       "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz",
@@ -4460,6 +4947,34 @@
         "is-glob": "^2.0.0"
       }
     },
+    "glob-slash": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/glob-slash/-/glob-slash-1.0.0.tgz",
+      "integrity": "sha1-/lLvpDMjP3Si/mTHq7m8hIICq5U=",
+      "dev": true
+    },
+    "glob-slasher": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/glob-slasher/-/glob-slasher-1.0.1.tgz",
+      "integrity": "sha1-dHoOW7IiZC7hDT4FRD4QlJPLD44=",
+      "dev": true,
+      "requires": {
+        "glob-slash": "^1.0.0",
+        "lodash.isobject": "^2.4.1",
+        "toxic": "^1.0.0"
+      },
+      "dependencies": {
+        "lodash.isobject": {
+          "version": "2.4.1",
+          "resolved": "https://registry.npmjs.org/lodash.isobject/-/lodash.isobject-2.4.1.tgz",
+          "integrity": "sha1-Wi5H/mmVPx7mMafrof5k0tBlWPU=",
+          "dev": true,
+          "requires": {
+            "lodash._objecttypes": "~2.4.1"
+          }
+        }
+      }
+    },
     "globals": {
       "version": "9.18.0",
       "resolved": "https://registry.npmjs.org/globals/-/globals-9.18.0.tgz",
@@ -4520,24 +5035,54 @@
       "dev": true
     },
     "handlebars": {
-      "version": "4.0.11",
-      "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.0.11.tgz",
-      "integrity": "sha1-Ywo13+ApS8KB7a5v/F0yn8eYLcw=",
+      "version": "4.0.14",
+      "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.0.14.tgz",
+      "integrity": "sha512-E7tDoyAA8ilZIV3xDJgl18sX3M8xB9/fMw8+mfW4msLW8jlX97bAnWgT3pmaNXuvzIEgSBMnAHfuXsB2hdzfow==",
       "dev": true,
       "requires": {
-        "async": "^1.4.0",
+        "async": "^2.5.0",
         "optimist": "^0.6.1",
-        "source-map": "^0.4.4",
-        "uglify-js": "^2.6"
+        "source-map": "^0.6.1",
+        "uglify-js": "^3.1.4"
       },
       "dependencies": {
-        "source-map": {
-          "version": "0.4.4",
-          "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.4.4.tgz",
-          "integrity": "sha1-66T12pwNyZneaAMti092FzZSA2s=",
+        "async": {
+          "version": "2.6.3",
+          "resolved": "https://registry.npmjs.org/async/-/async-2.6.3.tgz",
+          "integrity": "sha512-zflvls11DCy+dQWzTW2dzuilv8Z5X/pjfmZOWba6TNIVDm+2UDaJmXSOXlasHKfNBs8oo3M0aT50fDEWfKZjXg==",
           "dev": true,
           "requires": {
-            "amdefine": ">=0.0.4"
+            "lodash": "^4.17.14"
+          }
+        },
+        "commander": {
+          "version": "2.20.3",
+          "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz",
+          "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==",
+          "dev": true,
+          "optional": true
+        },
+        "lodash": {
+          "version": "4.17.15",
+          "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.15.tgz",
+          "integrity": "sha512-8xOcRHvCjnocdS5cpwXQXVzmmh5e5+saE2QGoeQmbKmRS6J3VQppPOIt0MnmE+4xlZoumy0GPG0D0MVIQbNA1A==",
+          "dev": true
+        },
+        "source-map": {
+          "version": "0.6.1",
+          "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
+          "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==",
+          "dev": true
+        },
+        "uglify-js": {
+          "version": "3.6.5",
+          "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.6.5.tgz",
+          "integrity": "sha512-7L3W+Npia1OCr5Blp4/Vw83tK1mu5gnoIURtT1fUVfQ3Kf8WStWV6NJz0fdoBJZls0KlweruRTLVe6XLafmy5g==",
+          "dev": true,
+          "optional": true,
+          "requires": {
+            "commander": "~2.20.3",
+            "source-map": "~0.6.1"
           }
         }
       }
@@ -4656,6 +5201,12 @@
         "pinkie-promise": "^2.0.0"
       }
     },
+    "hasurl": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/hasurl/-/hasurl-1.0.0.tgz",
+      "integrity": "sha512-43ypUd3DbwyCT01UYpA99AEZxZ4aKtRxWGBHEIbjcOsUghd9YUON0C+JF6isNjaiwC/UF5neaUudy6JS9jZPZQ==",
+      "dev": true
+    },
     "hawk": {
       "version": "2.3.1",
       "resolved": "https://registry.npmjs.org/hawk/-/hawk-2.3.1.tgz",
@@ -4690,11 +5241,14 @@
         "os-tmpdir": "^1.0.1"
       }
     },
-    "hosted-git-info": {
-      "version": "2.7.1",
-      "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.7.1.tgz",
-      "integrity": "sha512-7T/BxH19zbcCTa8XkMlbK5lTo1WtgkFi3GvdWEyNuc4Vex7/9Dqbnpsf4JMydcfj9HCg4zUWFTL3Za6lapg5/w==",
-      "dev": true
+    "homedir-polyfill": {
+      "version": "1.0.3",
+      "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.3.tgz",
+      "integrity": "sha512-eSmmWE5bZTK2Nou4g0AI3zZ9rswp7GRKoKXS1BLUkvPviOqs4YTN1djQIqrXy9k5gEtdLPy86JjRwsNM9tnDcA==",
+      "dev": true,
+      "requires": {
+        "parse-passwd": "^1.0.0"
+      }
     },
     "html-comment-regex": {
       "version": "1.1.1",
@@ -4702,15 +5256,6 @@
       "integrity": "sha1-ZouTd26q5V696POtRkswekljYl4=",
       "dev": true
     },
-    "html-encoding-sniffer": {
-      "version": "1.0.2",
-      "resolved": "https://registry.npmjs.org/html-encoding-sniffer/-/html-encoding-sniffer-1.0.2.tgz",
-      "integrity": "sha512-71lZziiDnsuabfdYiUeWdCVyKuqwWi23L8YeIgV9jSSZHCtb6wB1BKWooH7L3tn4/FuZJMVWyNaIDr4RGmaSYw==",
-      "dev": true,
-      "requires": {
-        "whatwg-encoding": "^1.0.1"
-      }
-    },
     "htmlescape": {
       "version": "1.1.1",
       "resolved": "https://registry.npmjs.org/htmlescape/-/htmlescape-1.1.1.tgz",
@@ -4748,6 +5293,36 @@
         }
       }
     },
+    "http-proxy-agent": {
+      "version": "2.1.0",
+      "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-2.1.0.tgz",
+      "integrity": "sha512-qwHbBLV7WviBl0rQsOzH6o5lwyOIvwp/BdFnvVxXORldu5TmjFfjzBcWUWS5kWAZhmv+JtiDhSuQCp4sBfbIgg==",
+      "dev": true,
+      "requires": {
+        "agent-base": "4",
+        "debug": "3.1.0"
+      },
+      "dependencies": {
+        "agent-base": {
+          "version": "4.3.0",
+          "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-4.3.0.tgz",
+          "integrity": "sha512-salcGninV0nPrwpGNn4VTXBb1SOuXQBiqbrNXoeizJsHrsL6ERFM2Ne3JUSBWRE6aeNJI2ROP/WEEIDUiDe3cg==",
+          "dev": true,
+          "requires": {
+            "es6-promisify": "^5.0.0"
+          }
+        },
+        "debug": {
+          "version": "3.1.0",
+          "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz",
+          "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==",
+          "dev": true,
+          "requires": {
+            "ms": "2.0.0"
+          }
+        }
+      }
+    },
     "http-server": {
       "version": "0.9.0",
       "resolved": "https://registry.npmjs.org/http-server/-/http-server-0.9.0.tgz",
@@ -4799,6 +5374,18 @@
         "extend": "3"
       }
     },
+    "humps": {
+      "version": "2.0.1",
+      "resolved": "https://registry.npmjs.org/humps/-/humps-2.0.1.tgz",
+      "integrity": "sha1-3QLqYIG9BWjcXQcxhEY5V7qe+ao=",
+      "dev": true
+    },
+    "hyperlinker": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/hyperlinker/-/hyperlinker-1.0.0.tgz",
+      "integrity": "sha512-Ty8UblRWFEcfSuIaajM34LdPXIhbs1ajEX/BBPv24J+enSVaEVY63xQ6lTO9VRYS5LAoghIG0IDJ+p+IPzKUQQ==",
+      "dev": true
+    },
     "iconv-lite": {
       "version": "0.4.23",
       "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz",
@@ -4825,13 +5412,6 @@
       "integrity": "sha512-Pgs951kaMm5GXP7MOvxERINe3gsaVjUWFm+UZPSq9xYriQAksyhg0csnS0KXSNRD5NmNdapXEpjxG49+AKh/ug==",
       "dev": true
     },
-    "image-size": {
-      "version": "0.5.5",
-      "resolved": "https://registry.npmjs.org/image-size/-/image-size-0.5.5.tgz",
-      "integrity": "sha1-Cd/Uq50g4p6xw+gLiZA3jfnjy5w=",
-      "dev": true,
-      "optional": true
-    },
     "imurmurhash": {
       "version": "0.1.4",
       "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz",
@@ -4881,24 +5461,83 @@
       }
     },
     "inquirer": {
-      "version": "0.12.0",
-      "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-0.12.0.tgz",
-      "integrity": "sha1-HvK/1jUE3wvHV4X/+MLEHfEvB34=",
+      "version": "3.3.0",
+      "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-3.3.0.tgz",
+      "integrity": "sha512-h+xtnyk4EwKvFWHrUYsWErEVR+igKtLdchu+o0Z1RL7VU/jVMFbYir2bp6bAj8efFNxWqHX0dIss6fJQ+/+qeQ==",
       "dev": true,
       "requires": {
-        "ansi-escapes": "^1.1.0",
-        "ansi-regex": "^2.0.0",
-        "chalk": "^1.0.0",
-        "cli-cursor": "^1.0.1",
+        "ansi-escapes": "^3.0.0",
+        "chalk": "^2.0.0",
+        "cli-cursor": "^2.1.0",
         "cli-width": "^2.0.0",
-        "figures": "^1.3.5",
+        "external-editor": "^2.0.4",
+        "figures": "^2.0.0",
         "lodash": "^4.3.0",
-        "readline2": "^1.0.1",
-        "run-async": "^0.1.0",
-        "rx-lite": "^3.1.2",
-        "string-width": "^1.0.1",
-        "strip-ansi": "^3.0.0",
+        "mute-stream": "0.0.7",
+        "run-async": "^2.2.0",
+        "rx-lite": "^4.0.8",
+        "rx-lite-aggregates": "^4.0.8",
+        "string-width": "^2.1.0",
+        "strip-ansi": "^4.0.0",
         "through": "^2.3.6"
+      },
+      "dependencies": {
+        "ansi-regex": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz",
+          "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=",
+          "dev": true
+        },
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
+          "dev": true,
+          "requires": {
+            "color-convert": "^1.9.0"
+          }
+        },
+        "chalk": {
+          "version": "2.4.2",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
+          "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "has-flag": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+          "dev": true
+        },
+        "rx-lite": {
+          "version": "4.0.8",
+          "resolved": "https://registry.npmjs.org/rx-lite/-/rx-lite-4.0.8.tgz",
+          "integrity": "sha1-Cx4Rr4vESDbwSmQH6S2kJGe3lEQ=",
+          "dev": true
+        },
+        "strip-ansi": {
+          "version": "4.0.0",
+          "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz",
+          "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=",
+          "dev": true,
+          "requires": {
+            "ansi-regex": "^3.0.0"
+          }
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          }
+        }
       }
     },
     "insert-module-globals": {
@@ -4934,12 +5573,6 @@
         "loose-envify": "^1.0.0"
       }
     },
-    "invert-kv": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz",
-      "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=",
-      "dev": true
-    },
     "ipv4": {
       "version": "1.0.4",
       "resolved": "https://registry.npmjs.org/ipv4/-/ipv4-1.0.4.tgz",
@@ -4957,12 +5590,6 @@
       "integrity": "sha1-LKmwM2UREYVUEvFr5dd8YqRYp2Y=",
       "dev": true
     },
-    "is": {
-      "version": "3.2.1",
-      "resolved": "https://registry.npmjs.org/is/-/is-3.2.1.tgz",
-      "integrity": "sha1-0Kwq1V63sL7JJqUmb2xmKqqD3KU=",
-      "dev": true
-    },
     "is-absolute-url": {
       "version": "2.1.0",
       "resolved": "https://registry.npmjs.org/is-absolute-url/-/is-absolute-url-2.1.0.tgz",
@@ -4999,15 +5626,6 @@
       "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==",
       "dev": true
     },
-    "is-builtin-module": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/is-builtin-module/-/is-builtin-module-1.0.0.tgz",
-      "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=",
-      "dev": true,
-      "requires": {
-        "builtin-modules": "^1.0.0"
-      }
-    },
     "is-data-descriptor": {
       "version": "0.1.4",
       "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz",
@@ -5079,13 +5697,10 @@
       }
     },
     "is-fullwidth-code-point": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz",
-      "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=",
-      "dev": true,
-      "requires": {
-        "number-is-nan": "^1.0.0"
-      }
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz",
+      "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=",
+      "dev": true
     },
     "is-glob": {
       "version": "2.0.1",
@@ -5161,18 +5776,18 @@
       "dev": true
     },
     "is-plain-object": {
-      "version": "2.0.4",
-      "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz",
-      "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==",
+      "version": "3.0.0",
+      "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-3.0.0.tgz",
+      "integrity": "sha512-tZIpofR+P05k8Aocp7UI/2UTa9lTJSebCXpFFoR9aibpokDj/uXBsJ8luUu0tTVYKkMU6URDUuOfJZ7koewXvg==",
       "dev": true,
       "requires": {
-        "isobject": "^3.0.1"
+        "isobject": "^4.0.0"
       },
       "dependencies": {
         "isobject": {
-          "version": "3.0.1",
-          "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz",
-          "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=",
+          "version": "4.0.0",
+          "resolved": "https://registry.npmjs.org/isobject/-/isobject-4.0.0.tgz",
+          "integrity": "sha512-S/2fF5wH8SJA/kmwr6HYhK/RI/OkhD84k8ntalo0iJjZikgq1XFvR5M8NPT1x5F7fBwCG3qHfnzeP/Vh/ZxCUA==",
           "dev": true
         }
       }
@@ -5227,12 +5842,6 @@
       "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz",
       "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo="
     },
-    "is-utf8": {
-      "version": "0.2.1",
-      "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz",
-      "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=",
-      "dev": true
-    },
     "is-windows": {
       "version": "1.0.2",
       "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz",
@@ -5288,27 +5897,6 @@
       "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz",
       "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo="
     },
-    "istanbul-lib-coverage": {
-      "version": "1.2.0",
-      "resolved": "https://registry.npmjs.org/istanbul-lib-coverage/-/istanbul-lib-coverage-1.2.0.tgz",
-      "integrity": "sha512-GvgM/uXRwm+gLlvkWHTjDAvwynZkL9ns15calTrmhGgowlwJBbWMYzWbKqE2DT6JDP1AFXKa+Zi0EkqNCUqY0A==",
-      "dev": true
-    },
-    "istanbul-lib-instrument": {
-      "version": "1.10.1",
-      "resolved": "https://registry.npmjs.org/istanbul-lib-instrument/-/istanbul-lib-instrument-1.10.1.tgz",
-      "integrity": "sha512-1dYuzkOCbuR5GRJqySuZdsmsNKPL3PTuyPevQfoCXJePT9C8y1ga75neU+Tuy9+yS3G/dgx8wgOmp2KLpgdoeQ==",
-      "dev": true,
-      "requires": {
-        "babel-generator": "^6.18.0",
-        "babel-template": "^6.16.0",
-        "babel-traverse": "^6.18.0",
-        "babel-types": "^6.18.0",
-        "babylon": "^6.18.0",
-        "istanbul-lib-coverage": "^1.2.0",
-        "semver": "^5.3.0"
-      }
-    },
     "jade": {
       "version": "0.26.3",
       "resolved": "https://registry.npmjs.org/jade/-/jade-0.26.3.tgz",
@@ -5333,259 +5921,6 @@
         }
       }
     },
-    "jest-config": {
-      "version": "19.0.4",
-      "resolved": "https://registry.npmjs.org/jest-config/-/jest-config-19.0.4.tgz",
-      "integrity": "sha1-QpgCEdRkF+kcp6v/0IbCcCNPc/0=",
-      "dev": true,
-      "requires": {
-        "chalk": "^1.1.1",
-        "jest-environment-jsdom": "^19.0.2",
-        "jest-environment-node": "^19.0.2",
-        "jest-jasmine2": "^19.0.2",
-        "jest-regex-util": "^19.0.0",
-        "jest-resolve": "^19.0.2",
-        "jest-validate": "^19.0.2",
-        "pretty-format": "^19.0.0"
-      }
-    },
-    "jest-diff": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/jest-diff/-/jest-diff-19.0.0.tgz",
-      "integrity": "sha1-0VY8/FbItgIymI+8BdTRbtkPBjw=",
-      "dev": true,
-      "requires": {
-        "chalk": "^1.1.3",
-        "diff": "^3.0.0",
-        "jest-matcher-utils": "^19.0.0",
-        "pretty-format": "^19.0.0"
-      }
-    },
-    "jest-environment-jsdom": {
-      "version": "19.0.2",
-      "resolved": "https://registry.npmjs.org/jest-environment-jsdom/-/jest-environment-jsdom-19.0.2.tgz",
-      "integrity": "sha1-ztqFnEpLlKs15N59q1S5JvKT5KM=",
-      "dev": true,
-      "requires": {
-        "jest-mock": "^19.0.0",
-        "jest-util": "^19.0.2",
-        "jsdom": "^9.11.0"
-      }
-    },
-    "jest-environment-node": {
-      "version": "19.0.2",
-      "resolved": "https://registry.npmjs.org/jest-environment-node/-/jest-environment-node-19.0.2.tgz",
-      "integrity": "sha1-boQHnbh+0h0MBeH5Zp8gexFv6Zs=",
-      "dev": true,
-      "requires": {
-        "jest-mock": "^19.0.0",
-        "jest-util": "^19.0.2"
-      }
-    },
-    "jest-file-exists": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/jest-file-exists/-/jest-file-exists-19.0.0.tgz",
-      "integrity": "sha1-zKLlh6EeyS4kz+qz+KlNZX8/zrg=",
-      "dev": true
-    },
-    "jest-haste-map": {
-      "version": "19.0.2",
-      "resolved": "https://registry.npmjs.org/jest-haste-map/-/jest-haste-map-19.0.2.tgz",
-      "integrity": "sha1-KGSEw6Fuhtp4crCHfDXc4ww9bwc=",
-      "dev": true,
-      "requires": {
-        "fb-watchman": "^2.0.0",
-        "graceful-fs": "^4.1.6",
-        "micromatch": "^2.3.11",
-        "sane": "~1.5.0",
-        "worker-farm": "^1.3.1"
-      }
-    },
-    "jest-jasmine2": {
-      "version": "19.0.2",
-      "resolved": "https://registry.npmjs.org/jest-jasmine2/-/jest-jasmine2-19.0.2.tgz",
-      "integrity": "sha1-FnmRrIJZgfsagArxJug6/MqDLHM=",
-      "dev": true,
-      "requires": {
-        "graceful-fs": "^4.1.6",
-        "jest-matcher-utils": "^19.0.0",
-        "jest-matchers": "^19.0.0",
-        "jest-message-util": "^19.0.0",
-        "jest-snapshot": "^19.0.2"
-      }
-    },
-    "jest-matcher-utils": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/jest-matcher-utils/-/jest-matcher-utils-19.0.0.tgz",
-      "integrity": "sha1-Xs2bY1ZdKwAfYfv37Ex/U3lkVk0=",
-      "dev": true,
-      "requires": {
-        "chalk": "^1.1.3",
-        "pretty-format": "^19.0.0"
-      }
-    },
-    "jest-matchers": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/jest-matchers/-/jest-matchers-19.0.0.tgz",
-      "integrity": "sha1-x07Mbr/sBvOEdnuk1vpKQtZ1V1Q=",
-      "dev": true,
-      "requires": {
-        "jest-diff": "^19.0.0",
-        "jest-matcher-utils": "^19.0.0",
-        "jest-message-util": "^19.0.0",
-        "jest-regex-util": "^19.0.0"
-      }
-    },
-    "jest-message-util": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/jest-message-util/-/jest-message-util-19.0.0.tgz",
-      "integrity": "sha1-cheWuJwOTXYWBvm6jLgoo7YkZBY=",
-      "dev": true,
-      "requires": {
-        "chalk": "^1.1.1",
-        "micromatch": "^2.3.11"
-      }
-    },
-    "jest-mock": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/jest-mock/-/jest-mock-19.0.0.tgz",
-      "integrity": "sha1-ZwOGQelgerLOCOxKjLg6q7yJnQE=",
-      "dev": true
-    },
-    "jest-regex-util": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/jest-regex-util/-/jest-regex-util-19.0.0.tgz",
-      "integrity": "sha1-t3VFhxEq7eFFZRC7H2r+dO9ZhpE=",
-      "dev": true
-    },
-    "jest-resolve": {
-      "version": "19.0.2",
-      "resolved": "https://registry.npmjs.org/jest-resolve/-/jest-resolve-19.0.2.tgz",
-      "integrity": "sha1-V5NXXeTweuwy99f/DGwYGWPu+zw=",
-      "dev": true,
-      "requires": {
-        "browser-resolve": "^1.11.2",
-        "jest-haste-map": "^19.0.0",
-        "resolve": "^1.2.0"
-      },
-      "dependencies": {
-        "resolve": {
-          "version": "1.8.1",
-          "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.8.1.tgz",
-          "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==",
-          "dev": true,
-          "requires": {
-            "path-parse": "^1.0.5"
-          }
-        }
-      }
-    },
-    "jest-runtime": {
-      "version": "19.0.4",
-      "resolved": "https://registry.npmjs.org/jest-runtime/-/jest-runtime-19.0.4.tgz",
-      "integrity": "sha1-8WfZ8TR3UvICc2EGeSZIU0n8wkU=",
-      "dev": true,
-      "requires": {
-        "babel-core": "^6.0.0",
-        "babel-jest": "^19.0.0",
-        "babel-plugin-istanbul": "^4.0.0",
-        "chalk": "^1.1.3",
-        "graceful-fs": "^4.1.6",
-        "jest-config": "^19.0.2",
-        "jest-file-exists": "^19.0.0",
-        "jest-haste-map": "^19.0.0",
-        "jest-regex-util": "^19.0.0",
-        "jest-resolve": "^19.0.2",
-        "jest-util": "^19.0.2",
-        "json-stable-stringify": "^1.0.1",
-        "micromatch": "^2.3.11",
-        "strip-bom": "3.0.0",
-        "yargs": "^6.3.0"
-      },
-      "dependencies": {
-        "camelcase": {
-          "version": "3.0.0",
-          "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz",
-          "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=",
-          "dev": true
-        },
-        "cliui": {
-          "version": "3.2.0",
-          "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz",
-          "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=",
-          "dev": true,
-          "requires": {
-            "string-width": "^1.0.1",
-            "strip-ansi": "^3.0.1",
-            "wrap-ansi": "^2.0.0"
-          }
-        },
-        "yargs": {
-          "version": "6.6.0",
-          "resolved": "https://registry.npmjs.org/yargs/-/yargs-6.6.0.tgz",
-          "integrity": "sha1-eC7CHvQDNF+DCoCMo9UTr1YGUgg=",
-          "dev": true,
-          "requires": {
-            "camelcase": "^3.0.0",
-            "cliui": "^3.2.0",
-            "decamelize": "^1.1.1",
-            "get-caller-file": "^1.0.1",
-            "os-locale": "^1.4.0",
-            "read-pkg-up": "^1.0.1",
-            "require-directory": "^2.1.1",
-            "require-main-filename": "^1.0.1",
-            "set-blocking": "^2.0.0",
-            "string-width": "^1.0.2",
-            "which-module": "^1.0.0",
-            "y18n": "^3.2.1",
-            "yargs-parser": "^4.2.0"
-          }
-        }
-      }
-    },
-    "jest-snapshot": {
-      "version": "19.0.2",
-      "resolved": "https://registry.npmjs.org/jest-snapshot/-/jest-snapshot-19.0.2.tgz",
-      "integrity": "sha1-nBshYhT3GHw4v9XHCx76sWsP9Qs=",
-      "dev": true,
-      "requires": {
-        "chalk": "^1.1.3",
-        "jest-diff": "^19.0.0",
-        "jest-file-exists": "^19.0.0",
-        "jest-matcher-utils": "^19.0.0",
-        "jest-util": "^19.0.2",
-        "natural-compare": "^1.4.0",
-        "pretty-format": "^19.0.0"
-      }
-    },
-    "jest-util": {
-      "version": "19.0.2",
-      "resolved": "https://registry.npmjs.org/jest-util/-/jest-util-19.0.2.tgz",
-      "integrity": "sha1-4KAjKiq55rK1Nmi9s1NMK1l37UE=",
-      "dev": true,
-      "requires": {
-        "chalk": "^1.1.1",
-        "graceful-fs": "^4.1.6",
-        "jest-file-exists": "^19.0.0",
-        "jest-message-util": "^19.0.0",
-        "jest-mock": "^19.0.0",
-        "jest-validate": "^19.0.2",
-        "leven": "^2.0.0",
-        "mkdirp": "^0.5.1"
-      }
-    },
-    "jest-validate": {
-      "version": "19.0.2",
-      "resolved": "https://registry.npmjs.org/jest-validate/-/jest-validate-19.0.2.tgz",
-      "integrity": "sha1-3FNN9fEnjVtj3zKxQkHU2/ckTAw=",
-      "dev": true,
-      "requires": {
-        "chalk": "^1.1.1",
-        "jest-matcher-utils": "^19.0.0",
-        "leven": "^2.0.0",
-        "pretty-format": "^19.0.0"
-      }
-    },
     "js-base64": {
       "version": "2.4.8",
       "resolved": "https://registry.npmjs.org/js-base64/-/js-base64-2.4.8.tgz",
@@ -5634,190 +5969,12 @@
       "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=",
       "optional": true
     },
-    "jsdom": {
-      "version": "9.12.0",
-      "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-9.12.0.tgz",
-      "integrity": "sha1-6MVG//ywbADUgzyoRBD+1/igl9Q=",
-      "dev": true,
-      "requires": {
-        "abab": "^1.0.3",
-        "acorn": "^4.0.4",
-        "acorn-globals": "^3.1.0",
-        "array-equal": "^1.0.0",
-        "content-type-parser": "^1.0.1",
-        "cssom": ">= 0.3.2 < 0.4.0",
-        "cssstyle": ">= 0.2.37 < 0.3.0",
-        "escodegen": "^1.6.1",
-        "html-encoding-sniffer": "^1.0.1",
-        "nwmatcher": ">= 1.3.9 < 2.0.0",
-        "parse5": "^1.5.1",
-        "request": "^2.79.0",
-        "sax": "^1.2.1",
-        "symbol-tree": "^3.2.1",
-        "tough-cookie": "^2.3.2",
-        "webidl-conversions": "^4.0.0",
-        "whatwg-encoding": "^1.0.1",
-        "whatwg-url": "^4.3.0",
-        "xml-name-validator": "^2.0.1"
-      }
-    },
     "jsesc": {
       "version": "1.3.0",
       "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-1.3.0.tgz",
       "integrity": "sha1-RsP+yMGJKxKwgz25vHYiF226s0s=",
       "dev": true
     },
-    "jsome": {
-      "version": "2.5.0",
-      "resolved": "https://registry.npmjs.org/jsome/-/jsome-2.5.0.tgz",
-      "integrity": "sha1-XkF+70NB/+uD7ov6kmWzbVb+Se0=",
-      "dev": true,
-      "requires": {
-        "chalk": "^2.3.0",
-        "json-stringify-safe": "^5.0.1",
-        "yargs": "^11.0.0"
-      },
-      "dependencies": {
-        "ansi-regex": {
-          "version": "3.0.0",
-          "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz",
-          "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=",
-          "dev": true
-        },
-        "ansi-styles": {
-          "version": "3.2.1",
-          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
-          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
-          "dev": true,
-          "requires": {
-            "color-convert": "^1.9.0"
-          }
-        },
-        "camelcase": {
-          "version": "4.1.0",
-          "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz",
-          "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=",
-          "dev": true
-        },
-        "chalk": {
-          "version": "2.4.1",
-          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.1.tgz",
-          "integrity": "sha512-ObN6h1v2fTJSmUXoS3nMQ92LbDK9be4TV+6G+omQlGJFdcUX5heKi1LZ1YnRMIgwTLEj3E24bT6tYni50rlCfQ==",
-          "dev": true,
-          "requires": {
-            "ansi-styles": "^3.2.1",
-            "escape-string-regexp": "^1.0.5",
-            "supports-color": "^5.3.0"
-          }
-        },
-        "cliui": {
-          "version": "4.1.0",
-          "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.1.0.tgz",
-          "integrity": "sha512-4FG+RSG9DL7uEwRUZXZn3SS34DiDPfzP0VOiEwtUWlE+AR2EIg+hSyvrIgUUfhdgR/UkAeW2QHgeP+hWrXs7jQ==",
-          "dev": true,
-          "requires": {
-            "string-width": "^2.1.1",
-            "strip-ansi": "^4.0.0",
-            "wrap-ansi": "^2.0.0"
-          }
-        },
-        "find-up": {
-          "version": "2.1.0",
-          "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz",
-          "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=",
-          "dev": true,
-          "requires": {
-            "locate-path": "^2.0.0"
-          }
-        },
-        "has-flag": {
-          "version": "3.0.0",
-          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
-          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
-          "dev": true
-        },
-        "is-fullwidth-code-point": {
-          "version": "2.0.0",
-          "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz",
-          "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=",
-          "dev": true
-        },
-        "os-locale": {
-          "version": "2.1.0",
-          "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz",
-          "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==",
-          "dev": true,
-          "requires": {
-            "execa": "^0.7.0",
-            "lcid": "^1.0.0",
-            "mem": "^1.1.0"
-          }
-        },
-        "string-width": {
-          "version": "2.1.1",
-          "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz",
-          "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==",
-          "dev": true,
-          "requires": {
-            "is-fullwidth-code-point": "^2.0.0",
-            "strip-ansi": "^4.0.0"
-          }
-        },
-        "strip-ansi": {
-          "version": "4.0.0",
-          "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz",
-          "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=",
-          "dev": true,
-          "requires": {
-            "ansi-regex": "^3.0.0"
-          }
-        },
-        "supports-color": {
-          "version": "5.4.0",
-          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.4.0.tgz",
-          "integrity": "sha512-zjaXglF5nnWpsq470jSv6P9DwPvgLkuapYmfDm3JWOm0vkNTVF2tI4UrN2r6jH1qM/uc/WtxYY1hYoA2dOKj5w==",
-          "dev": true,
-          "requires": {
-            "has-flag": "^3.0.0"
-          }
-        },
-        "which-module": {
-          "version": "2.0.0",
-          "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz",
-          "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=",
-          "dev": true
-        },
-        "yargs": {
-          "version": "11.1.0",
-          "resolved": "https://registry.npmjs.org/yargs/-/yargs-11.1.0.tgz",
-          "integrity": "sha512-NwW69J42EsCSanF8kyn5upxvjp5ds+t3+udGBeTbFnERA+lF541DDpMawzo4z6W/QrzNM18D+BPMiOBibnFV5A==",
-          "dev": true,
-          "requires": {
-            "cliui": "^4.0.0",
-            "decamelize": "^1.1.1",
-            "find-up": "^2.1.0",
-            "get-caller-file": "^1.0.1",
-            "os-locale": "^2.0.0",
-            "require-directory": "^2.1.1",
-            "require-main-filename": "^1.0.1",
-            "set-blocking": "^2.0.0",
-            "string-width": "^2.0.0",
-            "which-module": "^2.0.0",
-            "y18n": "^3.2.1",
-            "yargs-parser": "^9.0.2"
-          }
-        },
-        "yargs-parser": {
-          "version": "9.0.2",
-          "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-9.0.2.tgz",
-          "integrity": "sha1-nM9qQ0YP5O1Aqbto9I1DuKaMwHc=",
-          "dev": true,
-          "requires": {
-            "camelcase": "^4.1.0"
-          }
-        }
-      }
-    },
     "json-loader": {
       "version": "0.5.7",
       "resolved": "https://registry.npmjs.org/json-loader/-/json-loader-0.5.7.tgz",
@@ -5834,15 +5991,6 @@
       "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz",
       "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A="
     },
-    "json-stable-stringify": {
-      "version": "1.0.1",
-      "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz",
-      "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=",
-      "dev": true,
-      "requires": {
-        "jsonify": "~0.0.0"
-      }
-    },
     "json-stable-stringify-without-jsonify": {
       "version": "1.0.1",
       "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz",
@@ -5896,6 +6044,38 @@
       "integrity": "sha1-T9kss04OnbPInIYi7PUfm5eMbLk=",
       "dev": true
     },
+    "jsonwebtoken": {
+      "version": "8.5.1",
+      "resolved": "https://registry.npmjs.org/jsonwebtoken/-/jsonwebtoken-8.5.1.tgz",
+      "integrity": "sha512-XjwVfRS6jTMsqYs0EsuJ4LGxXV14zQybNd4L2r0UvbVnSF9Af8x7p5MzbJ90Ioz/9TI41/hTCvznF/loiSzn8w==",
+      "dev": true,
+      "requires": {
+        "jws": "^3.2.2",
+        "lodash.includes": "^4.3.0",
+        "lodash.isboolean": "^3.0.3",
+        "lodash.isinteger": "^4.0.4",
+        "lodash.isnumber": "^3.0.3",
+        "lodash.isplainobject": "^4.0.6",
+        "lodash.isstring": "^4.0.1",
+        "lodash.once": "^4.0.0",
+        "ms": "^2.1.1",
+        "semver": "^5.6.0"
+      },
+      "dependencies": {
+        "ms": {
+          "version": "2.1.2",
+          "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.2.tgz",
+          "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==",
+          "dev": true
+        },
+        "semver": {
+          "version": "5.7.1",
+          "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.1.tgz",
+          "integrity": "sha512-sauaDf/PZdVgrLTNYHRtpXa1iRiKcaebiKQ1BJdpQlWH2lCvexQdX55snPFyK7QzpudqbCI0qXFfOasHdyNDGQ==",
+          "dev": true
+        }
+      }
+    },
     "jsprim": {
       "version": "1.4.1",
       "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz",
@@ -5907,6 +6087,27 @@
         "verror": "1.10.0"
       }
     },
+    "jwa": {
+      "version": "1.4.1",
+      "resolved": "https://registry.npmjs.org/jwa/-/jwa-1.4.1.tgz",
+      "integrity": "sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA==",
+      "dev": true,
+      "requires": {
+        "buffer-equal-constant-time": "1.0.1",
+        "ecdsa-sig-formatter": "1.0.11",
+        "safe-buffer": "^5.0.1"
+      }
+    },
+    "jws": {
+      "version": "3.2.2",
+      "resolved": "https://registry.npmjs.org/jws/-/jws-3.2.2.tgz",
+      "integrity": "sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==",
+      "dev": true,
+      "requires": {
+        "jwa": "^1.4.1",
+        "safe-buffer": "^5.0.1"
+      }
+    },
     "kew": {
       "version": "0.7.0",
       "resolved": "https://registry.npmjs.org/kew/-/kew-0.7.0.tgz",
@@ -5931,6 +6132,30 @@
         "graceful-fs": "^4.1.9"
       }
     },
+    "ky": {
+      "version": "0.12.0",
+      "resolved": "https://registry.npmjs.org/ky/-/ky-0.12.0.tgz",
+      "integrity": "sha512-t9b7v3V2fGwAcQnnDDQwKQGF55eWrf4pwi1RN08Fy8b/9GEwV7Ea0xQiaSW6ZbeghBHIwl8kgnla4vVo9seepQ==",
+      "dev": true
+    },
+    "ky-universal": {
+      "version": "0.3.0",
+      "resolved": "https://registry.npmjs.org/ky-universal/-/ky-universal-0.3.0.tgz",
+      "integrity": "sha512-CM4Bgb2zZZpsprcjI6DNYTaH3oGHXL2u7BU4DK+lfCuC4snkt9/WRpMYeKbBbXscvKkeqBwzzjFX2WwmKY5K/A==",
+      "dev": true,
+      "requires": {
+        "abort-controller": "^3.0.0",
+        "node-fetch": "^2.6.0"
+      },
+      "dependencies": {
+        "node-fetch": {
+          "version": "2.6.0",
+          "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.0.tgz",
+          "integrity": "sha512-8dG4H5ujfvFiqDmVu9fQ5bOHUC15JMjMY/Zumv26oOvvVJjM67KF8koCWIabKQ1GJIa9r2mMZscBq/TbdOcmNA==",
+          "dev": true
+        }
+      }
+    },
     "labeled-stream-splicer": {
       "version": "2.0.1",
       "resolved": "https://registry.npmjs.org/labeled-stream-splicer/-/labeled-stream-splicer-2.0.1.tgz",
@@ -5979,74 +6204,6 @@
         }
       }
     },
-    "lcid": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz",
-      "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=",
-      "dev": true,
-      "requires": {
-        "invert-kv": "^1.0.0"
-      }
-    },
-    "less": {
-      "version": "3.0.4",
-      "resolved": "https://registry.npmjs.org/less/-/less-3.0.4.tgz",
-      "integrity": "sha512-q3SyEnPKbk9zh4l36PGeW2fgynKu+FpbhiUNx/yaiBUQ3V0CbACCgb9FzYWcRgI2DJlP6eI4jc8XPrCTi55YcQ==",
-      "dev": true,
-      "requires": {
-        "errno": "^0.1.1",
-        "graceful-fs": "^4.1.2",
-        "image-size": "~0.5.0",
-        "mime": "^1.4.1",
-        "mkdirp": "^0.5.0",
-        "promise": "^7.1.1",
-        "request": "^2.83.0",
-        "source-map": "~0.6.0"
-      },
-      "dependencies": {
-        "asap": {
-          "version": "2.0.6",
-          "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz",
-          "integrity": "sha1-5QNHYR1+aQlDIIu9r+vLwvuGbUY=",
-          "dev": true,
-          "optional": true
-        },
-        "promise": {
-          "version": "7.3.1",
-          "resolved": "https://registry.npmjs.org/promise/-/promise-7.3.1.tgz",
-          "integrity": "sha512-nolQXZ/4L+bP/UGlkfaIujX9BKxGwmQ9OT4mOt5yvy8iK1h3wqTEJCijzGANTCCl9nWjY41juyAn2K3Q1hLLTg==",
-          "dev": true,
-          "optional": true,
-          "requires": {
-            "asap": "~2.0.3"
-          }
-        },
-        "source-map": {
-          "version": "0.6.1",
-          "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz",
-          "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==",
-          "dev": true,
-          "optional": true
-        }
-      }
-    },
-    "less-middleware": {
-      "version": "3.0.1",
-      "resolved": "https://registry.npmjs.org/less-middleware/-/less-middleware-3.0.1.tgz",
-      "integrity": "sha512-FCG4zGd7c/lKMWGDzzkfU9Lcndfjc4TcSnuRwUtJ4E+NxPMuDGe7lJA1rOn+SI9x2lak+s4b6sQkcPa45eqKiw==",
-      "dev": true,
-      "requires": {
-        "less": "~3.0.4",
-        "mkdirp": "~0.5.1",
-        "node.extend": "~2.0.0"
-      }
-    },
-    "leven": {
-      "version": "2.1.0",
-      "resolved": "https://registry.npmjs.org/leven/-/leven-2.1.0.tgz",
-      "integrity": "sha1-wuep93IJTe6dNCAq6KzORoeHVYA=",
-      "dev": true
-    },
     "levn": {
       "version": "0.3.0",
       "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz",
@@ -6057,35 +6214,11 @@
         "type-check": "~0.3.2"
       }
     },
-    "load-json-file": {
-      "version": "1.1.0",
-      "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz",
-      "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=",
-      "dev": true,
-      "requires": {
-        "graceful-fs": "^4.1.2",
-        "parse-json": "^2.2.0",
-        "pify": "^2.0.0",
-        "pinkie-promise": "^2.0.0",
-        "strip-bom": "^2.0.0"
-      },
-      "dependencies": {
-        "pify": {
-          "version": "2.3.0",
-          "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
-          "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=",
-          "dev": true
-        },
-        "strip-bom": {
-          "version": "2.0.0",
-          "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz",
-          "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=",
-          "dev": true,
-          "requires": {
-            "is-utf8": "^0.2.0"
-          }
-        }
-      }
+    "li": {
+      "version": "1.3.0",
+      "resolved": "https://registry.npmjs.org/li/-/li-1.3.0.tgz",
+      "integrity": "sha1-IsWbyu+qmo7zWc91l4TkvxBq6hs=",
+      "dev": true
     },
     "loader-utils": {
       "version": "0.2.17",
@@ -6099,24 +6232,6 @@
         "object-assign": "^4.0.1"
       }
     },
-    "locate-path": {
-      "version": "2.0.0",
-      "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz",
-      "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=",
-      "dev": true,
-      "requires": {
-        "p-locate": "^2.0.0",
-        "path-exists": "^3.0.0"
-      },
-      "dependencies": {
-        "path-exists": {
-          "version": "3.0.0",
-          "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz",
-          "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=",
-          "dev": true
-        }
-      }
-    },
     "lodash": {
       "version": "4.17.10",
       "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.10.tgz",
@@ -6141,20 +6256,53 @@
       "integrity": "sha1-ywcE1Hq3F4n/oN6Ll92Sb7iLE7E=",
       "dev": true
     },
+    "lodash.get": {
+      "version": "4.4.2",
+      "resolved": "https://registry.npmjs.org/lodash.get/-/lodash.get-4.4.2.tgz",
+      "integrity": "sha1-LRd/ZS+jHpObRDjVNBSZ36OCXpk=",
+      "dev": true
+    },
     "lodash.includes": {
       "version": "4.3.0",
       "resolved": "https://registry.npmjs.org/lodash.includes/-/lodash.includes-4.3.0.tgz",
       "integrity": "sha1-YLuYqHy5I8aMoeUTJUgzFISfVT8=",
       "dev": true
     },
+    "lodash.isboolean": {
+      "version": "3.0.3",
+      "resolved": "https://registry.npmjs.org/lodash.isboolean/-/lodash.isboolean-3.0.3.tgz",
+      "integrity": "sha1-bC4XHbKiV82WgC/UOwGyDV9YcPY=",
+      "dev": true
+    },
+    "lodash.isinteger": {
+      "version": "4.0.4",
+      "resolved": "https://registry.npmjs.org/lodash.isinteger/-/lodash.isinteger-4.0.4.tgz",
+      "integrity": "sha1-YZwK89A/iwTDH1iChAt3sRzWg0M=",
+      "dev": true
+    },
+    "lodash.isnumber": {
+      "version": "3.0.3",
+      "resolved": "https://registry.npmjs.org/lodash.isnumber/-/lodash.isnumber-3.0.3.tgz",
+      "integrity": "sha1-POdoEMWSjQM1IwGsKHMX8RwLH/w=",
+      "dev": true
+    },
     "lodash.isobject": {
-      "version": "2.4.1",
-      "resolved": "https://registry.npmjs.org/lodash.isobject/-/lodash.isobject-2.4.1.tgz",
-      "integrity": "sha1-Wi5H/mmVPx7mMafrof5k0tBlWPU=",
-      "dev": true,
-      "requires": {
-        "lodash._objecttypes": "~2.4.1"
-      }
+      "version": "3.0.2",
+      "resolved": "https://registry.npmjs.org/lodash.isobject/-/lodash.isobject-3.0.2.tgz",
+      "integrity": "sha1-PI+41bW/S/kK4G4U8qUwpO2TXh0=",
+      "dev": true
+    },
+    "lodash.isplainobject": {
+      "version": "4.0.6",
+      "resolved": "https://registry.npmjs.org/lodash.isplainobject/-/lodash.isplainobject-4.0.6.tgz",
+      "integrity": "sha1-fFJqUtibRcRcxpC4gWO+BJf1UMs=",
+      "dev": true
+    },
+    "lodash.isstring": {
+      "version": "4.0.1",
+      "resolved": "https://registry.npmjs.org/lodash.isstring/-/lodash.isstring-4.0.1.tgz",
+      "integrity": "sha1-1SfftUVuynzJu5XV2ur4i6VKVFE=",
+      "dev": true
     },
     "lodash.keys": {
       "version": "4.2.0",
@@ -6162,12 +6310,36 @@
       "integrity": "sha1-oIYCrBLk+4P5H8H7ejYKTZujUgU=",
       "dev": true
     },
+    "lodash.mapvalues": {
+      "version": "4.6.0",
+      "resolved": "https://registry.npmjs.org/lodash.mapvalues/-/lodash.mapvalues-4.6.0.tgz",
+      "integrity": "sha1-G6+lAF3p3W9PJmaMMMo3IwzJaJw=",
+      "dev": true
+    },
     "lodash.memoize": {
       "version": "4.1.2",
       "resolved": "https://registry.npmjs.org/lodash.memoize/-/lodash.memoize-4.1.2.tgz",
       "integrity": "sha1-vMbEmkKihA7Zl/Mj6tpezRguC/4=",
       "dev": true
     },
+    "lodash.once": {
+      "version": "4.1.1",
+      "resolved": "https://registry.npmjs.org/lodash.once/-/lodash.once-4.1.1.tgz",
+      "integrity": "sha1-DdOXEhPHxW34gJd9UEyI+0cal6w=",
+      "dev": true
+    },
+    "lodash.set": {
+      "version": "4.3.2",
+      "resolved": "https://registry.npmjs.org/lodash.set/-/lodash.set-4.3.2.tgz",
+      "integrity": "sha1-2HV7HagH3eJIFrDWqEvqGnYjCyM=",
+      "dev": true
+    },
+    "lodash.sortby": {
+      "version": "4.7.0",
+      "resolved": "https://registry.npmjs.org/lodash.sortby/-/lodash.sortby-4.7.0.tgz",
+      "integrity": "sha1-7dFMgk4sycHgsKG0K7UhBRakJDg=",
+      "dev": true
+    },
     "lodash.uniq": {
       "version": "4.5.0",
       "resolved": "https://registry.npmjs.org/lodash.uniq/-/lodash.uniq-4.5.0.tgz",
@@ -6618,6 +6790,12 @@
         }
       }
     },
+    "macos-release": {
+      "version": "2.3.0",
+      "resolved": "https://registry.npmjs.org/macos-release/-/macos-release-2.3.0.tgz",
+      "integrity": "sha512-OHhSbtcviqMPt7yfw5ef5aghS2jzFVKEFyCJndQt2YpSQ9qRVSEv2axSJI1paVThEu+FFGs584h/1YhxjVqajA==",
+      "dev": true
+    },
     "magic-string": {
       "version": "0.16.0",
       "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.16.0.tgz",
@@ -6627,15 +6805,6 @@
         "vlq": "^0.2.1"
       }
     },
-    "makeerror": {
-      "version": "1.0.11",
-      "resolved": "https://registry.npmjs.org/makeerror/-/makeerror-1.0.11.tgz",
-      "integrity": "sha1-4BpckQnyr3lmDk6LlYd5AYT1qWw=",
-      "dev": true,
-      "requires": {
-        "tmpl": "1.0.x"
-      }
-    },
     "map-cache": {
       "version": "0.2.2",
       "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz",
@@ -6674,14 +6843,11 @@
         "is-buffer": "~1.1.1"
       }
     },
-    "mem": {
-      "version": "1.1.0",
-      "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz",
-      "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=",
-      "dev": true,
-      "requires": {
-        "mimic-fn": "^1.0.0"
-      }
+    "memfs-or-file-map-to-github-branch": {
+      "version": "1.1.2",
+      "resolved": "https://registry.npmjs.org/memfs-or-file-map-to-github-branch/-/memfs-or-file-map-to-github-branch-1.1.2.tgz",
+      "integrity": "sha512-D2JKK2DTuVYQqquBWco3K6UfSVyVwmd58dgNqh+TgxHOZdTmR8I130gjMbVCkemDl/EzqDA62417cJxKL3/FFA==",
+      "dev": true
     },
     "memory-fs": {
       "version": "0.3.0",
@@ -6725,12 +6891,6 @@
         }
       }
     },
-    "merge": {
-      "version": "1.2.0",
-      "resolved": "https://registry.npmjs.org/merge/-/merge-1.2.0.tgz",
-      "integrity": "sha1-dTHjnUlJwoGma4xabgJl6LBYlNo=",
-      "dev": true
-    },
     "micromatch": {
       "version": "2.3.11",
       "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz",
@@ -6798,9 +6958,9 @@
       "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0="
     },
     "mixin-deep": {
-      "version": "1.3.1",
-      "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz",
-      "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==",
+      "version": "1.3.2",
+      "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.2.tgz",
+      "integrity": "sha512-WRoDn//mXBiJ1H40rqa3vH0toePwSsGb45iInWlTySa+Uu4k3tYUSxa2v1KqAiLtvlrSzaExqS1gtk96A9zvEA==",
       "dev": true,
       "requires": {
         "for-in": "^1.0.2",
@@ -6815,6 +6975,21 @@
           "requires": {
             "is-plain-object": "^2.0.4"
           }
+        },
+        "is-plain-object": {
+          "version": "2.0.4",
+          "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz",
+          "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==",
+          "dev": true,
+          "requires": {
+            "isobject": "^3.0.1"
+          }
+        },
+        "isobject": {
+          "version": "3.0.1",
+          "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz",
+          "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=",
+          "dev": true
         }
       }
     },
@@ -7022,9 +7197,9 @@
       "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g="
     },
     "mute-stream": {
-      "version": "0.0.5",
-      "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.5.tgz",
-      "integrity": "sha1-j7+rsKmKJT0xhDMfno3rc3L6xsA=",
+      "version": "0.0.7",
+      "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz",
+      "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=",
       "dev": true
     },
     "nan": {
@@ -7091,10 +7266,16 @@
       "integrity": "sha1-a+lPysqNd63gqWcNxGCRTJRHJEQ=",
       "dev": true
     },
-    "next-tick": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/next-tick/-/next-tick-1.0.0.tgz",
-      "integrity": "sha1-yobR/ogoFpsBICCOPchCS524NCw=",
+    "nice-try": {
+      "version": "1.0.5",
+      "resolved": "https://registry.npmjs.org/nice-try/-/nice-try-1.0.5.tgz",
+      "integrity": "sha512-1nh45deeb5olNY7eX82BkPO7SSxR5SSYJiPTrTdFUVYwAl8CKMA5N9PjTYkHiRjisVcxcQ1HXdLhx2qxxJzLNQ==",
+      "dev": true
+    },
+    "node-cleanup": {
+      "version": "2.1.2",
+      "resolved": "https://registry.npmjs.org/node-cleanup/-/node-cleanup-2.1.2.tgz",
+      "integrity": "sha1-esGavSl+Caf3KnFUXZUbUX5N3iw=",
       "dev": true
     },
     "node-fetch": {
@@ -7107,12 +7288,6 @@
         "is-stream": "^1.0.1"
       }
     },
-    "node-int64": {
-      "version": "0.4.0",
-      "resolved": "https://registry.npmjs.org/node-int64/-/node-int64-0.4.0.tgz",
-      "integrity": "sha1-h6kGXNs1XTGC2PlM4RGIuCXGijs=",
-      "dev": true
-    },
     "node-libs-browser": {
       "version": "0.7.0",
       "resolved": "https://registry.npmjs.org/node-libs-browser/-/node-libs-browser-0.7.0.tgz",
@@ -7178,15 +7353,6 @@
         }
       }
     },
-    "node.extend": {
-      "version": "2.0.0",
-      "resolved": "https://registry.npmjs.org/node.extend/-/node.extend-2.0.0.tgz",
-      "integrity": "sha1-dSWih1Z36lNHhKXhCseJVhOWFN8=",
-      "dev": true,
-      "requires": {
-        "is": "^3.2.1"
-      }
-    },
     "nopt": {
       "version": "3.0.6",
       "resolved": "https://registry.npmjs.org/nopt/-/nopt-3.0.6.tgz",
@@ -7196,18 +7362,6 @@
         "abbrev": "1"
       }
     },
-    "normalize-package-data": {
-      "version": "2.4.0",
-      "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.4.0.tgz",
-      "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==",
-      "dev": true,
-      "requires": {
-        "hosted-git-info": "^2.1.4",
-        "is-builtin-module": "^1.0.0",
-        "semver": "2 || 3 || 4 || 5",
-        "validate-npm-package-license": "^3.0.1"
-      }
-    },
     "normalize-path": {
       "version": "2.1.1",
       "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz",
@@ -7256,12 +7410,6 @@
       "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=",
       "dev": true
     },
-    "nwmatcher": {
-      "version": "1.4.4",
-      "resolved": "https://registry.npmjs.org/nwmatcher/-/nwmatcher-1.4.4.tgz",
-      "integrity": "sha512-3iuY4N5dhgMpCUrOVnuAdGrgxVqV2cJpM+XNccjR2DKOB1RUP0aA+wGXEiNziG/UKboFyGBIoKOaNlJxx8bciQ==",
-      "dev": true
-    },
     "oauth-sign": {
       "version": "0.8.2",
       "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz",
@@ -7339,6 +7487,12 @@
         }
       }
     },
+    "octokit-pagination-methods": {
+      "version": "1.1.0",
+      "resolved": "https://registry.npmjs.org/octokit-pagination-methods/-/octokit-pagination-methods-1.1.0.tgz",
+      "integrity": "sha512-fZ4qZdQ2nxJvtcasX7Ghl+WlWS/d9IgnBIwFZXVNNZUmzpno91SX5bc5vuxiuKoCtK78XxGGNuSCrDC7xYB3OQ==",
+      "dev": true
+    },
     "once": {
       "version": "1.4.0",
       "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz",
@@ -7349,10 +7503,13 @@
       }
     },
     "onetime": {
-      "version": "1.1.0",
-      "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz",
-      "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=",
-      "dev": true
+      "version": "2.0.1",
+      "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz",
+      "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=",
+      "dev": true,
+      "requires": {
+        "mimic-fn": "^1.0.0"
+      }
     },
     "opener": {
       "version": "1.4.3",
@@ -7413,13 +7570,14 @@
       "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=",
       "dev": true
     },
-    "os-locale": {
-      "version": "1.4.0",
-      "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz",
-      "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=",
+    "os-name": {
+      "version": "3.1.0",
+      "resolved": "https://registry.npmjs.org/os-name/-/os-name-3.1.0.tgz",
+      "integrity": "sha512-h8L+8aNjNcMpo/mAIBPn5PXCM16iyPGjHNWo6U1YO8sJTMHtEtyczI6QJnLoplswm6goopQkqc7OAnjhWcugVg==",
       "dev": true,
       "requires": {
-        "lcid": "^1.0.0"
+        "macos-release": "^2.2.0",
+        "windows-release": "^3.1.0"
       }
     },
     "os-tmpdir": {
@@ -7428,6 +7586,12 @@
       "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=",
       "dev": true
     },
+    "override-require": {
+      "version": "1.1.1",
+      "resolved": "https://registry.npmjs.org/override-require/-/override-require-1.1.1.tgz",
+      "integrity": "sha1-auIvresfhQ/7DPTCD/e4fl62UN8=",
+      "dev": true
+    },
     "p-finally": {
       "version": "1.0.0",
       "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz",
@@ -7435,21 +7599,12 @@
       "dev": true
     },
     "p-limit": {
-      "version": "1.3.0",
-      "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz",
-      "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==",
+      "version": "2.2.1",
+      "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-2.2.1.tgz",
+      "integrity": "sha512-85Tk+90UCVWvbDavCLKPOLC9vvY8OwEX/RtKF+/1OADJMVlFfEHOiMTPVyxg7mk/dKa+ipdHm0OUkTvCpMTuwg==",
       "dev": true,
       "requires": {
-        "p-try": "^1.0.0"
-      }
-    },
-    "p-locate": {
-      "version": "2.0.0",
-      "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz",
-      "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=",
-      "dev": true,
-      "requires": {
-        "p-limit": "^1.1.0"
+        "p-try": "^2.0.0"
       }
     },
     "p-map": {
@@ -7459,9 +7614,9 @@
       "dev": true
     },
     "p-try": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz",
-      "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=",
+      "version": "2.2.0",
+      "resolved": "https://registry.npmjs.org/p-try/-/p-try-2.2.0.tgz",
+      "integrity": "sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==",
       "dev": true
     },
     "pako": {
@@ -7484,6 +7639,23 @@
       "integrity": "sha512-YYQzII66NqysdPgDVxzbdwNXMv5Ww562JSZSXZ4RIPoolzD7yqA4crgD8swrs+JNcvjoZMKMiT4kGcLYvf6IoA==",
       "dev": true
     },
+    "parse-git-config": {
+      "version": "2.0.3",
+      "resolved": "https://registry.npmjs.org/parse-git-config/-/parse-git-config-2.0.3.tgz",
+      "integrity": "sha512-Js7ueMZOVSZ3tP8C7E3KZiHv6QQl7lnJ+OkbxoaFazzSa2KyEHqApfGbU3XboUgUnq4ZuUmskUpYKTNx01fm5A==",
+      "dev": true,
+      "requires": {
+        "expand-tilde": "^2.0.2",
+        "git-config-path": "^1.0.1",
+        "ini": "^1.3.5"
+      }
+    },
+    "parse-github-url": {
+      "version": "1.0.2",
+      "resolved": "https://registry.npmjs.org/parse-github-url/-/parse-github-url-1.0.2.tgz",
+      "integrity": "sha512-kgBf6avCbO3Cn6+RnzRGLkUsv4ZVqv/VfAYkRsyBcgkshNvVBkRn1FEZcW0Jb+npXQWm2vHPnnOqFteZxRRGNw==",
+      "dev": true
+    },
     "parse-glob": {
       "version": "3.0.4",
       "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz",
@@ -7505,16 +7677,25 @@
         "error-ex": "^1.2.0"
       }
     },
+    "parse-link-header": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/parse-link-header/-/parse-link-header-1.0.1.tgz",
+      "integrity": "sha1-vt/g0hGK64S+deewJUGeyKYRQKc=",
+      "dev": true,
+      "requires": {
+        "xtend": "~4.0.1"
+      }
+    },
     "parse-ms": {
       "version": "1.0.1",
       "resolved": "https://registry.npmjs.org/parse-ms/-/parse-ms-1.0.1.tgz",
       "integrity": "sha1-VjRtR0nXjyNDDKDHE4UK75GqNh0=",
       "dev": true
     },
-    "parse5": {
-      "version": "1.5.1",
-      "resolved": "https://registry.npmjs.org/parse5/-/parse5-1.5.1.tgz",
-      "integrity": "sha1-m387DeMr543CQBsXVzzK8Pb1nZQ=",
+    "parse-passwd": {
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz",
+      "integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=",
       "dev": true
     },
     "pascalcase": {
@@ -7577,25 +7758,6 @@
         "isarray": "0.0.1"
       }
     },
-    "path-type": {
-      "version": "1.1.0",
-      "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz",
-      "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=",
-      "dev": true,
-      "requires": {
-        "graceful-fs": "^4.1.2",
-        "pify": "^2.0.0",
-        "pinkie-promise": "^2.0.0"
-      },
-      "dependencies": {
-        "pify": {
-          "version": "2.3.0",
-          "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz",
-          "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=",
-          "dev": true
-        }
-      }
-    },
     "pathval": {
       "version": "1.1.0",
       "resolved": "https://registry.npmjs.org/pathval/-/pathval-1.1.0.tgz",
@@ -7670,6 +7832,12 @@
         "pinkie": "^2.0.0"
       }
     },
+    "pinpoint": {
+      "version": "1.1.0",
+      "resolved": "https://registry.npmjs.org/pinpoint/-/pinpoint-1.1.0.tgz",
+      "integrity": "sha1-DPd1eml38b9/ajIge3CeN3OI6HQ=",
+      "dev": true
+    },
     "pkg-dir": {
       "version": "1.0.0",
       "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-1.0.0.tgz",
@@ -7735,9 +7903,9 @@
       }
     },
     "pluralize": {
-      "version": "1.2.1",
-      "resolved": "https://registry.npmjs.org/pluralize/-/pluralize-1.2.1.tgz",
-      "integrity": "sha1-0aIUg/0iu0HlihL6NCGCMUCJfEU=",
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/pluralize/-/pluralize-7.0.0.tgz",
+      "integrity": "sha512-ARhBOdzS3e41FbkW/XWrTEtukqqLoK5+Z/4UeDaLuSW+39JPeFgs4gCGqsrJHVZX0fUrx//4OF0K1CUGwlIFow==",
       "dev": true
     },
     "pngjs": {
@@ -8391,26 +8559,6 @@
       "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=",
       "dev": true
     },
-    "pretty-format": {
-      "version": "19.0.0",
-      "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-19.0.0.tgz",
-      "integrity": "sha1-VlMNMqy5ij+khRxOK503tCBoTIQ=",
-      "dev": true,
-      "requires": {
-        "ansi-styles": "^3.0.0"
-      },
-      "dependencies": {
-        "ansi-styles": {
-          "version": "3.2.1",
-          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
-          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
-          "dev": true,
-          "requires": {
-            "color-convert": "^1.9.0"
-          }
-        }
-      }
-    },
     "pretty-ms": {
       "version": "3.0.1",
       "resolved": "https://registry.npmjs.org/pretty-ms/-/pretty-ms-3.0.1.tgz",
@@ -8421,6 +8569,24 @@
         "plur": "^2.1.2"
       }
     },
+    "prettyjson": {
+      "version": "1.2.1",
+      "resolved": "https://registry.npmjs.org/prettyjson/-/prettyjson-1.2.1.tgz",
+      "integrity": "sha1-/P+rQdGcq0365eV15kJGYZsS0ok=",
+      "dev": true,
+      "requires": {
+        "colors": "^1.1.2",
+        "minimist": "^1.2.0"
+      },
+      "dependencies": {
+        "minimist": {
+          "version": "1.2.0",
+          "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz",
+          "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=",
+          "dev": true
+        }
+      }
+    },
     "printf": {
       "version": "0.2.5",
       "resolved": "https://registry.npmjs.org/printf/-/printf-0.2.5.tgz",
@@ -8477,6 +8643,16 @@
       "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=",
       "dev": true
     },
+    "pump": {
+      "version": "3.0.0",
+      "resolved": "https://registry.npmjs.org/pump/-/pump-3.0.0.tgz",
+      "integrity": "sha512-LwZy+p3SFs1Pytd/jYct4wpv49HiYCqd9Rlc5ZVdk0V+8Yzv6jR5Blk3TRmPL1ft69TxP0IMZGJ+WPFU2BFhww==",
+      "dev": true,
+      "requires": {
+        "end-of-stream": "^1.1.0",
+        "once": "^1.3.1"
+      }
+    },
     "punycode": {
       "version": "1.4.1",
       "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz",
@@ -8540,12 +8716,6 @@
         }
       }
     },
-    "range-parser": {
-      "version": "0.0.4",
-      "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-0.0.4.tgz",
-      "integrity": "sha1-wEJ//vUcEKy6B4KkbJYC50T/Ygs=",
-      "dev": true
-    },
     "rax": {
       "version": "0.4.20",
       "resolved": "https://registry.npmjs.org/rax/-/rax-0.4.20.tgz",
@@ -8558,6 +8728,26 @@
         "universal-env": "^0.4.20"
       }
     },
+    "rc": {
+      "version": "1.2.8",
+      "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz",
+      "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==",
+      "dev": true,
+      "requires": {
+        "deep-extend": "^0.6.0",
+        "ini": "~1.3.0",
+        "minimist": "^1.2.0",
+        "strip-json-comments": "~2.0.1"
+      },
+      "dependencies": {
+        "minimist": {
+          "version": "1.2.0",
+          "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz",
+          "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=",
+          "dev": true
+        }
+      }
+    },
     "read-only-stream": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/read-only-stream/-/read-only-stream-2.0.0.tgz",
@@ -8599,27 +8789,6 @@
         }
       }
     },
-    "read-pkg": {
-      "version": "1.1.0",
-      "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz",
-      "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=",
-      "dev": true,
-      "requires": {
-        "load-json-file": "^1.0.0",
-        "normalize-package-data": "^2.3.2",
-        "path-type": "^1.0.0"
-      }
-    },
-    "read-pkg-up": {
-      "version": "1.0.1",
-      "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz",
-      "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=",
-      "dev": true,
-      "requires": {
-        "find-up": "^1.0.0",
-        "read-pkg": "^1.0.0"
-      }
-    },
     "readable-stream": {
       "version": "1.1.14",
       "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-1.1.14.tgz",
@@ -8675,16 +8844,11 @@
         }
       }
     },
-    "readline2": {
-      "version": "1.0.1",
-      "resolved": "https://registry.npmjs.org/readline2/-/readline2-1.0.1.tgz",
-      "integrity": "sha1-QQWWCP/BVHV7cV2ZidGZ/783LjU=",
-      "dev": true,
-      "requires": {
-        "code-point-at": "^1.0.0",
-        "is-fullwidth-code-point": "^1.0.0",
-        "mute-stream": "0.0.5"
-      }
+    "readline-sync": {
+      "version": "1.4.10",
+      "resolved": "https://registry.npmjs.org/readline-sync/-/readline-sync-1.4.10.tgz",
+      "integrity": "sha512-gNva8/6UAe8QYepIQH/jQ2qn91Qj0B9sYjMBBs3QOB8F2CXcKgLxQaJRP76sWVRQt+QU+8fAkCbCvjjMFu7Ycw==",
+      "dev": true
     },
     "rechoir": {
       "version": "0.6.2",
@@ -8790,6 +8954,25 @@
         "regjsparser": "^0.1.4"
       }
     },
+    "registry-auth-token": {
+      "version": "3.3.2",
+      "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.3.2.tgz",
+      "integrity": "sha512-JL39c60XlzCVgNrO+qq68FoNb56w/m7JYvGR2jT5iR1xBrUA3Mfx5Twk5rqTThPmQKMWydGmq8oFtDlxfrmxnQ==",
+      "dev": true,
+      "requires": {
+        "rc": "^1.1.6",
+        "safe-buffer": "^5.0.1"
+      }
+    },
+    "registry-url": {
+      "version": "3.1.0",
+      "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-3.1.0.tgz",
+      "integrity": "sha1-PU74cPc93h138M+aOBQyRE4XSUI=",
+      "dev": true,
+      "requires": {
+        "rc": "^1.0.1"
+      }
+    },
     "regjsgen": {
       "version": "0.2.0",
       "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.2.0.tgz",
@@ -8976,24 +9159,12 @@
         "throttleit": "^1.0.0"
       }
     },
-    "require-directory": {
-      "version": "2.1.1",
-      "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz",
-      "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=",
-      "dev": true
-    },
     "require-from-string": {
       "version": "1.2.1",
       "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-1.2.1.tgz",
       "integrity": "sha1-UpyczvJzgK3+yaL5ZbZJu+5jZBg=",
       "dev": true
     },
-    "require-main-filename": {
-      "version": "1.0.1",
-      "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz",
-      "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=",
-      "dev": true
-    },
     "require-uncached": {
       "version": "1.0.3",
       "resolved": "https://registry.npmjs.org/require-uncached/-/require-uncached-1.0.3.tgz",
@@ -9038,13 +9209,13 @@
       "dev": true
     },
     "restore-cursor": {
-      "version": "1.0.1",
-      "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz",
-      "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=",
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz",
+      "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=",
       "dev": true,
       "requires": {
-        "exit-hook": "^1.0.0",
-        "onetime": "^1.0.0"
+        "onetime": "^2.0.0",
+        "signal-exit": "^3.0.2"
       }
     },
     "ret": {
@@ -9053,10 +9224,16 @@
       "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==",
       "dev": true
     },
+    "retry": {
+      "version": "0.12.0",
+      "resolved": "https://registry.npmjs.org/retry/-/retry-0.12.0.tgz",
+      "integrity": "sha1-G0KmJmoh8HQh0bC1S33BZ7AcATs=",
+      "dev": true
+    },
     "rfc6902": {
-      "version": "1.3.0",
-      "resolved": "https://registry.npmjs.org/rfc6902/-/rfc6902-1.3.0.tgz",
-      "integrity": "sha1-hbLGnELc8RYIJDe5gpqWJEa0xKU=",
+      "version": "3.0.4",
+      "resolved": "https://registry.npmjs.org/rfc6902/-/rfc6902-3.0.4.tgz",
+      "integrity": "sha512-OnzreaZXrwT5w2ikKXWr5QcuI7NZpL+J3hIkAwozjOnKVUL7fPsB8Vcmu8YBiiou1/r3V0Jc0T1uQDyfAPvLzA==",
       "dev": true
     },
     "right-align": {
@@ -9558,12 +9735,12 @@
       }
     },
     "run-async": {
-      "version": "0.1.0",
-      "resolved": "https://registry.npmjs.org/run-async/-/run-async-0.1.0.tgz",
-      "integrity": "sha1-yK1KXhEGYeQCp9IbUw4AnyX444k=",
+      "version": "2.3.0",
+      "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz",
+      "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=",
       "dev": true,
       "requires": {
-        "once": "^1.3.0"
+        "is-promise": "^2.1.0"
       }
     },
     "runtime-shared": {
@@ -9611,47 +9788,6 @@
       "integrity": "sha512-1HwIYD/8UlOtFS3QO3w7ey+SdSDFE4HRNLZoZRYVQefrOY3l17epswImeB1ijgJFQJodIaHcwkp3r/myBjFVbg==",
       "dev": true
     },
-    "sane": {
-      "version": "1.5.0",
-      "resolved": "https://registry.npmjs.org/sane/-/sane-1.5.0.tgz",
-      "integrity": "sha1-pK3q52TQSGIeyyfV+ez1ExAZOfM=",
-      "dev": true,
-      "requires": {
-        "anymatch": "^1.3.0",
-        "exec-sh": "^0.2.0",
-        "fb-watchman": "^1.8.0",
-        "minimatch": "^3.0.2",
-        "minimist": "^1.1.1",
-        "walker": "~1.0.5",
-        "watch": "~0.10.0"
-      },
-      "dependencies": {
-        "bser": {
-          "version": "1.0.2",
-          "resolved": "https://registry.npmjs.org/bser/-/bser-1.0.2.tgz",
-          "integrity": "sha1-OBEWlwsqbe6lZG3RXdcnhES1YWk=",
-          "dev": true,
-          "requires": {
-            "node-int64": "^0.4.0"
-          }
-        },
-        "fb-watchman": {
-          "version": "1.9.2",
-          "resolved": "https://registry.npmjs.org/fb-watchman/-/fb-watchman-1.9.2.tgz",
-          "integrity": "sha1-okz0eCf4LTj7Waaa1wt247auc4M=",
-          "dev": true,
-          "requires": {
-            "bser": "1.0.2"
-          }
-        },
-        "minimist": {
-          "version": "1.2.0",
-          "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz",
-          "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=",
-          "dev": true
-        }
-      }
-    },
     "sax": {
       "version": "1.2.4",
       "resolved": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz",
@@ -9669,53 +9805,104 @@
       "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.0.tgz",
       "integrity": "sha512-4SJ3dm0WAwWy/NVeioZh5AntkdJoWKxHxcmyP622fOkgHa4z3R0TdBJICINyaSDE6uNwVc8gZr+ZinwZAH4xIA=="
     },
-    "send": {
-      "version": "0.0.3",
-      "resolved": "https://registry.npmjs.org/send/-/send-0.0.3.tgz",
-      "integrity": "sha1-TV+EPt+dZdrDHIpdJnLBeey2cYQ=",
+    "serve": {
+      "version": "7.1.3",
+      "resolved": "https://registry.npmjs.org/serve/-/serve-7.1.3.tgz",
+      "integrity": "sha512-XNDcJbtFWn6dc6U46/kq6LkXFuk33MqA+FZZdWJ/Y4ttEV1P7oD+mVNcKS9DYuXQEnKgqLH36Qv88mSvLxQPcw==",
       "dev": true,
       "requires": {
-        "debug": "*",
-        "fresh": "0.1.0",
-        "mime": "1.2.6",
-        "range-parser": "0.0.4"
+        "@zeit/schemas": "1.1.2",
+        "ajv": "6.5.0",
+        "arg": "2.0.0",
+        "chalk": "2.4.1",
+        "serve-handler": "2.3.15",
+        "update-check": "1.5.2"
+      },
+      "dependencies": {
+        "ajv": {
+          "version": "6.5.0",
+          "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.5.0.tgz",
+          "integrity": "sha512-VDUX1oSajablmiyFyED9L1DFndg0P9h7p1F+NO8FkIzei6EPrR6Zu1n18rd5P8PqaSRd/FrWv3G1TVBqpM83gA==",
+          "dev": true,
+          "requires": {
+            "fast-deep-equal": "^2.0.1",
+            "fast-json-stable-stringify": "^2.0.0",
+            "json-schema-traverse": "^0.3.0",
+            "uri-js": "^4.2.1"
+          }
+        },
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
+          "dev": true,
+          "requires": {
+            "color-convert": "^1.9.0"
+          }
+        },
+        "chalk": {
+          "version": "2.4.1",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.1.tgz",
+          "integrity": "sha512-ObN6h1v2fTJSmUXoS3nMQ92LbDK9be4TV+6G+omQlGJFdcUX5heKi1LZ1YnRMIgwTLEj3E24bT6tYni50rlCfQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "fast-deep-equal": {
+          "version": "2.0.1",
+          "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz",
+          "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=",
+          "dev": true
+        },
+        "has-flag": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+          "dev": true
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          }
+        }
+      }
+    },
+    "serve-handler": {
+      "version": "2.3.15",
+      "resolved": "https://registry.npmjs.org/serve-handler/-/serve-handler-2.3.15.tgz",
+      "integrity": "sha512-GBJtA2DPAJzo+6bdYeXdM7Wwt676kh1s64yi9k+jxlNTbezC7MZJa3csInGOG9VRFKr9r3+xZwyCLNcd8my33Q==",
+      "dev": true,
+      "requires": {
+        "bytes": "3.0.0",
+        "fast-url-parser": "1.1.3",
+        "glob-slasher": "1.0.1",
+        "mime": "2.3.1",
+        "minimatch": "3.0.4",
+        "path-is-inside": "1.0.2",
+        "path-to-regexp": "2.2.1"
       },
       "dependencies": {
         "mime": {
-          "version": "1.2.6",
-          "resolved": "https://registry.npmjs.org/mime/-/mime-1.2.6.tgz",
-          "integrity": "sha1-sfhsdowCX6h7SAdfFwnyiuryA2U=",
+          "version": "2.3.1",
+          "resolved": "https://registry.npmjs.org/mime/-/mime-2.3.1.tgz",
+          "integrity": "sha512-OEUllcVoydBHGN1z84yfQDimn58pZNNNXgZlHXSboxMlFvgI6MXSWpWKpFRra7H1HxpVhHTkrghfRW49k6yjeg==",
+          "dev": true
+        },
+        "path-to-regexp": {
+          "version": "2.2.1",
+          "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-2.2.1.tgz",
+          "integrity": "sha512-gu9bD6Ta5bwGrrU8muHzVOBFFREpp2iRkVfhBJahwJ6p6Xw20SjT0MxLnwkjOibQmGSYhiUnf2FLe7k+jcFmGQ==",
           "dev": true
         }
       }
     },
-    "serve": {
-      "version": "1.4.0",
-      "resolved": "https://registry.npmjs.org/serve/-/serve-1.4.0.tgz",
-      "integrity": "sha1-41885rQlhrfz3te1sKMaAbsOEAU=",
-      "dev": true,
-      "requires": {
-        "commander": "0.6.1",
-        "connect": "2.3.x",
-        "jade": "*",
-        "less-middleware": "*",
-        "stylus": "*"
-      },
-      "dependencies": {
-        "commander": {
-          "version": "0.6.1",
-          "resolved": "https://registry.npmjs.org/commander/-/commander-0.6.1.tgz",
-          "integrity": "sha1-+mihT2qUXVTbvlDYzbMyDp47GgY=",
-          "dev": true
-        }
-      }
-    },
-    "set-blocking": {
-      "version": "2.0.0",
-      "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz",
-      "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=",
-      "dev": true
-    },
     "set-immediate-shim": {
       "version": "1.0.1",
       "resolved": "https://registry.npmjs.org/set-immediate-shim/-/set-immediate-shim-1.0.1.tgz",
@@ -9723,9 +9910,9 @@
       "dev": true
     },
     "set-value": {
-      "version": "2.0.0",
-      "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz",
-      "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==",
+      "version": "2.0.1",
+      "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.1.tgz",
+      "integrity": "sha512-JxHc1weCN68wRY0fhCoXpyK55m/XPHafOmK4UWD7m2CI14GMcFypt4w/0+NV5f/ZMby2F6S2wwA7fgynh9gWSw==",
       "dev": true,
       "requires": {
         "extend-shallow": "^2.0.1",
@@ -9742,6 +9929,21 @@
           "requires": {
             "is-extendable": "^0.1.0"
           }
+        },
+        "is-plain-object": {
+          "version": "2.0.4",
+          "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz",
+          "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==",
+          "dev": true,
+          "requires": {
+            "isobject": "^3.0.1"
+          }
+        },
+        "isobject": {
+          "version": "3.0.1",
+          "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz",
+          "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=",
+          "dev": true
         }
       }
     },
@@ -9897,10 +10099,13 @@
       "dev": true
     },
     "slice-ansi": {
-      "version": "0.0.4",
-      "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-0.0.4.tgz",
-      "integrity": "sha1-7b+JA/ZvfOL46v1s7tZeJkyDGzU=",
-      "dev": true
+      "version": "1.0.0",
+      "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-1.0.0.tgz",
+      "integrity": "sha512-POqxBK6Lb3q6s047D/XsDVNPnF9Dl8JSaqe9h9lURl0OdNqy/ujDrOiIHtsqXMGbWWTIomRzAMaTyawAU//Reg==",
+      "dev": true,
+      "requires": {
+        "is-fullwidth-code-point": "^2.0.0"
+      }
     },
     "snapdragon": {
       "version": "0.8.2",
@@ -10068,36 +10273,10 @@
       "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=",
       "dev": true
     },
-    "spdx-correct": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.0.0.tgz",
-      "integrity": "sha512-N19o9z5cEyc8yQQPukRCZ9EUmb4HUpnrmaL/fxS2pBo2jbfcFRVuFZ/oFC+vZz0MNNk0h80iMn5/S6qGZOL5+g==",
-      "dev": true,
-      "requires": {
-        "spdx-expression-parse": "^3.0.0",
-        "spdx-license-ids": "^3.0.0"
-      }
-    },
-    "spdx-exceptions": {
-      "version": "2.1.0",
-      "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.1.0.tgz",
-      "integrity": "sha512-4K1NsmrlCU1JJgUrtgEeTVyfx8VaYea9J9LvARxhbHtVtohPs/gFGG5yy49beySjlIMhhXZ4QqujIZEfS4l6Cg==",
-      "dev": true
-    },
-    "spdx-expression-parse": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.0.tgz",
-      "integrity": "sha512-Yg6D3XpRD4kkOmTpdgbUiEJFKghJH03fiC1OPll5h/0sO6neh2jqRDVHOQ4o/LMea0tgCkbMgea5ip/e+MkWyg==",
-      "dev": true,
-      "requires": {
-        "spdx-exceptions": "^2.1.0",
-        "spdx-license-ids": "^3.0.0"
-      }
-    },
-    "spdx-license-ids": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.0.tgz",
-      "integrity": "sha512-2+EPwgbnmOIl8HjGBXXMd9NAu02vLjOO1nWw4kmeRDFyHn+M/ETfHxQUK0oXg8ctgVnl9t3rosNVsZ1jG61nDA==",
+    "split-on-first": {
+      "version": "1.1.0",
+      "resolved": "https://registry.npmjs.org/split-on-first/-/split-on-first-1.1.0.tgz",
+      "integrity": "sha512-43ZssAJaMusuKWL8sKUBQXHWOpq8d6CfN/u1p4gUzfJkM05C8rxTmYrkIPTXapZpORA6LkkzcUulJ8FqA7Uudw==",
       "dev": true
     },
     "split-string": {
@@ -10359,14 +10538,30 @@
       "dev": true
     },
     "string-width": {
-      "version": "1.0.2",
-      "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz",
-      "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=",
+      "version": "2.1.1",
+      "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz",
+      "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==",
       "dev": true,
       "requires": {
-        "code-point-at": "^1.0.0",
-        "is-fullwidth-code-point": "^1.0.0",
-        "strip-ansi": "^3.0.0"
+        "is-fullwidth-code-point": "^2.0.0",
+        "strip-ansi": "^4.0.0"
+      },
+      "dependencies": {
+        "ansi-regex": {
+          "version": "3.0.0",
+          "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz",
+          "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=",
+          "dev": true
+        },
+        "strip-ansi": {
+          "version": "4.0.0",
+          "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz",
+          "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=",
+          "dev": true,
+          "requires": {
+            "ansi-regex": "^3.0.0"
+          }
+        }
       }
     },
     "string_decoder": {
@@ -10389,12 +10584,6 @@
         "ansi-regex": "^2.0.0"
       }
     },
-    "strip-bom": {
-      "version": "3.0.0",
-      "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz",
-      "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=",
-      "dev": true
-    },
     "strip-eof": {
       "version": "1.0.0",
       "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz",
@@ -10402,9 +10591,9 @@
       "dev": true
     },
     "strip-json-comments": {
-      "version": "1.0.4",
-      "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-1.0.4.tgz",
-      "integrity": "sha1-HhX7ysl9Pumb8tc7TGVrCCu6+5E=",
+      "version": "2.0.1",
+      "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz",
+      "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=",
       "dev": true
     },
     "style-unit": {
@@ -10412,51 +10601,6 @@
       "resolved": "https://registry.npmjs.org/style-unit/-/style-unit-0.4.20.tgz",
       "integrity": "sha1-x/Nrgz+V3y9Zj5TcLVQXwIqtD8Q="
     },
-    "stylus": {
-      "version": "0.54.5",
-      "resolved": "https://registry.npmjs.org/stylus/-/stylus-0.54.5.tgz",
-      "integrity": "sha1-QrlWCTHKcJDOhRWnmLqeaqPW3Hk=",
-      "dev": true,
-      "requires": {
-        "css-parse": "1.7.x",
-        "debug": "*",
-        "glob": "7.0.x",
-        "mkdirp": "0.5.x",
-        "sax": "0.5.x",
-        "source-map": "0.1.x"
-      },
-      "dependencies": {
-        "glob": {
-          "version": "7.0.6",
-          "resolved": "https://registry.npmjs.org/glob/-/glob-7.0.6.tgz",
-          "integrity": "sha1-IRuvr0nlJbjNkyYNFKsTYVKz9Xo=",
-          "dev": true,
-          "requires": {
-            "fs.realpath": "^1.0.0",
-            "inflight": "^1.0.4",
-            "inherits": "2",
-            "minimatch": "^3.0.2",
-            "once": "^1.3.0",
-            "path-is-absolute": "^1.0.0"
-          }
-        },
-        "sax": {
-          "version": "0.5.8",
-          "resolved": "https://registry.npmjs.org/sax/-/sax-0.5.8.tgz",
-          "integrity": "sha1-1HLbIo6zMcJQaw6MFVJK25OdEsE=",
-          "dev": true
-        },
-        "source-map": {
-          "version": "0.1.43",
-          "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.1.43.tgz",
-          "integrity": "sha1-wkvBRspRfBRx9drL4lcbK3+eM0Y=",
-          "dev": true,
-          "requires": {
-            "amdefine": ">=0.0.4"
-          }
-        }
-      }
-    },
     "subarg": {
       "version": "1.0.0",
       "resolved": "https://registry.npmjs.org/subarg/-/subarg-1.0.0.tgz",
@@ -10483,6 +10627,41 @@
         "has-flag": "^1.0.0"
       }
     },
+    "supports-hyperlinks": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/supports-hyperlinks/-/supports-hyperlinks-1.0.1.tgz",
+      "integrity": "sha512-HHi5kVSefKaJkGYXbDuKbUGRVxqnWGn3J2e39CYcNJEfWciGq2zYtOhXLTlvrOZW1QU7VX67w7fMmWafHX9Pfw==",
+      "dev": true,
+      "requires": {
+        "has-flag": "^2.0.0",
+        "supports-color": "^5.0.0"
+      },
+      "dependencies": {
+        "has-flag": {
+          "version": "2.0.0",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz",
+          "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=",
+          "dev": true
+        },
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
+          "dev": true,
+          "requires": {
+            "has-flag": "^3.0.0"
+          },
+          "dependencies": {
+            "has-flag": {
+              "version": "3.0.0",
+              "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+              "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
+              "dev": true
+            }
+          }
+        }
+      }
+    },
     "svgo": {
       "version": "0.7.2",
       "resolved": "https://registry.npmjs.org/svgo/-/svgo-0.7.2.tgz",
@@ -10510,12 +10689,6 @@
         }
       }
     },
-    "symbol-tree": {
-      "version": "3.2.2",
-      "resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.2.tgz",
-      "integrity": "sha1-rifbOPZgp64uHDt9G8KQgZuFGeY=",
-      "dev": true
-    },
     "sync-exec": {
       "version": "0.6.2",
       "resolved": "https://registry.npmjs.org/sync-exec/-/sync-exec-0.6.2.tgz",
@@ -10533,58 +10706,52 @@
       }
     },
     "table": {
-      "version": "3.8.3",
-      "resolved": "https://registry.npmjs.org/table/-/table-3.8.3.tgz",
-      "integrity": "sha1-K7xULw/amGGnVdOUf+/Ys/UThV8=",
+      "version": "4.0.2",
+      "resolved": "https://registry.npmjs.org/table/-/table-4.0.2.tgz",
+      "integrity": "sha512-UUkEAPdSGxtRpiV9ozJ5cMTtYiqz7Ni1OGqLXRCynrvzdtR1p+cfOWe2RJLwvUG8hNanaSRjecIqwOjqeatDsA==",
       "dev": true,
       "requires": {
-        "ajv": "^4.7.0",
-        "ajv-keywords": "^1.0.0",
-        "chalk": "^1.1.1",
-        "lodash": "^4.0.0",
-        "slice-ansi": "0.0.4",
-        "string-width": "^2.0.0"
+        "ajv": "^5.2.3",
+        "ajv-keywords": "^2.1.0",
+        "chalk": "^2.1.0",
+        "lodash": "^4.17.4",
+        "slice-ansi": "1.0.0",
+        "string-width": "^2.1.1"
       },
       "dependencies": {
-        "ajv": {
-          "version": "4.11.8",
-          "resolved": "https://registry.npmjs.org/ajv/-/ajv-4.11.8.tgz",
-          "integrity": "sha1-gv+wKynmYq5TvcIK8VlHcGc5xTY=",
+        "ansi-styles": {
+          "version": "3.2.1",
+          "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz",
+          "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==",
           "dev": true,
           "requires": {
-            "co": "^4.6.0",
-            "json-stable-stringify": "^1.0.1"
+            "color-convert": "^1.9.0"
           }
         },
-        "ansi-regex": {
+        "chalk": {
+          "version": "2.4.2",
+          "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz",
+          "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==",
+          "dev": true,
+          "requires": {
+            "ansi-styles": "^3.2.1",
+            "escape-string-regexp": "^1.0.5",
+            "supports-color": "^5.3.0"
+          }
+        },
+        "has-flag": {
           "version": "3.0.0",
-          "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz",
-          "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=",
+          "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz",
+          "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=",
           "dev": true
         },
-        "is-fullwidth-code-point": {
-          "version": "2.0.0",
-          "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz",
-          "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=",
-          "dev": true
-        },
-        "string-width": {
-          "version": "2.1.1",
-          "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz",
-          "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==",
+        "supports-color": {
+          "version": "5.5.0",
+          "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz",
+          "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==",
           "dev": true,
           "requires": {
-            "is-fullwidth-code-point": "^2.0.0",
-            "strip-ansi": "^4.0.0"
-          }
-        },
-        "strip-ansi": {
-          "version": "4.0.0",
-          "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz",
-          "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=",
-          "dev": true,
-          "requires": {
-            "ansi-regex": "^3.0.0"
+            "has-flag": "^3.0.0"
           }
         }
       }
@@ -10621,295 +10788,6 @@
         }
       }
     },
-    "test-exclude": {
-      "version": "4.2.1",
-      "resolved": "https://registry.npmjs.org/test-exclude/-/test-exclude-4.2.1.tgz",
-      "integrity": "sha512-qpqlP/8Zl+sosLxBcVKl9vYy26T9NPalxSzzCP/OY6K7j938ui2oKgo+kRZYfxAeIpLqpbVnsHq1tyV70E4lWQ==",
-      "dev": true,
-      "requires": {
-        "arrify": "^1.0.1",
-        "micromatch": "^3.1.8",
-        "object-assign": "^4.1.0",
-        "read-pkg-up": "^1.0.1",
-        "require-main-filename": "^1.0.1"
-      },
-      "dependencies": {
-        "arr-diff": {
-          "version": "4.0.0",
-          "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz",
-          "integrity": "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=",
-          "dev": true
-        },
-        "array-unique": {
-          "version": "0.3.2",
-          "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz",
-          "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=",
-          "dev": true
-        },
-        "braces": {
-          "version": "2.3.2",
-          "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz",
-          "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==",
-          "dev": true,
-          "requires": {
-            "arr-flatten": "^1.1.0",
-            "array-unique": "^0.3.2",
-            "extend-shallow": "^2.0.1",
-            "fill-range": "^4.0.0",
-            "isobject": "^3.0.1",
-            "repeat-element": "^1.1.2",
-            "snapdragon": "^0.8.1",
-            "snapdragon-node": "^2.0.1",
-            "split-string": "^3.0.2",
-            "to-regex": "^3.0.1"
-          },
-          "dependencies": {
-            "extend-shallow": {
-              "version": "2.0.1",
-              "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
-              "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
-              "dev": true,
-              "requires": {
-                "is-extendable": "^0.1.0"
-              }
-            }
-          }
-        },
-        "expand-brackets": {
-          "version": "2.1.4",
-          "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz",
-          "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=",
-          "dev": true,
-          "requires": {
-            "debug": "^2.3.3",
-            "define-property": "^0.2.5",
-            "extend-shallow": "^2.0.1",
-            "posix-character-classes": "^0.1.0",
-            "regex-not": "^1.0.0",
-            "snapdragon": "^0.8.1",
-            "to-regex": "^3.0.1"
-          },
-          "dependencies": {
-            "define-property": {
-              "version": "0.2.5",
-              "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz",
-              "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=",
-              "dev": true,
-              "requires": {
-                "is-descriptor": "^0.1.0"
-              }
-            },
-            "extend-shallow": {
-              "version": "2.0.1",
-              "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
-              "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
-              "dev": true,
-              "requires": {
-                "is-extendable": "^0.1.0"
-              }
-            },
-            "is-accessor-descriptor": {
-              "version": "0.1.6",
-              "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz",
-              "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=",
-              "dev": true,
-              "requires": {
-                "kind-of": "^3.0.2"
-              },
-              "dependencies": {
-                "kind-of": {
-                  "version": "3.2.2",
-                  "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
-                  "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
-                  "dev": true,
-                  "requires": {
-                    "is-buffer": "^1.1.5"
-                  }
-                }
-              }
-            },
-            "is-data-descriptor": {
-              "version": "0.1.4",
-              "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz",
-              "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=",
-              "dev": true,
-              "requires": {
-                "kind-of": "^3.0.2"
-              },
-              "dependencies": {
-                "kind-of": {
-                  "version": "3.2.2",
-                  "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
-                  "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
-                  "dev": true,
-                  "requires": {
-                    "is-buffer": "^1.1.5"
-                  }
-                }
-              }
-            },
-            "is-descriptor": {
-              "version": "0.1.6",
-              "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz",
-              "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==",
-              "dev": true,
-              "requires": {
-                "is-accessor-descriptor": "^0.1.6",
-                "is-data-descriptor": "^0.1.4",
-                "kind-of": "^5.0.0"
-              }
-            },
-            "kind-of": {
-              "version": "5.1.0",
-              "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz",
-              "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==",
-              "dev": true
-            }
-          }
-        },
-        "extglob": {
-          "version": "2.0.4",
-          "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz",
-          "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==",
-          "dev": true,
-          "requires": {
-            "array-unique": "^0.3.2",
-            "define-property": "^1.0.0",
-            "expand-brackets": "^2.1.4",
-            "extend-shallow": "^2.0.1",
-            "fragment-cache": "^0.2.1",
-            "regex-not": "^1.0.0",
-            "snapdragon": "^0.8.1",
-            "to-regex": "^3.0.1"
-          },
-          "dependencies": {
-            "define-property": {
-              "version": "1.0.0",
-              "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz",
-              "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=",
-              "dev": true,
-              "requires": {
-                "is-descriptor": "^1.0.0"
-              }
-            },
-            "extend-shallow": {
-              "version": "2.0.1",
-              "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
-              "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
-              "dev": true,
-              "requires": {
-                "is-extendable": "^0.1.0"
-              }
-            }
-          }
-        },
-        "fill-range": {
-          "version": "4.0.0",
-          "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz",
-          "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=",
-          "dev": true,
-          "requires": {
-            "extend-shallow": "^2.0.1",
-            "is-number": "^3.0.0",
-            "repeat-string": "^1.6.1",
-            "to-regex-range": "^2.1.0"
-          },
-          "dependencies": {
-            "extend-shallow": {
-              "version": "2.0.1",
-              "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
-              "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
-              "dev": true,
-              "requires": {
-                "is-extendable": "^0.1.0"
-              }
-            }
-          }
-        },
-        "is-accessor-descriptor": {
-          "version": "1.0.0",
-          "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz",
-          "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==",
-          "dev": true,
-          "requires": {
-            "kind-of": "^6.0.0"
-          }
-        },
-        "is-data-descriptor": {
-          "version": "1.0.0",
-          "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz",
-          "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==",
-          "dev": true,
-          "requires": {
-            "kind-of": "^6.0.0"
-          }
-        },
-        "is-descriptor": {
-          "version": "1.0.2",
-          "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz",
-          "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==",
-          "dev": true,
-          "requires": {
-            "is-accessor-descriptor": "^1.0.0",
-            "is-data-descriptor": "^1.0.0",
-            "kind-of": "^6.0.2"
-          }
-        },
-        "is-number": {
-          "version": "3.0.0",
-          "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz",
-          "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=",
-          "dev": true,
-          "requires": {
-            "kind-of": "^3.0.2"
-          },
-          "dependencies": {
-            "kind-of": {
-              "version": "3.2.2",
-              "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz",
-              "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=",
-              "dev": true,
-              "requires": {
-                "is-buffer": "^1.1.5"
-              }
-            }
-          }
-        },
-        "isobject": {
-          "version": "3.0.1",
-          "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz",
-          "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=",
-          "dev": true
-        },
-        "kind-of": {
-          "version": "6.0.2",
-          "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz",
-          "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==",
-          "dev": true
-        },
-        "micromatch": {
-          "version": "3.1.10",
-          "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz",
-          "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==",
-          "dev": true,
-          "requires": {
-            "arr-diff": "^4.0.0",
-            "array-unique": "^0.3.2",
-            "braces": "^2.3.1",
-            "define-property": "^2.0.2",
-            "extend-shallow": "^3.0.2",
-            "extglob": "^2.0.4",
-            "fragment-cache": "^0.2.1",
-            "kind-of": "^6.0.2",
-            "nanomatch": "^1.2.9",
-            "object.pick": "^1.3.0",
-            "regex-not": "^1.0.0",
-            "snapdragon": "^0.8.1",
-            "to-regex": "^3.0.2"
-          }
-        }
-      }
-    },
     "text-encoding": {
       "version": "0.6.4",
       "resolved": "https://registry.npmjs.org/text-encoding/-/text-encoding-0.6.4.tgz",
@@ -10994,12 +10872,6 @@
         "os-tmpdir": "~1.0.2"
       }
     },
-    "tmpl": {
-      "version": "1.0.4",
-      "resolved": "https://registry.npmjs.org/tmpl/-/tmpl-1.0.4.tgz",
-      "integrity": "sha1-I2QN17QtAEM5ERQIIOXPRA5SHdE=",
-      "dev": true
-    },
     "to-arraybuffer": {
       "version": "1.0.1",
       "resolved": "https://registry.npmjs.org/to-arraybuffer/-/to-arraybuffer-1.0.1.tgz",
@@ -11068,11 +10940,31 @@
         "punycode": "^1.4.1"
       }
     },
+    "toxic": {
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/toxic/-/toxic-1.0.1.tgz",
+      "integrity": "sha512-WI3rIGdcaKULYg7KVoB0zcjikqvcYYvcuT6D89bFPz2rVR0Rl0PK6x8/X62rtdLtBKIE985NzVf/auTtGegIIg==",
+      "dev": true,
+      "requires": {
+        "lodash": "^4.17.10"
+      }
+    },
     "tr46": {
-      "version": "0.0.3",
-      "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz",
-      "integrity": "sha1-gYT9NH2snNwYWZLzpmIuFLnZq2o=",
-      "dev": true
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/tr46/-/tr46-1.0.1.tgz",
+      "integrity": "sha1-qLE/1r/SSJUZZ0zN5VujaTtwbQk=",
+      "dev": true,
+      "requires": {
+        "punycode": "^2.1.0"
+      },
+      "dependencies": {
+        "punycode": {
+          "version": "2.1.1",
+          "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz",
+          "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==",
+          "dev": true
+        }
+      }
     },
     "trim-right": {
       "version": "1.0.1",
@@ -11209,38 +11101,15 @@
       }
     },
     "union-value": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz",
-      "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=",
+      "version": "1.0.1",
+      "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.1.tgz",
+      "integrity": "sha512-tJfXmxMeWYnczCVs7XAEvIV7ieppALdyepWMkHkwciRpZraG/xwT+s2JN8+pr1+8jCRf80FFzvr+MpQeeoF4Xg==",
       "dev": true,
       "requires": {
         "arr-union": "^3.1.0",
         "get-value": "^2.0.6",
         "is-extendable": "^0.1.1",
-        "set-value": "^0.4.3"
-      },
-      "dependencies": {
-        "extend-shallow": {
-          "version": "2.0.1",
-          "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz",
-          "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=",
-          "dev": true,
-          "requires": {
-            "is-extendable": "^0.1.0"
-          }
-        },
-        "set-value": {
-          "version": "0.4.3",
-          "resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz",
-          "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=",
-          "dev": true,
-          "requires": {
-            "extend-shallow": "^2.0.1",
-            "is-extendable": "^0.1.1",
-            "is-plain-object": "^2.0.1",
-            "to-object-path": "^0.3.0"
-          }
-        }
+        "set-value": "^2.0.1"
       }
     },
     "uniq": {
@@ -11260,6 +11129,25 @@
       "resolved": "https://registry.npmjs.org/universal-env/-/universal-env-0.4.20.tgz",
       "integrity": "sha1-aVoXaccMGnFDNQllZnQYQfiQlyY="
     },
+    "universal-url": {
+      "version": "2.0.0",
+      "resolved": "https://registry.npmjs.org/universal-url/-/universal-url-2.0.0.tgz",
+      "integrity": "sha512-3DLtXdm/G1LQMCnPj+Aw7uDoleQttNHp2g5FnNQKR6cP6taNWS1b/Ehjjx4PVyvejKi3TJyu8iBraKM4q3JQPg==",
+      "dev": true,
+      "requires": {
+        "hasurl": "^1.0.0",
+        "whatwg-url": "^7.0.0"
+      }
+    },
+    "universal-user-agent": {
+      "version": "4.0.0",
+      "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-4.0.0.tgz",
+      "integrity": "sha512-eM8knLpev67iBDizr/YtqkJsF3GK8gzDc6st/WKzrTuPtcsOKW/0IdL4cnMBsU69pOx0otavLWBDGTwg+dB0aA==",
+      "dev": true,
+      "requires": {
+        "os-name": "^3.1.0"
+      }
+    },
     "unset-value": {
       "version": "1.0.0",
       "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz",
@@ -11312,6 +11200,33 @@
         }
       }
     },
+    "update-check": {
+      "version": "1.5.2",
+      "resolved": "https://registry.npmjs.org/update-check/-/update-check-1.5.2.tgz",
+      "integrity": "sha512-1TrmYLuLj/5ZovwUS7fFd1jMH3NnFDN1y1A8dboedIDt7zs/zJMo6TwwlhYKkSeEwzleeiSBV5/3c9ufAQWDaQ==",
+      "dev": true,
+      "requires": {
+        "registry-auth-token": "3.3.2",
+        "registry-url": "3.1.0"
+      }
+    },
+    "uri-js": {
+      "version": "4.2.2",
+      "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz",
+      "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==",
+      "dev": true,
+      "requires": {
+        "punycode": "^2.1.0"
+      },
+      "dependencies": {
+        "punycode": {
+          "version": "2.1.1",
+          "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz",
+          "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==",
+          "dev": true
+        }
+      }
+    },
     "urix": {
       "version": "0.1.0",
       "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz",
@@ -11348,15 +11263,6 @@
       "integrity": "sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==",
       "dev": true
     },
-    "user-home": {
-      "version": "2.0.0",
-      "resolved": "https://registry.npmjs.org/user-home/-/user-home-2.0.0.tgz",
-      "integrity": "sha1-nHC/2Babwdy/SGBODwS4tJzenp8=",
-      "dev": true,
-      "requires": {
-        "os-homedir": "^1.0.0"
-      }
-    },
     "util": {
       "version": "0.10.4",
       "resolved": "https://registry.npmjs.org/util/-/util-0.10.4.tgz",
@@ -11377,16 +11283,6 @@
       "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz",
       "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA=="
     },
-    "validate-npm-package-license": {
-      "version": "3.0.3",
-      "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.3.tgz",
-      "integrity": "sha512-63ZOUnL4SIXj4L0NixR3L1lcjO38crAbgrTpl28t8jjrfuiOBL5Iygm+60qPs/KsZGzPNg6Smnc/oY16QTjF0g==",
-      "dev": true,
-      "requires": {
-        "spdx-correct": "^3.0.0",
-        "spdx-expression-parse": "^3.0.0"
-      }
-    },
     "vargs": {
       "version": "0.1.0",
       "resolved": "https://registry.npmjs.org/vargs/-/vargs-0.1.0.tgz",
@@ -11424,12 +11320,6 @@
         "indexof": "0.0.1"
       }
     },
-    "voca": {
-      "version": "1.4.0",
-      "resolved": "https://registry.npmjs.org/voca/-/voca-1.4.0.tgz",
-      "integrity": "sha512-8Xz4H3vhYRGbFupLtl6dHwMx0ojUcjt0HYkqZ9oBCfipd/5mD7Md58m2/dq7uPuZU/0T3Gb1m66KS9jn+I+14Q==",
-      "dev": true
-    },
     "vue": {
       "version": "2.4.3",
       "resolved": "https://registry.npmjs.org/vue/-/vue-2.4.3.tgz",
@@ -11532,21 +11422,6 @@
       "integrity": "sha512-x3LV3wdmmERhVCYy3quqA57NJW7F3i6faas++pJQWtknWT+n7k30F4TVdHvCLn48peTJFRvCpxs3UuFPqgeELg==",
       "dev": true
     },
-    "walker": {
-      "version": "1.0.7",
-      "resolved": "https://registry.npmjs.org/walker/-/walker-1.0.7.tgz",
-      "integrity": "sha1-L3+bj9ENZ3JisYqITijRlhjgKPs=",
-      "dev": true,
-      "requires": {
-        "makeerror": "1.0.x"
-      }
-    },
-    "watch": {
-      "version": "0.10.0",
-      "resolved": "https://registry.npmjs.org/watch/-/watch-0.10.0.tgz",
-      "integrity": "sha1-d3mLLaD5kQ1ZXxrOWwwiWFIfIdw=",
-      "dev": true
-    },
     "watchpack": {
       "version": "0.2.9",
       "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-0.2.9.tgz",
@@ -12040,23 +11915,6 @@
         "webdriver-client": "^1.0.17"
       }
     },
-    "whatwg-encoding": {
-      "version": "1.0.3",
-      "resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-1.0.3.tgz",
-      "integrity": "sha512-jLBwwKUhi8WtBfsMQlL4bUUcT8sMkAtQinscJAe/M4KHCkHuUJAF6vuB0tueNIw4c8ziO6AkRmgY+jL3a0iiPw==",
-      "dev": true,
-      "requires": {
-        "iconv-lite": "0.4.19"
-      },
-      "dependencies": {
-        "iconv-lite": {
-          "version": "0.4.19",
-          "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz",
-          "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==",
-          "dev": true
-        }
-      }
-    },
     "whatwg-fetch": {
       "version": "2.0.4",
       "resolved": "https://registry.npmjs.org/whatwg-fetch/-/whatwg-fetch-2.0.4.tgz",
@@ -12064,21 +11922,14 @@
       "dev": true
     },
     "whatwg-url": {
-      "version": "4.8.0",
-      "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-4.8.0.tgz",
-      "integrity": "sha1-0pgaqRSMHgCkHFphMRZqtGg7vMA=",
+      "version": "7.1.0",
+      "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-7.1.0.tgz",
+      "integrity": "sha512-WUu7Rg1DroM7oQvGWfOiAK21n74Gg+T4elXEQYkOhtyLeWiJFoOGLXPKI/9gzIie9CtwVLm8wtw6YJdKyxSjeg==",
       "dev": true,
       "requires": {
-        "tr46": "~0.0.3",
-        "webidl-conversions": "^3.0.0"
-      },
-      "dependencies": {
-        "webidl-conversions": {
-          "version": "3.0.1",
-          "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz",
-          "integrity": "sha1-JFNCdeKnvGvnvIZhHMFq4KVlSHE=",
-          "dev": true
-        }
+        "lodash.sortby": "^4.7.0",
+        "tr46": "^1.0.1",
+        "webidl-conversions": "^4.0.2"
       }
     },
     "whet.extend": {
@@ -12096,43 +11947,27 @@
         "isexe": "^2.0.0"
       }
     },
-    "which-module": {
-      "version": "1.0.0",
-      "resolved": "https://registry.npmjs.org/which-module/-/which-module-1.0.0.tgz",
-      "integrity": "sha1-u6Y8qGGUiZT/MHc2CJ47lgJsKk8=",
-      "dev": true
-    },
     "window-size": {
       "version": "0.1.0",
       "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.0.tgz",
       "integrity": "sha1-VDjNLqk7IC76Ohn+iIeu58lPnJ0=",
       "dev": true
     },
+    "windows-release": {
+      "version": "3.2.0",
+      "resolved": "https://registry.npmjs.org/windows-release/-/windows-release-3.2.0.tgz",
+      "integrity": "sha512-QTlz2hKLrdqukrsapKsINzqMgOUpQW268eJ0OaOpJN32h272waxR9fkB9VoWRtK7uKHG5EHJcTXQBD8XZVJkFA==",
+      "dev": true,
+      "requires": {
+        "execa": "^1.0.0"
+      }
+    },
     "wordwrap": {
       "version": "1.0.0",
       "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz",
       "integrity": "sha1-J1hIEIkUVqQXHI0CJkQa3pDLyus=",
       "dev": true
     },
-    "worker-farm": {
-      "version": "1.6.0",
-      "resolved": "https://registry.npmjs.org/worker-farm/-/worker-farm-1.6.0.tgz",
-      "integrity": "sha512-6w+3tHbM87WnSWnENBUvA2pxJPLhQUg5LKwUQHq3r+XPhIM+Gh2R5ycbwPCyuGbNg+lPgdcnQUhuC02kJCvffQ==",
-      "dev": true,
-      "requires": {
-        "errno": "~0.1.7"
-      }
-    },
-    "wrap-ansi": {
-      "version": "2.1.0",
-      "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz",
-      "integrity": "sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=",
-      "dev": true,
-      "requires": {
-        "string-width": "^1.0.1",
-        "strip-ansi": "^3.0.1"
-      }
-    },
     "wrappy": {
       "version": "1.0.2",
       "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz",
@@ -12164,12 +11999,6 @@
         "xutil": "~1.0.0"
       }
     },
-    "xml-name-validator": {
-      "version": "2.0.1",
-      "resolved": "https://registry.npmjs.org/xml-name-validator/-/xml-name-validator-2.0.1.tgz",
-      "integrity": "sha1-TYuPHszTQZqjYgYb7O9RXh5VljU=",
-      "dev": true
-    },
     "xml-writer": {
       "version": "1.7.0",
       "resolved": "https://registry.npmjs.org/xml-writer/-/xml-writer-1.7.0.tgz",
@@ -12268,12 +12097,6 @@
         }
       }
     },
-    "y18n": {
-      "version": "3.2.1",
-      "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.1.tgz",
-      "integrity": "sha1-bRX7qITAhnnA136I53WegR4H+kE=",
-      "dev": true
-    },
     "yallist": {
       "version": "2.1.2",
       "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz",
@@ -12292,23 +12115,6 @@
         "window-size": "0.1.0"
       }
     },
-    "yargs-parser": {
-      "version": "4.2.1",
-      "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-4.2.1.tgz",
-      "integrity": "sha1-KczqwNxPA8bIe0qfIX3RjJ90hxw=",
-      "dev": true,
-      "requires": {
-        "camelcase": "^3.0.0"
-      },
-      "dependencies": {
-        "camelcase": {
-          "version": "3.0.0",
-          "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz",
-          "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=",
-          "dev": true
-        }
-      }
-    },
     "yauzl": {
       "version": "2.4.1",
       "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.4.1.tgz",
diff --git a/package.json b/package.json
index 28cb05c..9c0de09 100644
--- a/package.json
+++ b/package.json
@@ -99,7 +99,7 @@
     "css-loader": "^0.26.1",
     "danger": "^9.0.0",
     "dateformat": "^2.0.0",
-    "eslint": "^2.11.1",
+    "eslint": "^4.18.2",
     "eslint-plugin-flowtype": "^2.40.1",
     "fs-extra": "^2.0.0",
     "github": "^9.2.0",
@@ -120,7 +120,7 @@
     "rollup-plugin-replace": "^2.0.0",
     "rollup-plugin-uglify": "^2.0.1",
     "selenium-server": "2.53.1",
-    "serve": "^1.4.0",
+    "serve": "^7.1.3",
     "shelljs": "^0.7.8",
     "sinon": "^2.1.0",
     "sinon-chai": "^2.8.0",
diff --git a/scripts/build_from_source.sh b/scripts/build_from_source.sh
index de67740..30b89af 100755
--- a/scripts/build_from_source.sh
+++ b/scripts/build_from_source.sh
@@ -17,7 +17,7 @@
 # under the License.
 
 # This script is used to build weex from source, One may invoke this script by 
-# scripts/build_from_source.sh $NDK13_dir $NDK_16dir
+# scripts/build_from_source.sh 
 
 set -e
 if [ ! -f scripts/build_from_source.sh ];then
@@ -43,60 +43,16 @@
 cp dist/weex-rax.min.js pre-build/weex-rax-api.js
 
 # Build android_sdk
-if [ -d "android_sdk" ]
+cd android/
+if [ ! -d "gradle" ]
 then
-    git clone -b 0.23 --depth=1 git@github.com:alibaba/weex_js_engine.git
-    old_path=$PATH
-    export ANDROID_NDK=$1
-    export PATH=$1:$PATH
-    cd weex_js_engine/
-
-    sh build.jsc.sh
-    cp libWTF.so libJavaScriptCore.so ../android_sdk/libs/armeabi
-    cp libWTF.so libJavaScriptCore.so ../android_sdk/libs/armeabi-v7a
-
-    mkdir -p ../weex_core/Source/libs/armeabi
-    cp libWTF.so libJavaScriptCore.so ../weex_core/Source/libs/armeabi
-    mkdir -p ../weex_core/Source/libs/armeabi-v7a
-    cp libWTF.so libJavaScriptCore.so ../weex_core/Source/libs/armeabi-v7a
-
-    rm -rf build32
-    sh build.jsc.sh -t x86
-    cp libWTF.so libJavaScriptCore.so ../android_sdk/libs/x86
-    mkdir -p ../weex_core/Source/libs/x86
-    cp libWTF.so libJavaScriptCore.so ../weex_core/Source/libs/x86
-
-    PATH=$old_path
-    export ANDROID_NDK=$2
-    cd ..
-
-    gradle wrapper --gradle-version 4.4
-    echo 'include ":android_sdk"'>settings.gradle
-    echo "ndk.dir=$2">local.properties
-
-    ./gradlew :android_sdk:clean :android_sdk:assembleRelease -PignoreVersionCheck="true" -PbuildRuntimeApi=true
-
-    cp android_sdk/.externalNativeBuild/cmake/release/armeabi/Source/android/jsengine/libweexjsb.so android_sdk/libs/armeabi
-    cp android_sdk/.externalNativeBuild/cmake/release/armeabi/Source/android/jsengine/libweexjst.so android_sdk/libs/armeabi
-    cp android_sdk/.externalNativeBuild/cmake/release/armeabi-v7a/Source/android/jsengine/libweexjsb.so android_sdk/libs/armeabi-v7a
-    cp android_sdk/.externalNativeBuild/cmake/release/armeabi-v7a/Source/android/jsengine/libweexjst.so android_sdk/libs/armeabi-v7a
-    cp android_sdk/.externalNativeBuild/cmake/release/x86/Source/android/jsengine/libweexjsb.so android_sdk/libs/x86
-    cp android_sdk/.externalNativeBuild/cmake/release/x86/Source/android/jsengine/libweexjst.so android_sdk/libs/x86
-
-else
-    cd android/
-    ./gradlew :playground:clean :playground:assemble
-    cd ..
+    gradle wrapper --gradle-version 4.10.1
 fi
 
+./gradlew :weex_sdk:clean :weex_sdk:assembleRelease -PignoreVersionCheck="true" -PbuildRuntimeApi=true -PapachePackageName="true"
+cd ..
+
 # Build iOS sdk
-if [ -d "ios_sdk" ]
-then
-    xcodebuild -project ios_sdk/WeexSDK.xcodeproj -scheme WeexSDK_MTL
-else
-    cd ios
-    xcodebuild -project sdk/WeexSDK.xcodeproj -scheme WeexSDK_MTL
-    cd ..
-fi
+xcodebuild -project ios/sdk/WeexSDK.xcodeproj -scheme WeexSDK_MTL
 
 echo "Weex SDK Build completed."
diff --git a/scripts/generate_apache_source.sh b/scripts/generate_apache_source.sh
index d339337..9098be3 100755
--- a/scripts/generate_apache_source.sh
+++ b/scripts/generate_apache_source.sh
@@ -9,33 +9,4 @@
 
 rm -rf $dest
 mkdir $dest
-rsync -r --include-from=scripts/release_files.rules ./ $dest
-
-SED_CMD=sed
-if [ $(uname) == 'Darwin' ]; then
-  SED_CMD=/usr/bin/sed
-fi
-
-#repackage
-find $dest/android/sdk -type f \( -name '*.java' -o -name 'AndroidManifest.xml' -o -name 'proguard-rules.pro' \) -exec $SED_CMD -i '' 's/com\.taobao\.weex/org\.apache\.weex/g' {} \;
-find $dest/ios/sdk -type f \( -name 'project.pbxproj' -o -name '*.h' -o -name '*.m' -o -name '*.mm' \) -exec $SED_CMD -i '' 's/com\.taobao\.weex/org\.apache\.weex/g' {} \;
-
-mkdir -p $dest/android/sdk/src/main/java/org
-mkdir -p $dest/android/sdk/src/main/java/org/apache
-mv $dest/android/sdk/src/main/java/com/taobao $dest/android/sdk/src/main/java/org/apache
-rm -rf $dest/android/sdk/src/main/java/com
-
-mkdir -p $dest/android/sdk/src/test/java/org
-mkdir -p $dest/android/sdk/src/test/java/org/apache
-mv $dest/android/sdk/src/test/java/com/taobao $dest/android/sdk/src/test/java/org/apache
-rm -rf $dest/android/sdk/src/test/java/com
-
-mv $dest/ios/sdk $dest/ios_sdk
-mv $dest/android/sdk $dest/android_sdk
-$SED_CMD -i '' 's/\.\.\/\.\.\/weex_core/\.\.\/weex_core/g' $dest/android_sdk/build.gradle $dest/ios_sdk/WeexSDK.xcodeproj/project.pbxproj
-$SED_CMD -i '' 's/\.\.\/\.\.\/pre-build/\.\.\/pre-build/g' $dest/android_sdk/build.gradle $dest/ios_sdk/WeexSDK.xcodeproj/project.pbxproj
-[ -d "$dest/ios_sdk/build" ] && rm -rf "$dest/ios_sdk/build"
-mv $dest/android/build.gradle $dest/build.gradle
-rm -rf $dest/android $dest/ios
-
-rm -rf $dest/android_sdk/gradle
+rsync -r --include-from=scripts/release_files.rules ./ $dest
\ No newline at end of file
diff --git a/scripts/publish_release_candidate.sh b/scripts/publish_release_candidate.sh
index ef7465e..dba1748 100755
--- a/scripts/publish_release_candidate.sh
+++ b/scripts/publish_release_candidate.sh
@@ -36,5 +36,5 @@
 mkdir -p "$TMPDIR""weex_release_candidate/""$1/$2"
 cp "apache-weex-incubating-$1-$2-src.tar.gz" "apache-weex-incubating-$1-$2-src.tar.gz.asc" "apache-weex-incubating-$1-$2-src.tar.gz.sha512" "$TMPDIR""weex_release_candidate/""$1/$2"
 cd "$TMPDIR""weex_release_candidate"
-svn add "$1/$2"
-svn commit -m "$4"
\ No newline at end of file
+svn add . --force
+svn commit -m "Update for $1-$2"
diff --git a/scripts/publish_release_official.sh b/scripts/publish_release_official.sh
index 3d147a2..0752946 100755
--- a/scripts/publish_release_official.sh
+++ b/scripts/publish_release_official.sh
@@ -36,23 +36,26 @@
 sed -i '' 's/^/* /' commit-history.log
 sed -i '' -e '1i \
 # Detail Commit' commit-history.log
-cat CHANGELOG.md commit-history.log > RELEASE_NOTE.md
+cat DISCLAIMER CHANGELOG.md commit-history.log > RELEASE_NOTE.md
 
 echo "Publish source file to Apache SVN server"
 if [ ! -d "${TMPDIR}weex_release" ]
 then
     svn checkout https://dist.apache.org/repos/dist/release/incubator/weex/ "${TMPDIR}weex_release"
 fi
+cd "${TMPDIR}weex_release"
+export svn_dir=`ls -C -d */` ; svn delete $svn_dir
 mkdir -p "${TMPDIR}weex_release/${1}" && cd "$_"
 curl "https://dist.apache.org/repos/dist/dev/incubator/weex/${1}/${2}/apache-weex-incubating-${1}-${2}-src.tar.gz" -o "apache-weex-incubating-${1}-src.tar.gz"
 curl "https://dist.apache.org/repos/dist/dev/incubator/weex/${1}/${2}/apache-weex-incubating-${1}-${2}-src.tar.gz.asc" -o "apache-weex-incubating-${1}-src.tar.gz.asc"
 curl "https://dist.apache.org/repos/dist/dev/incubator/weex/${1}/${2}/apache-weex-incubating-${1}-${2}-src.tar.gz.sha512" -o "apache-weex-incubating-${1}-src.tar.gz.sha512"
 cd ..
-svn add "$1"
+svn add . --force
 svn commit -m "Release ${1}"
 
 echo "Push Git Tag to Github Repo"
-git tag -a -F "RELEASE_NOTE.md" "$1"
+pushd +3
+git tag -a -F "RELEASE_NOTE.md" "$1" "$1-$2"
 git push "$4" "$1"
 
 echo "Publish Github Release"
@@ -62,6 +65,7 @@
 
 echo "Publish Android JCenter Release"
 cd android
-./gradlew clean install bintray -PbuildRuntimeApi=true -PignoreVersionCheck="true"  -PweexVersion="$1" -PbintrayUser=alibabaweex -PbintrayApiKey="$6" 
+./gradlew :weex_sdk:clean :weex_sdk:install :weex_sdk:bintray -PgroupId="org.apache.weex" -PartifactName="sdk" -PapachePackageName="true" -PvcsTag="$1" -PunbundlingJSC="true" -PbuildRuntimeApi=true -PignoreVersionCheck="true" -PweexVersion="$1" -PbintrayUser=weex -PbintrayApiKey="$6" 
+./gradlew :weex_sdk:install :weex_sdk:bintray -PgroupId="org.apache.weex" -PartifactName="sdk_legacy" -PapachePackageName="false" -PvcsTag="$1" -PunbundlingJSC="true" -PbuildRuntimeApi=true -PignoreVersionCheck="true" -PweexVersion="$1" -PbintrayUser=weex -PbintrayApiKey="$6" 
 
 # Publish iOS to Cocoapods
\ No newline at end of file
diff --git a/scripts/release_files.rules b/scripts/release_files.rules
index 02e8b0f..0049f0a 100644
--- a/scripts/release_files.rules
+++ b/scripts/release_files.rules
@@ -29,6 +29,7 @@
 + /.eslintignore
 + /.babelrc
 + /src
++ /.rat-excludes
 - /src/h5-render/dist/index.js
 - /src/h5-render/node_modules
 - /src/js-framework/node_modules
@@ -53,22 +54,20 @@
 - weex_core/Source/base/android/jniprebuild/jni_files
 - weex_core/Source/base/android/jniprebuild/jni_generator.py
 - weex_core/Source/base/android/jniprebuild/prebuild.sh
-+ /weex_core/Source/include/JavaScriptCore/API/
-+ /weex_core/Source/include/JavaScriptCore/API/**
-+ /weex_core/Source/include/JavaScriptCore/ForwardingHeaders/
-+ /weex_core/Source/include/JavaScriptCore/ForwardingHeaders/JavaScriptCore/
-+ /weex_core/Source/include/JavaScriptCore/ForwardingHeaders/JavaScriptCore/**
-- /weex_core/Source/include/JavaScriptCore/**
+- /weex_core/Source/android/jsengine/dependence/
+- /weex_core/Source/include/JavaScriptCore/
 - /weex_core/Source/include/wtf/
+- /weex_core/Source/include/JSCHeaderNew/JavaScriptCore/
 + /weex_core
 + /weex_core/CMakeLists.txt
 + /weex_core/Source
 + /weex_core/Source/**
 
 ###### android #######
-+ /android
++ /android/
 + /android/build.gradle
-+ /android/sdk/
++ /android/settings.gradle
++ /android/license/***
 - /android/sdk/assets/*.js
 - /android/sdk/.gradle
 - /android/sdk/build
@@ -79,19 +78,25 @@
 - /android/sdk/.classpath
 - /android/sdk/.project
 - /android/sdk/weex_sdk.iml
-+ /android/sdk/**
+- /android/sdk/android-weex_sdk.iml
+- /android/sdk/weex-android-weex_sdk.iml
+- /android/sdk/.cxx
+- /android/sdk/src/legacyRelease
+- /android/sdk/src/main/jniLibs
++ /android/sdk/***
 
 ###### ios ###########
-+ /ios
-+ /ios/sdk/
++ /ios/
 - /ios/sdk/LICENSE
 - /ios/sdk/NOTICE
 - /ios/sdk/WeexSDK/Resources/main.js
-- ios/sdk/Products
+- /ios/sdk/Products
 - /ios/sdk/WeexSDK.xcodeproj/project.xcworkspace/xcuserdata
 - /ios/sdk/WeexSDK.xcodeproj/xcuserdata
 - /ios/sdk/WeexSDKTests/dependency
-+ /ios/sdk/**
+- /ios/sdk/build
+- /ios/playground
++ /ios/sdk/***
 
 ##### Others #######
 + /RELEASE_NOTE.md
diff --git a/test/scripts/util.js b/test/scripts/util.js
index 197858f..9267562 100644
--- a/test/scripts/util.js
+++ b/test/scripts/util.js
@@ -114,7 +114,7 @@
         return isIOS? iOSOpts : androidOpts;
     },
     getDeviceHost:function(){
-        return getIpAddress()+":12581";
+        return getIpAddress()+':'+ servePort;
     },
     getPage:function(name){
         let url
diff --git a/weex-playground b/weex-playground
index 2cb8f27..75d1051 160000
--- a/weex-playground
+++ b/weex-playground
@@ -1 +1 @@
-Subproject commit 2cb8f2740fe51917f945c4423b6720c77beb95af
+Subproject commit 75d10519cf4d05a2d133b07930aee3612f0cba3f
diff --git a/weex_core/.gitignore b/weex_core/.gitignore
index ba15c87..766f1a1 100644
--- a/weex_core/.gitignore
+++ b/weex_core/.gitignore
@@ -3,3 +3,5 @@
 build64/
 cmake-build-debug
 cscope.out
+
+/Source/include/JSCHeaderNew/JavaScriptCore
\ No newline at end of file
diff --git a/weex_core/Source/CMakeLists.txt b/weex_core/Source/CMakeLists.txt
index 035fd7a..19135ca 100755
--- a/weex_core/Source/CMakeLists.txt
+++ b/weex_core/Source/CMakeLists.txt
@@ -42,7 +42,7 @@
 add_definitions(-DDEBUG=1)
 
 message("ANDROID_PROJECT_DIR:"${ANDROID_PROJECT_DIR})
-set(LOCAL_LIBRARIES_DIR ${ANDROID_PROJECT_DIR}/libs/${ANDROID_ABI})
+set(LOCAL_LIBRARIES_DIR ${ANDROID_PROJECT_DIR}/src/main/jniLibs/${ANDROID_ABI})
 
 if ("${ANDROID_ABI}" STREQUAL "x86")
     # todo
@@ -119,19 +119,14 @@
   ## add_subdirectory for subdirectory has a CMakeLists.txt
   add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/third_party/IPC)
 
-
-  message("check build jsc BUILD_RUNTIME_API flag: ${BUILD_RUNTIME_API}")
-  if ("${BUILD_RUNTIME_API}" STREQUAL "true")
-      add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/js_runtime)
-      message("cmake build jsApi for runtime")
+  if (DEFINED BUILD_RUNTIME_API)
+    message("Variable BUILD_RUNTIME_API is defined with value: ${BUILD_RUNTIME_API}")
+    add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/js_runtime)
   else()
-      add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/android/jsengine)
-      message("cmake build jsApi for jsc")
+    message("Variable BUILD_RUNTIME_API is not defined")
+    add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/android/jsengine)
   endif()
 
-
-
-
   ## include_directories for include head file
   include_directories(${CMAKE_CURRENT_SOURCE_DIR}/third_party/IPC)
 
diff --git a/weex_core/Source/WXBridge_jni.h b/weex_core/Source/WXBridge_jni.h
index 685f9f5..b889289 100644
--- a/weex_core/Source/WXBridge_jni.h
+++ b/weex_core/Source/WXBridge_jni.h
@@ -23,7 +23,7 @@
 // This file is autogenerated by
 //     base/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/bridge/WXBridge
+//     org/apache/weex/bridge/WXBridge
 
 #ifndef com_taobao_weex_bridge_WXBridge_JNI
 #define com_taobao_weex_bridge_WXBridge_JNI
@@ -34,7 +34,7 @@
 
 // Step 1: forward declarations.
 namespace {
-const char kWXBridgeClassPath[] = "com/taobao/weex/bridge/WXBridge";
+const char kWXBridgeClassPath[] = "org/apache/weex/bridge/WXBridge";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 jclass g_WXBridge_clazz = NULL;
 #define WXBridge_clazz(env) g_WXBridge_clazz
@@ -915,7 +915,7 @@
 "Ljava/lang/String;"
 "J"
 ")"
-"Lcom/taobao/weex/layout/ContentBoxMeasurement;",
+"Lorg/apache/weex/layout/ContentBoxMeasurement;",
       &g_WXBridge_getMeasurementFunc);
 
   jobject ret =
@@ -957,7 +957,7 @@
     { "nativeInitFrameworkEnv",
 "("
 "Ljava/lang/String;"
-"Lcom/taobao/weex/bridge/WXParams;"
+"Lorg/apache/weex/bridge/WXParams;"
 "Ljava/lang/String;"
 "Z"
 ")"
@@ -965,7 +965,7 @@
     { "nativeInitFramework",
 "("
 "Ljava/lang/String;"
-"Lcom/taobao/weex/bridge/WXParams;"
+"Lorg/apache/weex/bridge/WXParams;"
 ")"
 "I", reinterpret_cast<void*>(InitFramework) },
     { "nativeRefreshInstance",
@@ -973,7 +973,7 @@
 "Ljava/lang/String;"
 "Ljava/lang/String;"
 "Ljava/lang/String;"
-"[Lcom/taobao/weex/bridge/WXJSObject;"
+"[Lorg/apache/weex/bridge/WXJSObject;"
 ")"
 "V", reinterpret_cast<void*>(RefreshInstance) },
     { "nativeExecJS",
@@ -981,7 +981,7 @@
 "Ljava/lang/String;"
 "Ljava/lang/String;"
 "Ljava/lang/String;"
-"[Lcom/taobao/weex/bridge/WXJSObject;"
+"[Lorg/apache/weex/bridge/WXJSObject;"
 ")"
 "I", reinterpret_cast<void*>(ExecJS) },
     { "nativeExecJSService",
@@ -994,7 +994,7 @@
 "Ljava/lang/String;"
 "Ljava/lang/String;"
 "Ljava/lang/String;"
-"[Lcom/taobao/weex/bridge/WXJSObject;"
+"[Lorg/apache/weex/bridge/WXJSObject;"
 ")"
 "[B", reinterpret_cast<void*>(ExecJSWithResult) },
     { "nativeExecJSWithCallback",
@@ -1002,7 +1002,7 @@
 "Ljava/lang/String;"
 "Ljava/lang/String;"
 "Ljava/lang/String;"
-"[Lcom/taobao/weex/bridge/WXJSObject;"
+"[Lorg/apache/weex/bridge/WXJSObject;"
 "J"
 ")"
 "V", reinterpret_cast<void*>(ExecJSWithCallback) },
@@ -1011,7 +1011,7 @@
 "Ljava/lang/String;"
 "Ljava/lang/String;"
 "Ljava/lang/String;"
-"[Lcom/taobao/weex/bridge/WXJSObject;"
+"[Lorg/apache/weex/bridge/WXJSObject;"
 ")"
 "I", reinterpret_cast<void*>(CreateInstanceContext) },
     { "nativeDestoryInstance",
@@ -1019,7 +1019,7 @@
 "Ljava/lang/String;"
 "Ljava/lang/String;"
 "Ljava/lang/String;"
-"[Lcom/taobao/weex/bridge/WXJSObject;"
+"[Lorg/apache/weex/bridge/WXJSObject;"
 ")"
 "I", reinterpret_cast<void*>(DestoryInstance) },
     { "nativeExecJSOnInstance",
diff --git a/weex_core/Source/android/jsengine/object/js_action.h b/weex_core/Source/android/jsengine/object/js_action.h
index 3068df0..4e954ad 100644
--- a/weex_core/Source/android/jsengine/object/js_action.h
+++ b/weex_core/Source/android/jsengine/object/js_action.h
@@ -24,9 +24,16 @@
 #define WEEX_PROJECT_RUN_JS_NOT_FOR_WEEX_H
 
 #include <string>
-#include <task/back_to_weex_core_queue.h>
+
+#ifdef USE_JS_RUNTIME
+#include "js_runtime/weex/task/back_to_weex_core_queue.h"
+#include "js_runtime/weex/object/weex_global_object_v2.h"
+#include "js_runtime/runtime/jsc/jsc_utils.h"
+#else
+#include "android/jsengine/task/back_to_weex_core_queue.h"
+#include "android/jsengine/object/weex_global_object.h"
 #include "android/jsengine/weex_jsc_utils.h"
-#include "weex_global_object.h"
+#endif
 
 class JSAction {
  public:
diff --git a/weex_core/Source/android/wrap/log_utils.cpp b/weex_core/Source/android/wrap/log_utils.cpp
index 1942259..0c432c0 100644
--- a/weex_core/Source/android/wrap/log_utils.cpp
+++ b/weex_core/Source/android/wrap/log_utils.cpp
@@ -27,7 +27,7 @@
 
 namespace WeexCore {
 
-const char kWXLogUtilsClassPath[] = "com/taobao/weex/utils/WXLogUtils";
+const char kWXLogUtilsClassPath[] = "org/apache/weex/utils/WXLogUtils";
 static jclass g_WXLogUtils_clazz = nullptr;
 
 static intptr_t g_WXLogUtils_d = 0;
diff --git a/weex_core/Source/android/wrap/wml_bridge.cpp b/weex_core/Source/android/wrap/wml_bridge.cpp
index f93dbfd..63741f8 100644
--- a/weex_core/Source/android/wrap/wml_bridge.cpp
+++ b/weex_core/Source/android/wrap/wml_bridge.cpp
@@ -189,7 +189,7 @@
 
 static JNINativeMethod gWMMethods[] = {
     {"nativeInitAppFramework",
-     "(Ljava/lang/String;Ljava/lang/String;[Lcom/taobao/weex/bridge/"
+     "(Ljava/lang/String;Ljava/lang/String;[Lorg/apache/weex/bridge/"
      "WXJSObject;)I",
      (void*)InitAppFramework},
     {"nativeCreateAppContext",
@@ -197,7 +197,7 @@
      (void*)CreateAppContext},
     {"nativeExecJsOnApp",
      "(Ljava/lang/String;Ljava/lang/String;"
-     "[Lcom/taobao/weex/bridge/WXJSObject;)I",
+     "[Lorg/apache/weex/bridge/WXJSObject;)I",
      (void*)ExecJsOnApp},
     {"nativeExecJsOnAppWithResult",
      "(Ljava/lang/String;Ljava/lang/String;"
diff --git a/weex_core/Source/android/wrap/wx_js_object.cpp b/weex_core/Source/android/wrap/wx_js_object.cpp
index 50a10dc..adceb5c 100644
--- a/weex_core/Source/android/wrap/wx_js_object.cpp
+++ b/weex_core/Source/android/wrap/wx_js_object.cpp
@@ -22,7 +22,7 @@
 #include "base/android/jni/android_jni.h"
 
 namespace WeexCore {
-const char kWXJSObjectClassPath[] = "com/taobao/weex/bridge/WXJSObject";
+const char kWXJSObjectClassPath[] = "org/apache/weex/bridge/WXJSObject";
 jclass g_WXJSObject_clazz = nullptr;
 
 jfieldID g_WXJSObject_filedID_type = nullptr;
diff --git a/weex_core/Source/android/wrap/wx_map.cpp b/weex_core/Source/android/wrap/wx_map.cpp
index 116d754..2470ab4 100644
--- a/weex_core/Source/android/wrap/wx_map.cpp
+++ b/weex_core/Source/android/wrap/wx_map.cpp
@@ -24,7 +24,7 @@
 #include "base/android/jni/android_jni.h"
 
 namespace WeexCore {
-const char kWXMapClassPath[] = "com/taobao/weex/utils/WXMap";
+const char kWXMapClassPath[] = "org/apache/weex/utils/WXMap";
 jclass g_WXMap_clazz = nullptr;
 
 static intptr_t g_WXMap_constructor = 0;
diff --git a/weex_core/Source/base/android/jniprebuild/jni_files b/weex_core/Source/base/android/jniprebuild/jni_files
index 1662c27..c8276c5 100644
--- a/weex_core/Source/base/android/jniprebuild/jni_files
+++ b/weex_core/Source/base/android/jniprebuild/jni_files
@@ -1 +1 @@
-com/taobao/weex/bridge/WXBridge.java
+org/apache/weex/bridge/WXBridge.java
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/ContentBoxMeasurement_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/ContentBoxMeasurement_jni.h
index dd92724..5a055e9 100644
--- a/weex_core/Source/base/android/jniprebuild/jniheader/ContentBoxMeasurement_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/ContentBoxMeasurement_jni.h
@@ -21,7 +21,7 @@
 // This file is autogenerated by
 //    weex-core2/weex_core/Source/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/layout/ContentBoxMeasurement
+//     org/apache/weex/layout/ContentBoxMeasurement
 
 #ifndef com_taobao_weex_layout_ContentBoxMeasurement_JNI
 #define com_taobao_weex_layout_ContentBoxMeasurement_JNI
@@ -33,7 +33,7 @@
 // Step 1: forward declarations.
 namespace {
 const char kContentBoxMeasurementClassPath[] =
-    "com/taobao/weex/layout/ContentBoxMeasurement";
+    "org/apache/weex/layout/ContentBoxMeasurement";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 jclass g_ContentBoxMeasurement_clazz = NULL;
 #define ContentBoxMeasurement_clazz(env) g_ContentBoxMeasurement_clazz
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/JSContext_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/JSContext_jni.h
index 601ef47..18e03d7 100644
--- a/weex_core/Source/base/android/jniprebuild/jniheader/JSContext_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/JSContext_jni.h
@@ -25,7 +25,7 @@
 #include <jni.h>
 #include "base/android/jni/android_jni.h"
 
-const char kJSContextClassPath[] = "com/taobao/weex/jsEngine/JSContext";
+const char kJSContextClassPath[] = "org/apache/weex/jsEngine/JSContext";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 jclass g_JSContext_clazz = NULL;
 
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/NativeRenderObjectUtils_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/NativeRenderObjectUtils_jni.h
index 2a71a70..e15dac3 100644
--- a/weex_core/Source/base/android/jniprebuild/jniheader/NativeRenderObjectUtils_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/NativeRenderObjectUtils_jni.h
@@ -20,7 +20,7 @@
 // This file is autogenerated by
 //     incubator-weex/weex_core/Source/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/ui/component/list/template/jni/NativeRenderObjectUtils
+//     org/apache/weex/ui/component/list/template/jni/NativeRenderObjectUtils
 
 #ifndef com_taobao_weex_ui_component_list_template_jni_NativeRenderObjectUtils_JNI
 #define com_taobao_weex_ui_component_list_template_jni_NativeRenderObjectUtils_JNI
@@ -32,7 +32,7 @@
 // Step 1: forward declarations.
 namespace {
 const char kNativeRenderObjectUtilsClassPath[] =
-    "com/taobao/weex/ui/component/list/template/jni/NativeRenderObjectUtils";
+    "org/apache/weex/ui/component/list/template/jni/NativeRenderObjectUtils";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 jclass g_NativeRenderObjectUtils_clazz = NULL;
 #define NativeRenderObjectUtils_clazz(env) g_NativeRenderObjectUtils_clazz
@@ -107,7 +107,7 @@
       "updateComponentSize",
 
 "("
-"Lcom/taobao/weex/ui/component/WXComponent;"
+"Lorg/apache/weex/ui/component/WXComponent;"
 "F"
 "F"
 "F"
@@ -189,7 +189,7 @@
     { "nativeRenderObjectUpdateComponent",
 "("
 "J"
-"Lcom/taobao/weex/ui/component/WXComponent;"
+"Lorg/apache/weex/ui/component/WXComponent;"
 ")"
 "V", reinterpret_cast<void*>(RenderObjectUpdateComponent) },
     { "nativeRenderObjectChildWaste",
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/RequestHandler_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/RequestHandler_jni.h
index e4ffd3c..d2eb6dd 100644
--- a/weex_core/Source/base/android/jniprebuild/jniheader/RequestHandler_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/RequestHandler_jni.h
@@ -20,7 +20,7 @@
 // This file is autogenerated by
 //     weex/weex_core/Source/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/bridge/RequestHandler
+//     org/apache/weex/bridge/RequestHandler
 
 #ifndef com_taobao_weex_bridge_RequestHandler_JNI
 #define com_taobao_weex_bridge_RequestHandler_JNI
@@ -31,7 +31,7 @@
 
 // Step 1: forward declarations.
 namespace {
-const char kRequestHandlerClassPath[] = "com/taobao/weex/bridge/RequestHandler";
+const char kRequestHandlerClassPath[] = "org/apache/weex/bridge/RequestHandler";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 jclass g_RequestHandler_clazz = NULL;
 #define RequestHandler_clazz(env) g_RequestHandler_clazz
@@ -62,7 +62,7 @@
 
 "("
 ")"
-"Lcom/taobao/weex/bridge/RequestHandler;",
+"Lorg/apache/weex/bridge/RequestHandler;",
       &g_RequestHandler_create);
 
   jobject ret =
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/SystemMessageHandler_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/SystemMessageHandler_jni.h
index 3df56e9..bebf2e5 100644
--- a/weex_core/Source/base/android/jniprebuild/jniheader/SystemMessageHandler_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/SystemMessageHandler_jni.h
@@ -20,7 +20,7 @@
 // This file is autogenerated by
 //     incubator-weex/weex_core/Source/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/base/SystemMessageHandler
+//     org/apache/weex/base/SystemMessageHandler
 
 #ifndef com_taobao_weex_base_SystemMessageHandler_JNI
 #define com_taobao_weex_base_SystemMessageHandler_JNI
@@ -32,7 +32,7 @@
 // Step 1: forward declarations.
 namespace {
 const char kSystemMessageHandlerClassPath[] =
-    "com/taobao/weex/base/SystemMessageHandler";
+    "org/apache/weex/base/SystemMessageHandler";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 jclass g_SystemMessageHandler_clazz = NULL;
 #define SystemMessageHandler_clazz(env) g_SystemMessageHandler_clazz
@@ -60,7 +60,7 @@
 "("
 "J"
 ")"
-"Lcom/taobao/weex/base/SystemMessageHandler;",
+"Lorg/apache/weex/base/SystemMessageHandler;",
       &g_SystemMessageHandler_create);
 
   jobject ret =
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/WXBridge_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/WXBridge_jni.h
index 0e89ab6..3b68c16 100755
--- a/weex_core/Source/base/android/jniprebuild/jniheader/WXBridge_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/WXBridge_jni.h
@@ -20,7 +20,7 @@
 // This file is autogenerated by
 //     incubator-weex/weex_core/Source/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/bridge/WXBridge
+//     org/apache/weex/bridge/WXBridge
 
 #ifndef com_taobao_weex_bridge_WXBridge_JNI
 #define com_taobao_weex_bridge_WXBridge_JNI
@@ -32,7 +32,7 @@
 
 // Step 1: forward declarations.
 namespace {
-const char kWXBridgeClassPath[] = "com/taobao/weex/bridge/WXBridge";
+const char kWXBridgeClassPath[] = "org/apache/weex/bridge/WXBridge";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 jclass g_WXBridge_clazz = NULL;
 #define WXBridge_clazz(env) g_WXBridge_clazz
@@ -1100,7 +1100,7 @@
           "Ljava/lang/String;"
           "J"
           ")"
-          "Lcom/taobao/weex/layout/ContentBoxMeasurement;",
+          "Lorg/apache/weex/layout/ContentBoxMeasurement;",
           &g_WXBridge_getMeasurementFunc);
 
   jobject ret =
@@ -1167,7 +1167,7 @@
     {"nativeInitFrameworkEnv",
      "("
      "Ljava/lang/String;"
-     "Lcom/taobao/weex/bridge/WXParams;"
+     "Lorg/apache/weex/bridge/WXParams;"
      "Ljava/lang/String;"
      "Z"
      ")"
@@ -1175,7 +1175,7 @@
     {"nativeInitFramework",
      "("
      "Ljava/lang/String;"
-     "Lcom/taobao/weex/bridge/WXParams;"
+     "Lorg/apache/weex/bridge/WXParams;"
      ")"
      "I", reinterpret_cast<void *>(InitFramework)},
     {"nativeRefreshInstance",
@@ -1183,7 +1183,7 @@
      "Ljava/lang/String;"
      "Ljava/lang/String;"
      "Ljava/lang/String;"
-     "[Lcom/taobao/weex/bridge/WXJSObject;"
+     "[Lorg/apache/weex/bridge/WXJSObject;"
      ")"
      "V", reinterpret_cast<void *>(RefreshInstance)},
     {"nativeExecJS",
@@ -1191,7 +1191,7 @@
      "Ljava/lang/String;"
      "Ljava/lang/String;"
      "Ljava/lang/String;"
-     "[Lcom/taobao/weex/bridge/WXJSObject;"
+     "[Lorg/apache/weex/bridge/WXJSObject;"
      ")"
      "I", reinterpret_cast<void *>(ExecJS)},
     {"nativeExecJSService",
@@ -1204,7 +1204,7 @@
      "Ljava/lang/String;"
      "Ljava/lang/String;"
      "Ljava/lang/String;"
-     "[Lcom/taobao/weex/bridge/WXJSObject;"
+     "[Lorg/apache/weex/bridge/WXJSObject;"
      "J"
      ")"
      "V", reinterpret_cast<void *>(ExecJSWithCallback)},
@@ -1213,7 +1213,7 @@
      "Ljava/lang/String;"
      "Ljava/lang/String;"
      "Ljava/lang/String;"
-     "[Lcom/taobao/weex/bridge/WXJSObject;"
+     "[Lorg/apache/weex/bridge/WXJSObject;"
      ")"
      "I", reinterpret_cast<void *>(CreateInstanceContext)},
     {"nativeDestoryInstance",
@@ -1221,7 +1221,7 @@
      "Ljava/lang/String;"
      "Ljava/lang/String;"
      "Ljava/lang/String;"
-     "[Lcom/taobao/weex/bridge/WXJSObject;"
+     "[Lorg/apache/weex/bridge/WXJSObject;"
      ")"
      "I", reinterpret_cast<void *>(DestoryInstance)},
     {"nativeExecJSOnInstance",
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/WXDebugJsBridge_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/WXDebugJsBridge_jni.h
index 458f435..78859ce 100644
--- a/weex_core/Source/base/android/jniprebuild/jniheader/WXDebugJsBridge_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/WXDebugJsBridge_jni.h
@@ -20,7 +20,7 @@
 // This file is autogenerated by
 //     weex_core_debug/Source/WeexCore/platform/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/bridge/WxDebugJsBridge
+//     org/apache/weex/bridge/WxDebugJsBridge
 
 #ifndef WEEX_PROJECT_WXDEBUGJSBRIDGE_JNI_H
 #define WEEX_PROJECT_WXDEBUGJSBRIDGE_JNI_H
@@ -29,7 +29,7 @@
 #include "base/android/jni/android_jni.h"
 
 namespace {
-    const char kWXDebugJsBridgeClassPath[] = "com/taobao/weex/bridge/WXDebugJsBridge";
+    const char kWXDebugJsBridgeClassPath[] = "org/apache/weex/bridge/WXDebugJsBridge";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
     jclass g_WXDebugJsBridge_clazz = NULL;
 #define WXDebugJsBridge_clazz(env) g_WXDebugJsBridge_clazz
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/WXJsFunctions_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/WXJsFunctions_jni.h
index 2a18241..62a6e5e 100644
--- a/weex_core/Source/base/android/jniprebuild/jniheader/WXJsFunctions_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/WXJsFunctions_jni.h
@@ -20,7 +20,7 @@
 // This file is autogenerated by
 //     weex_core_debug/Source/WeexCore/platform/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/bridge/JsFunctions
+//     org/apache/weex/bridge/JsFunctions
 
 #ifndef WEEX_PROJECT_WXJSFUNCTIONS_JNI_H
 #define WEEX_PROJECT_WXJSFUNCTIONS_JNI_H
@@ -29,7 +29,7 @@
 #include "base/android/jni/android_jni.h"
 
 namespace {
-    const char kWXJsFunctionClassPath[] = "com/taobao/weex/bridge/WXJsFunctions";
+    const char kWXJsFunctionClassPath[] = "org/apache/weex/bridge/WXJsFunctions";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
     jclass g_WXJsFunction_clazz = NULL;
 #define WXJsFunction_clazz(env) g_WXJsFunction_clazz
diff --git a/weex_core/Source/base/android/jniprebuild/jniheader/WXParams_jni.h b/weex_core/Source/base/android/jniprebuild/jniheader/WXParams_jni.h
index a215be4..7b68ba8 100644
--- a/weex_core/Source/base/android/jniprebuild/jniheader/WXParams_jni.h
+++ b/weex_core/Source/base/android/jniprebuild/jniheader/WXParams_jni.h
@@ -20,7 +20,7 @@
 // This file is autogenerated by
 //     incubator-weex/weex_core/Source/android/jniprebuild/jni_generator.py
 // For
-//     com/taobao/weex/bridge/WXParams
+//     org/apache/weex/bridge/WXParams
 
 #ifndef com_taobao_weex_bridge_WXParams_JNI
 #define com_taobao_weex_bridge_WXParams_JNI
@@ -32,7 +32,7 @@
 
 // Step 1: forward declarations.
 namespace {
-const char kWXParamsClassPath[] = "com/taobao/weex/bridge/WXParams";
+const char kWXParamsClassPath[] = "org/apache/weex/bridge/WXParams";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 jclass g_WXParams_clazz = NULL;
 #define WXParams_clazz(env) g_WXParams_clazz
diff --git a/weex_core/Source/core/bridge/platform/core_side_in_platform.cpp b/weex_core/Source/core/bridge/platform/core_side_in_platform.cpp
index bc58557..192b9bf 100644
--- a/weex_core/Source/core/bridge/platform/core_side_in_platform.cpp
+++ b/weex_core/Source/core/bridge/platform/core_side_in_platform.cpp
@@ -396,8 +396,11 @@
     args->value.string = genWeexString(
         reinterpret_cast<const uint16_t*>(utf16_key.c_str()), utf16_key.size());
     msg.push_back(args);
-
-    WeexCore::WeexCoreManager::Instance()->script_bridge()->script_side()->ExecJS(
+    ScriptBridge* bridge = WeexCore::WeexCoreManager::Instance()->script_bridge();
+    if (!bridge){
+      return false;
+    }
+    bridge->script_side()->ExecJS(
         instanceId, "", "callJS", msg);
     freeParams(msg);
     return true;
diff --git a/weex_core/Source/core/layout/layout.h b/weex_core/Source/core/layout/layout.h
index 6217972..e8d58f7 100644
--- a/weex_core/Source/core/layout/layout.h
+++ b/weex_core/Source/core/layout/layout.h
@@ -731,6 +731,10 @@
       
       markDirty();
     }
+      
+    inline void clearBFCs() {
+        BFCs.clear();
+    }
 
     inline void addChildAt(WXCoreLayoutNode* const child, Index index) {
       mChildList.insert(mChildList.begin() + index, child);
diff --git a/weex_core/Source/core/render/page/render_page.cpp b/weex_core/Source/core/render/page/render_page.cpp
index edf96cb..79a3644 100755
--- a/weex_core/Source/core/render/page/render_page.cpp
+++ b/weex_core/Source/core/render/page/render_page.cpp
@@ -221,6 +221,16 @@
     }
   }
 
+  if(index > new_parent->getChildCount()){
+    std::stringstream msg;
+    msg << "Out of array bounds when RenderPage::MoveRenderObject, specified index: "
+    << index << "array size " << new_parent->getChildCount();
+
+    WeexCore::WeexCoreManager::Instance()->getPlatformBridge()->platform_side()
+    ->ReportException(page_id().c_str(), "RenderPage::MoveRenderObject", msg.str().c_str());
+    return false;
+  }
+
   set_is_dirty(true);
   child->getParent()->removeChild(child);
   new_parent->addChildAt(child, index);
diff --git a/weex_core/Source/core/render/page/render_page_custom.cpp b/weex_core/Source/core/render/page/render_page_custom.cpp
index 2317511..3d464ff 100644
--- a/weex_core/Source/core/render/page/render_page_custom.cpp
+++ b/weex_core/Source/core/render/page/render_page_custom.cpp
@@ -21,11 +21,6 @@
 #include "render_page_custom.h"
 
 namespace WeexCore {
-    
-    template<typename T>
-    static std::shared_ptr<T> SharedMove(T& source) {
-        return std::make_shared<T>(std::move(source));
-    }
 
     RenderPageCustom::RenderPageCustom(const std::string& page_id, const std::string& page_type, const PageOptions& options): RenderPageBase(page_id, page_type) {
         valid_ = true;
@@ -37,7 +32,7 @@
             targetOptions.is_round_off = options.is_round_off;
             targetOptions.viewport_width = options.viewport_width;
             targetOptions.device_width = options.device_width;
-            target_->createPage(page_id, targetOptions);;
+            target_->createPage(page_id, targetOptions);
         }
     }
     
@@ -46,10 +41,8 @@
                             std::map<std::string, std::string>* attrs,
                             std::set<std::string>* events) {
         if (target_) {
-            auto managedStyles = SharedMove(*styles);
-            auto managedAttrs = SharedMove(*attrs);
-            auto managedEvents = SharedMove(*events);
-            target_->createBody(page_id_, ref, type, managedStyles, managedAttrs, managedEvents);
+            target_->createBody(page_id_, ref, type, styles, attrs, events);
+            return true;
         }
         delete styles;
         delete attrs;
@@ -63,10 +56,8 @@
                                            std::map<std::string, std::string>* attrs,
                                            std::set<std::string>* events) {
         if (target_) {
-            auto managedStyles = SharedMove(*styles);
-            auto managedAttrs = SharedMove(*attrs);
-            auto managedEvents = SharedMove(*events);
-            target_->addElement(page_id_, ref, type, parent_ref, index, managedStyles, managedAttrs, managedEvents);
+            target_->addElement(page_id_, ref, type, parent_ref, index, styles, attrs, events);
+            return true;
         }
         delete styles;
         delete attrs;
@@ -90,11 +81,11 @@
     
     bool RenderPageCustom::UpdateStyle(const std::string &ref, std::vector<std::pair<std::string, std::string>> *styles) {
         if (target_) {
-            std::shared_ptr<std::map<std::string, std::string>> managedStyles = std::make_shared<std::map<std::string, std::string>>();
+            std::map<std::string, std::string>* stylesMap = new std::map<std::string, std::string>();
             for (auto& p : *styles) {
-                (*managedStyles)[std::move(p.first)] = std::move(p.second);
+                (*stylesMap)[std::move(p.first)] = std::move(p.second);
             }
-            target_->updateStyles(page_id_, ref, managedStyles);
+            target_->updateStyles(page_id_, ref, stylesMap);
         }
         delete styles;
         return true;
@@ -102,11 +93,11 @@
     
     bool RenderPageCustom::UpdateAttr(const std::string &ref, std::vector<std::pair<std::string, std::string>> *attrs) {
         if (target_) {
-            std::shared_ptr<std::map<std::string, std::string>> managedAttrs = std::make_shared<std::map<std::string, std::string>>();
+            std::map<std::string, std::string>* attrsMap = new std::map<std::string, std::string>();
             for (auto& p : *attrs) {
-                (*managedAttrs)[std::move(p.first)] = std::move(p.second);
+                (*attrsMap)[std::move(p.first)] = std::move(p.second);
             }
-            target_->updateAttributes(page_id_, ref, managedAttrs);
+            target_->updateAttributes(page_id_, ref, attrsMap);
         }
         delete attrs;
         return true;
diff --git a/weex_core/Source/core/render/target/render_target.h b/weex_core/Source/core/render/target/render_target.h
index 81f7fc4..6b89455 100644
--- a/weex_core/Source/core/render/target/render_target.h
+++ b/weex_core/Source/core/render/target/render_target.h
@@ -56,23 +56,23 @@
         virtual void deletePage(const std::string& page) = 0;
 
         virtual void createBody(const std::string& page, const std::string& ref, const std::string& type,
-                                std::shared_ptr<std::map<std::string, std::string>> styles,
-                                std::shared_ptr<std::map<std::string, std::string>> attrs,
-                                std::shared_ptr<std::set<std::string>> events) = 0;
+                                std::map<std::string, std::string>* styles,
+                                std::map<std::string, std::string>* attrs,
+                                std::set<std::string>* events) = 0;
 
         virtual void addElement(const std::string& page, const std::string& ref, const std::string& type,
                                 const std::string &parent_ref, int index,
-                                std::shared_ptr<std::map<std::string, std::string>> styles,
-                                std::shared_ptr<std::map<std::string, std::string>> attrs,
-                                std::shared_ptr<std::set<std::string>> events) = 0;
+                                std::map<std::string, std::string>* styles,
+                                std::map<std::string, std::string>* attrs,
+                                std::set<std::string>* events) = 0;
 
         virtual void removeElement(const std::string& page, const std::string &ref) = 0;
 
         virtual void moveElement(const std::string& page, const std::string &ref, const std::string &parent_ref, int index) = 0;
 
-        virtual void updateStyles(const std::string& page, const std::string &ref, std::shared_ptr<std::map<std::string, std::string>> styles) = 0;
+        virtual void updateStyles(const std::string& page, const std::string &ref, std::map<std::string, std::string>* styles) = 0;
 
-        virtual void updateAttributes(const std::string& page, const std::string &ref, std::shared_ptr<std::map<std::string, std::string>> attrs) = 0;
+        virtual void updateAttributes(const std::string& page, const std::string &ref, std::map<std::string, std::string>* attrs) = 0;
 
         virtual void addEvent(const std::string& page, const std::string &ref, const std::string &event) = 0;
 
diff --git a/weex_core/Source/js_runtime/CMakeLists.txt b/weex_core/Source/js_runtime/CMakeLists.txt
index 42bd160..b62b59b 100644
--- a/weex_core/Source/js_runtime/CMakeLists.txt
+++ b/weex_core/Source/js_runtime/CMakeLists.txt
@@ -86,8 +86,7 @@
 
 include_directories(${WEEX_CORE_SOURCE_DIR})
 include_directories(${WEEX_CORE_SOURCE_DIR}/include)
-include_directories(${WEEX_CORE_SOURCE_DIR}/include/JavaScriptCore)
-include_directories(${WEEX_CORE_SOURCE_DIR}/include/JavaScriptCore/ForwardingHeaders)
+include_directories(${WEEX_CORE_SOURCE_DIR}/include/JSCHeaderNew)
 
 
 
@@ -169,6 +168,8 @@
         ${WEEX_CORE_SOURCE_DIR}/android/jsengine/object/args.cpp
         ${WEEX_CORE_SOURCE_DIR}/android/jsengine/object/weex_env.h
         ${WEEX_CORE_SOURCE_DIR}/android/jsengine/object/weex_env.cpp
+        ${WEEX_CORE_SOURCE_DIR}/android/jsengine/object/js_action.h
+        ${WEEX_CORE_SOURCE_DIR}/android/jsengine/object/js_action.cpp
 
         weex/task/impl/init_framework_task.cpp
         weex/task/impl/create_app_context_task.cpp
@@ -182,6 +183,7 @@
         weex/task/impl/exe_js_services_task.cpp
         weex/task/impl/exe_js_on_instance_task.cpp
         weex/task/impl/exe_js_task.cpp
+        weex/task/impl/js_action_task.cpp
         weex/task/impl/take_heap_snapshot.cpp
         weex/task/impl/native_timer_task.cpp
         weex/task/impl/update_init_framework_params_task.cpp
@@ -212,10 +214,6 @@
 weexbase
 weexipc
 wson
-#c++_shared
-JavaScriptCore
-WTF
-#jsc
 log
 z
 -lc
@@ -223,6 +221,20 @@
 -pthread
 )
 
+if (DEFINED BUILD_RUNTIME_API)
+    set(${WEEXJSSERVER_NAME}_LIBRARIES
+        ${${WEEXJSSERVER_NAME}_LIBRARIES}
+        c++_shared
+        jsc
+    )
+else()
+    set(${WEEXJSSERVER_NAME}_LIBRARIES
+        ${${WEEXJSSERVER_NAME}_LIBRARIES}
+        JavaScriptCore
+        WTF
+    )
+endif()
+
 add_library(${WEEXJSSERVER_NAME} SHARED
             ${${WEEXJSSERVER_NAME}_SOURCES} )
 
diff --git a/weex_core/Source/js_runtime/weex/bridge/script/script_side_in_queue.cpp b/weex_core/Source/js_runtime/weex/bridge/script/script_side_in_queue.cpp
index 2b71b9f..483eb4e 100644
--- a/weex_core/Source/js_runtime/weex/bridge/script/script_side_in_queue.cpp
+++ b/weex_core/Source/js_runtime/weex/bridge/script/script_side_in_queue.cpp
@@ -38,6 +38,7 @@
 #include "js_runtime/weex/task/impl/exe_js_task.h"
 #include "js_runtime/weex/task/impl/take_heap_snapshot.h"
 #include "js_runtime/weex/task/impl/native_timer_task.h"
+#include "js_runtime/weex/task/impl/js_action_task.h"
 
 namespace weex {
 namespace bridge {
@@ -357,6 +358,13 @@
   }
   return weexTaskQueue_;
 }
+
+int64_t ScriptSideInQueue::JsAction(long ctxContainer, int32_t jsActionType, const char *arg) {
+  WeexTask *task = new JSActionTask(ctxContainer, jsActionType, arg);
+  weexTaskQueue_->addTask(task);
+  return 0;
+}
+
 }  // namespace js
 }  // namespace bridge
 
diff --git a/weex_core/Source/js_runtime/weex/bridge/script/script_side_in_simple.cpp b/weex_core/Source/js_runtime/weex/bridge/script/script_side_in_simple.cpp
index fee2931..5a41f66 100644
--- a/weex_core/Source/js_runtime/weex/bridge/script/script_side_in_simple.cpp
+++ b/weex_core/Source/js_runtime/weex/bridge/script/script_side_in_simple.cpp
@@ -147,6 +147,9 @@
   //do nothing
 }
 
+int64_t ScriptSideInSimple::JsAction(long ctxContainer, int32_t jsActionType, const char *arg) {
+  return 0;
+}
 
 }  // namespace js
 }  // namespace bridge
diff --git a/weex_core/Source/js_runtime/weex/task/impl/js_action_task.cpp b/weex_core/Source/js_runtime/weex/task/impl/js_action_task.cpp
new file mode 100644
index 0000000..7ebaf9c
--- /dev/null
+++ b/weex_core/Source/js_runtime/weex/task/impl/js_action_task.cpp
@@ -0,0 +1,46 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+//
+// Created by 董亚运 on 2019-08-18.
+//
+
+#include "android/jsengine/object/weex_env.h"
+#include "js_action_task.h"
+JSActionTask::JSActionTask(long ctxContainer, const int32_t jsActionType, const std::string arg)
+    : WeexTask("") {
+  this->m_ctxContainer = ctxContainer;
+  this->m_js_action_type = jsActionType;
+  this->m_arg = arg;
+}
+void JSActionTask::run(WeexRuntime *runtime) {
+  JSAction *pAction = WeexEnv::getEnv()->getJSAction(this->m_ctxContainer);
+  if(pAction == nullptr) {
+    return;
+  }
+  if (pAction) {
+    if (this->m_js_action_type == static_cast<int32_t>(JSACTION::BIND)) {
+      pAction->BindFunction(m_arg.c_str());
+    } else if (this->m_js_action_type == static_cast<int32_t>(JSACTION::UNBIND)) {
+      pAction->UnBindFunction(m_arg.c_str());
+    } else if (this->m_js_action_type == static_cast<int32_t>(JSACTION::EXEJS)) {
+      pAction->EvaluateScript(m_arg.c_str());
+    }
+  }
+
+}
diff --git a/weex_core/Source/js_runtime/weex/task/impl/js_action_task.h b/weex_core/Source/js_runtime/weex/task/impl/js_action_task.h
new file mode 100644
index 0000000..8b30b6b
--- /dev/null
+++ b/weex_core/Source/js_runtime/weex/task/impl/js_action_task.h
@@ -0,0 +1,49 @@
+/**
+ * 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
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * 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.
+ */
+//
+// Created by 董亚运 on 2019-08-18.
+//
+
+#ifndef WEEX_PROJECT_JS_ACTION_TASK_H
+#define WEEX_PROJECT_JS_ACTION_TASK_H
+
+#include "js_runtime/weex/task/weex_task.h"
+
+class JSActionTask : public WeexTask {
+ public:
+  explicit JSActionTask(long ctxContainer, const int32_t jsActionType, const std::string arg);
+  void run(WeexRuntime *runtime) override;
+
+  std::string taskName() {
+    return "JSActionTask";
+  };
+
+
+  ~JSActionTask() {
+
+  }
+
+ private:
+  long m_ctxContainer;
+  int32_t m_js_action_type;
+  std::string m_arg;
+
+};
+
+#endif //WEEX_PROJECT_JS_ACTION_TASK_H
diff --git a/weex_core/Source/js_runtime/weex/utils/weex_jsc_utils.h b/weex_core/Source/js_runtime/weex/utils/weex_jsc_utils.h
index 30a87d8..a4a2701 100644
--- a/weex_core/Source/js_runtime/weex/utils/weex_jsc_utils.h
+++ b/weex_core/Source/js_runtime/weex/utils/weex_jsc_utils.h
@@ -209,6 +209,7 @@
 //    }
 
     static bool initICUEnv(bool multiProcess) {
+#ifdef INIT_JSC_PRIVATE_API
         static bool isInit = false;
         if (isInit)
             return true;
@@ -245,6 +246,10 @@
             return true;//mapIcuData(std::string(path));
         }
         return false;
+#else
+        LOGE("skip initICUEnv");
+        return true;
+#endif
     }
 
 }
diff --git a/weex_core/Source/libs/arm64-v8a/libJavaScriptCore.so b/weex_core/Source/libs/arm64-v8a/libJavaScriptCore.so
deleted file mode 100755
index 56307f0..0000000
--- a/weex_core/Source/libs/arm64-v8a/libJavaScriptCore.so
+++ /dev/null
Binary files differ
diff --git a/weex_core/Source/libs/arm64-v8a/libWTF.so b/weex_core/Source/libs/arm64-v8a/libWTF.so
deleted file mode 100755
index ce8d0bc..0000000
--- a/weex_core/Source/libs/arm64-v8a/libWTF.so
+++ /dev/null
Binary files differ
diff --git a/weex_core/Source/libs/armeabi-v7a/libJavaScriptCore.so b/weex_core/Source/libs/armeabi-v7a/libJavaScriptCore.so
deleted file mode 100755
index 2d59099..0000000
--- a/weex_core/Source/libs/armeabi-v7a/libJavaScriptCore.so
+++ /dev/null
Binary files differ
diff --git a/weex_core/Source/libs/armeabi-v7a/libWTF.so b/weex_core/Source/libs/armeabi-v7a/libWTF.so
deleted file mode 100755
index 790bef2..0000000
--- a/weex_core/Source/libs/armeabi-v7a/libWTF.so
+++ /dev/null
Binary files differ
diff --git a/weex_core/Source/libs/armeabi/libJavaScriptCore.so b/weex_core/Source/libs/armeabi/libJavaScriptCore.so
deleted file mode 100755
index 2d59099..0000000
--- a/weex_core/Source/libs/armeabi/libJavaScriptCore.so
+++ /dev/null
Binary files differ
diff --git a/weex_core/Source/libs/armeabi/libWTF.so b/weex_core/Source/libs/armeabi/libWTF.so
deleted file mode 100755
index 790bef2..0000000
--- a/weex_core/Source/libs/armeabi/libWTF.so
+++ /dev/null
Binary files differ
diff --git a/weex_core/Source/libs/x86/libJavaScriptCore.so b/weex_core/Source/libs/x86/libJavaScriptCore.so
deleted file mode 100755
index b7abc27..0000000
--- a/weex_core/Source/libs/x86/libJavaScriptCore.so
+++ /dev/null
Binary files differ
diff --git a/weex_core/Source/libs/x86/libWTF.so b/weex_core/Source/libs/x86/libWTF.so
deleted file mode 100755
index 0f4c2df..0000000
--- a/weex_core/Source/libs/x86/libWTF.so
+++ /dev/null
Binary files differ
diff --git a/weex_core/Source/third_party/json11/CMakeLists.txt b/weex_core/Source/third_party/json11/CMakeLists.txt
index 148c31f..ed876dd 100644
--- a/weex_core/Source/third_party/json11/CMakeLists.txt
+++ b/weex_core/Source/third_party/json11/CMakeLists.txt
@@ -1,3 +1,21 @@
+#
+# 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
+#
+#   http://www.apache.org/licenses/LICENSE-2.0
+#
+# 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.
+#
 cmake_minimum_required(VERSION 3.4.1)
 
 set(JSON11_LIBRARY_NAME json11)
