@@ -4,6 +4,7 @@ import VNode from './vnode'
4
4
import { createElement } from './create-element'
5
5
import { resolveInject } from '../instance/inject'
6
6
import { resolveSlots } from '../instance/render-helpers/resolve-slots'
7
+ import { installRenderHelpers } from '../instance/render-helpers/index'
7
8
8
9
import {
9
10
isDef ,
@@ -12,15 +13,43 @@ import {
12
13
validateProp
13
14
} from '../util/index'
14
15
16
+ function FunctionalRenderContext (
17
+ data ,
18
+ props ,
19
+ children ,
20
+ parent ,
21
+ Ctor
22
+ ) {
23
+ const options = Ctor . options
24
+ this . data = data
25
+ this . props = props
26
+ this . children = children
27
+ this . parent = parent
28
+ this . listeners = data . on || emptyObject
29
+ this . injections = resolveInject ( options . inject , parent )
30
+ this . slots = ( ) => resolveSlots ( children , parent )
31
+ // support for compiled functional template
32
+ if ( options . _compiled ) {
33
+ this . constructor = Ctor
34
+ this . $options = options
35
+ this . _c = parent . _c
36
+ this . $slots = this . slots ( )
37
+ this . $scopedSlots = data . scopedSlots || emptyObject
38
+ }
39
+ }
40
+
41
+ installRenderHelpers ( FunctionalRenderContext . prototype )
42
+
15
43
export function createFunctionalComponent (
16
44
Ctor : Class < Component > ,
17
45
propsData : ?Object ,
18
46
data : VNodeData ,
19
- context : Component ,
47
+ contextVm : Component ,
20
48
children : ?Array < VNode >
21
49
) : VNode | void {
50
+ const options = Ctor . options
22
51
const props = { }
23
- const propOptions = Ctor . options . props
52
+ const propOptions = options . props
24
53
if ( isDef ( propOptions ) ) {
25
54
for ( const key in propOptions ) {
26
55
props [ key ] = validateProp ( key , propOptions , propsData || emptyObject )
@@ -31,20 +60,19 @@ export function createFunctionalComponent (
31
60
}
32
61
// ensure the createElement function in functional components
33
62
// gets a unique context - this is necessary for correct named slot check
34
- const _context = Object . create ( context )
35
- const h = ( a , b , c , d ) => createElement ( _context , a , b , c , d , true )
36
- const vnode = Ctor . options . render . call ( null , h , {
63
+ const _contextVm = Object . create ( contextVm )
64
+ const h = ( a , b , c , d ) => createElement ( _contextVm , a , b , c , d , true )
65
+ const renderContext = new FunctionalRenderContext (
37
66
data ,
38
67
props ,
39
68
children ,
40
- parent : context ,
41
- listeners : data . on || emptyObject ,
42
- injections : resolveInject ( Ctor . options . inject , context ) ,
43
- slots : ( ) => resolveSlots ( children , context )
44
- } )
69
+ contextVm ,
70
+ Ctor
71
+ )
72
+ const vnode = options . render . call ( null , h , renderContext )
45
73
if ( vnode instanceof VNode ) {
46
- vnode . functionalContext = context
47
- vnode . functionalOptions = Ctor . options
74
+ vnode . functionalContext = contextVm
75
+ vnode . functionalOptions = options
48
76
if ( data . slot ) {
49
77
( vnode . data || ( vnode . data = { } ) ) . slot = data . slot
50
78
}
1 commit comments
eshell commentedon Oct 11, 2017
Lol. The second you posted this, I just converted my dumb components to jsx based functional components ;)