Skip to content

Commit

Permalink
feat(weex): WIP invoke recycle-list child component with backing inst…
Browse files Browse the repository at this point in the history
…ance
  • Loading branch information
yyx990803 committed Dec 19, 2017
1 parent c1743a9 commit 801f793
Show file tree
Hide file tree
Showing 11 changed files with 59 additions and 17 deletions.
1 change: 1 addition & 0 deletions flow/compiler.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ declare type CompilerOptions = {
shouldDecodeTags?: boolean;
shouldDecodeNewlines?: boolean;
shouldDecodeNewlinesForHref?: boolean;
optimize?: boolean;

// support <recycle-list> in weex
recyclable?: boolean;
Expand Down
5 changes: 5 additions & 0 deletions src/compiler/helpers.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,12 @@ export function pluckModuleFunction<F: Function> (

export function addProp (el: ASTElement, name: string, value: string) {
(el.props || (el.props = [])).push({ name, value })
el.plain = false
}

export function addAttr (el: ASTElement, name: string, value: any) {
(el.attrs || (el.attrs = [])).push({ name, value })
el.plain = false
}

export function addDirective (
Expand All @@ -33,6 +35,7 @@ export function addDirective (
modifiers: ?ASTModifiers
) {
(el.directives || (el.directives = [])).push({ name, rawName, value, arg, modifiers })
el.plain = false
}

export function addHandler (
Expand Down Expand Up @@ -105,6 +108,8 @@ export function addHandler (
} else {
events[name] = newHandler
}

el.plain = false
}

export function getBindingAttr (
Expand Down
4 changes: 3 additions & 1 deletion src/compiler/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,9 @@ export const createCompiler = createCompilerCreator(function baseCompile (
options: CompilerOptions
): CompiledResult {
const ast = parse(template.trim(), options)
optimize(ast, options)
if (options.optimize !== false) {
optimize(ast, options)
}
const code = generate(ast, options)
return {
ast,
Expand Down
24 changes: 9 additions & 15 deletions src/core/vdom/create-component.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import VNode from './vnode'
import { resolveConstructorOptions } from 'core/instance/init'
import { queueActivatedComponent } from 'core/observer/scheduler'
import { createFunctionalComponent } from './create-functional-component'
import { renderRecyclableComponentTemplate } from 'weex/runtime/recycle-list/render-component-template'

import {
warn,
Expand Down Expand Up @@ -144,21 +145,6 @@ export function createComponent (
data = data || {}
// recycle-list optimized render function for extracting cell-slot
// template. This is essentially inline expanding instead of creating
// an actual instance.
// https://github.com/Hanks10100/weex-native-directive/tree/master/component
if (__WEEX__ && data.attrs && data.attrs['@isInRecycleList']) {
const altRender = Ctor.options['@render']
if (altRender) {
return altRender.call(
context,
context.$createElement,
data.attrs
)
}
}
// resolve constructor options in case global mixins are applied after
// component constructor creation
resolveConstructorOptions(Ctor)
Expand Down Expand Up @@ -206,6 +192,14 @@ export function createComponent (
{ Ctor, propsData, listeners, tag, children },
asyncFactory
)
// Weex specific: invoke recycle-list optimized @render function for
// extracting cell-slot template.
// https://github.com/Hanks10100/weex-native-directive/tree/master/component
if (__WEEX__ && data.attrs && ('@inRecycleList' in data.attrs)) {
return renderRecyclableComponentTemplate(vnode)
}
return vnode
}
Expand Down
2 changes: 2 additions & 0 deletions src/platforms/weex/compiler/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,8 @@ export function compile (
// generate @render function for <recycle-list>
if (options && generateAltRender) {
options.recyclable = true
// disable static optimizations
options.optimize = false
const { render } = compiler.compile(template, options)
result['@render'] = render
}
Expand Down
12 changes: 12 additions & 0 deletions src/platforms/weex/compiler/modules/recycle-list/component.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
/* @flow */

import { addAttr } from 'compiler/helpers'
import { RECYCLE_LIST_MARKER } from 'weex/util/index'

// mark components as inside recycle-list so that we know we need to invoke
// their special @render function instead of render in create-component.js
export function postTransformComponent (el: ASTElement, options: CompilerOptions) {
if (!options.isReservedTag(el.tag) && el.tag !== 'cell-slot') {
addAttr(el, RECYCLE_LIST_MARKER, true)
}
}
2 changes: 2 additions & 0 deletions src/platforms/weex/compiler/modules/recycle-list/index.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
/* @flow */

import { postTransformComponent } from './component'
import { postTransformText } from './text'
import { preTransformVBind } from './v-bind'
import { preTransformVIf } from './v-if'
Expand Down Expand Up @@ -32,6 +33,7 @@ function transformNode (el: ASTElement, options: CompilerOptions) {

function postTransformNode (el: ASTElement, options: CompilerOptions) {
if (shouldCompile(el, options)) {
postTransformComponent(el, options)
// <text>: transform children text into value attr
if (el.tag === 'text') {
postTransformText(el, options)
Expand Down
1 change: 0 additions & 1 deletion src/platforms/weex/compiler/modules/recycle-list/text.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,5 @@ export function postTransformText (el: ASTElement, options: CompilerOptions) {
if (el.children.length) {
addAttr(el, 'value', genText(el.children[0]))
el.children = []
el.plain = false
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
/* @flow */

import { RECYCLE_LIST_MARKER } from 'weex/util/index'
import { createComponentInstanceForVnode } from 'core/vdom/create-component'

export function isRecyclableComponent (vnode: VNodeWithData): boolean {
return vnode.data.attrs && (RECYCLE_LIST_MARKER in vnode.data.attrs)
}

export function renderRecyclableComponentTemplate (vnode: VNodeWithData): VNode {
// TODO:
// 1. adding @isComponentRoot / @componentProps to the root node
// 2. proper error handling
delete vnode.data.attrs[RECYCLE_LIST_MARKER]
const instance = createComponentInstanceForVnode(vnode)
return instance.$options['@render'].call(instance)
}
6 changes: 6 additions & 0 deletions src/platforms/weex/runtime/recycle-list/virtual-component.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
// import {
// // id, 'lifecycle', hookname, fn
// // https://github.com/Hanks10100/weex-native-directive/tree/master/component
// registerComponentHook,
// updateComponentData
// } from '../util/index'
2 changes: 2 additions & 0 deletions src/platforms/weex/util/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ declare var document: Object;
import { makeMap } from 'shared/util'
import { warn } from 'core/util/index'

export const RECYCLE_LIST_MARKER = '@inRecycleList'

export const isReservedTag = makeMap(
'template,script,style,element,content,slot,link,meta,svg,view,' +
'a,div,img,image,text,span,input,switch,textarea,spinner,select,' +
Expand Down

0 comments on commit 801f793

Please sign in to comment.