diff --git a/docs/en_communication.md b/docs/en_communication.md
new file mode 100644
index 000000000..22e66f5f5
--- /dev/null
+++ b/docs/en_communication.md
@@ -0,0 +1,307 @@
+
Component Communication
+
+Communication between [Omi](https://github.com/AlloyTeam/omi) components is very flexible, there are many options:
+
+- By declaring `data-*` on the component to pass data to child node
+- By declaring `data` on the component to pass data to child node (support complex data types mapping)
+- By declaring `childrenData` on parent component to automatically pass data to child node
+- By declaring `group-data` (support complex data types mapping)
+- It's completely object-oriented, you can easily get the object instance, then you can set the instance of the property or call the instance of the method
+
+Let's see some examples.
+
+### Communicate by `data-*`
+
+```js
+class Hello extends Omi.Component {
+ constructor(data) {
+ super(data);
+ }
+ style () {
+ return `
+ h1{
+ cursor:pointer;
+ }
+ `;
+ }
+ handleClick(target, evt){
+ alert(target.innerHTML);
+ }
+ render() {
+ return `
+
+
Hello ,{{name}}!
+
+ `;
+
+ }
+}
+
+Omi.makeHTML('Hello', Hello);
+
+class App extends Omi.Component {
+ constructor(data) {
+ super(data);
+ }
+
+ render() {
+ return `
+
+
+
+ `;
+ }
+}
+
+Omi.render(new App(),"#container");
+```
+
+Generally `data-*` is used to pass value types such as string and number. It is worth noting that, through `data-*`, received data types are string. You need to manually transform it to the number type.
+
+Normally, communicate by `data-*` is enough, but sometimes we may need to use complex data types, then we can use `data` to communicate.
+
+### Communicate by `data`
+
+As shown in the above code, name can be passed to the subcomponent by `data-name="Omi"`. The following code can also achieve the same effect.
+
+```js
+...
+class App extends Omi.Component {
+ constructor(data) {
+ super(data);
+ this.helloData = { name : 'Omi' };
+ }
+
+ render() {
+ return `
+
+
+
+ `;
+ }
+}
+
+Omi.render(new App(),"#container");
+```
+
+Use the `data` tag, it will find the property from the component instance (that is, this), this can be mounted with any complex objects. This also broke the limitations of `data-*`.
+
+Then how do we pass `data` that is in a deep depth of the instance to the Hello? No worries, `data` tag can be a complex statement:
+
+```js
+...
+class App extends Omi.Component {
+ constructor(data) {
+ super(data);
+ this.complexData ={
+ a:{
+ b:{
+ c:[
+ {
+ e:[{
+ name:'ComplexData Support1'
+ },{
+ name:'ComplexData Support2'
+ }]
+ },
+ {
+ name: 'ComplexData Support3'
+ }
+ ]
+ }
+ }
+ };
+ }
+
+ render() {
+ return `
+
+
+
+ `;
+ }
+}
+...
+```
+
+Click me for the complex data mapping
+
+### Communicate by `childrenData`
+
+```js
+...
+class App extends Omi.Component {
+ constructor(data) {
+ super(data);
+ this.childrenData = [{ name : 'Omi' } , { name : 'dntzhang' }];
+ }
+
+ render() {
+ return `
+
+
+
+
+ `;
+ }
+}
+
+Omi.render(new App(),"#container");
+```
+
+通用this.childrenData传递data给子组件,childrenData是一个数组类型,所以支持同时给多个组件传递data,与render里面的组件会一一对应上。
+
+### group-data通讯
+
+childrenData的方式可以批量传递数据给组件,但是有很多场景下data的来源不一定非要都从childrenData来,childrenData是个数组,会和组件的顺序一一对应,这就给不同传递方式的data必须全部集中的childrenData中,非常不方便。group-data专门为解决上面的痛点而生,专门是为了给一组组件批量传递data。
+
+```js
+import Hello from './hello.js';
+
+
+Omi.makeHTML('Hello', Hello);
+
+class App extends Omi.Component {
+ constructor(data) {
+ super(data);
+ this.testData = [{name: 'Omi'}, {name: 'dntzhang'}, {name: 'AlloyTeam'}];
+ }
+
+ render() {
+ return `
+
+
+
+
+
+ `;
+
+ }
+}
+
+Omi.render(new App(),"#container");
+```
+
+只需要在声明的子组件上标记group-data,就会去当前组件的instance(也就是this)下面找对应的属性,然后根据当前的位置,和对应数组的位置会一一对应起来。
+
+运行结果如下:
+![](http://images2015.cnblogs.com/blog/105416/201702/105416-20170216110701535-1698390390.png)
+
+点击这里→group-data
+
+同样group-data支持复杂数据类型的映射,需要注意的是,group-data映射的终点必须是一个数组:
+
+```js
+import Hello from './hello.js';
+
+
+Omi.makeHTML('Hello', Hello);
+
+class App extends Omi.Component {
+ constructor(data) {
+ super(data);
+ this.complexData ={
+ a:{
+ b:{
+ c:[
+ {
+ e:[{
+ name:'ComplexData Support1'
+ },{
+ name:'ComplexData Support2'
+ }]
+ },
+ {
+ name: 'ComplexData Support3'
+ }
+ ]
+ }
+ }
+ };
+ }
+
+ render() {
+ return `
+
+
+
+
+ `;
+
+ }
+}
+
+Omi.render(new App(),"#container");
+```
+
+点击这里→group-data映射复杂数据
+
+### 通过对象实例
+
+```js
+...
+class App extends Omi.Component {
+ constructor(data) {
+ super(data);
+ }
+
+ installed(){
+ this.hello.data.name = "Omi";
+ this.update()
+ }
+
+ render() {
+ return `
+
+
+
+ `;
+ }
+}
+
+Omi.render(new App(),"#container");
+```
+
+### 通过omi-id
+
+```js
+...
+class App extends Omi.Component {
+ constructor(data) {
+ super(data);
+ }
+
+ installed(){
+ Omi.get("hello").data.name = "Omi";
+ this.update()
+ }
+
+ render() {
+ return `
+
+
+
+ `;
+
+ }
+}
+
+Omi.render(new App(),"#container");
+```
+
+通过在组件上声明omi-id,在程序任何地方拿到该对象的实例。这个可以算是跨任意组件通讯神器。
+
+### 特别强调
+
+* 通过childrenData或者data方式通讯都是一锤子买卖。后续变更只能通过组件实例下的data属性去更新组件
+* 通过data-✼通讯也是一锤子买卖。后续变更只能通过组件实例下的data属性去更新组件。
+* 关于data-✼通讯也可以不是一锤子买卖,但是要设置组件实例的dataFirst为false,这样的话data-✼就会覆盖组件实例的data对应的属性
+
+关于上面的第三条也就是这样的逻辑伪代码:
+```js
+if(this.dataFirst){
+ this.data = Object.assign({},data-✼ ,this.data);
+}else{
+ this.data = Object.assign({},this.data, data-✼);
+}
+```
\ No newline at end of file