1
1
import { Attributes , DOM , IFiber } from "./type"
2
2
import { isStr , LANE } from "./reconcile"
3
3
4
+ const hasOwnProperty = Object . prototype . hasOwnProperty ;
5
+
6
+ const defaultObj = { } as const ;
7
+
8
+ const jointIter = < P extends Attributes > (
9
+ aProps = defaultObj as P ,
10
+ bProps = defaultObj as P ,
11
+ callback : ( name : string , a : any , b : any ) => void
12
+ ) => {
13
+ for ( const name in aProps ) {
14
+ if ( hasOwnProperty . call ( aProps , name ) ) {
15
+ callback ( name , aProps [ name ] , bProps [ name ] ) ;
16
+ }
17
+ }
18
+ for ( const name in bProps ) {
19
+ if ( hasOwnProperty . call ( bProps , name ) && ! hasOwnProperty . call ( aProps , name ) ) {
20
+ callback ( name , undefined , bProps [ name ] ) ;
21
+ }
22
+ }
23
+ }
24
+
4
25
export const updateElement = < P extends Attributes > (
5
26
dom : DOM ,
6
27
aProps : P ,
7
28
bProps : P
8
29
) => {
9
- for ( let name in { ...aProps , ...bProps } ) {
10
- let a = aProps [ name ]
11
- let b = bProps [ name ]
12
-
30
+ jointIter ( aProps , bProps , ( name , a , b ) => {
13
31
if ( a === b || name === "children" ) {
14
32
} else if ( name === "style" && ! isStr ( b ) ) {
15
- for ( const k in { ... a , ... b } ) {
16
- if ( ! ( a && b && a [ k ] === b [ k ] ) ) {
17
- ; ( dom as any ) [ name ] [ k ] = b ?. [ k ] || ""
33
+ jointIter ( a , b , ( styleKey , aStyle , bStyle ) => {
34
+ if ( aStyle !== bStyle ) {
35
+ ; ( dom as any ) [ name ] [ styleKey ] = bStyle || ""
18
36
}
19
- }
37
+ } )
20
38
} else if ( name [ 0 ] === "o" && name [ 1 ] === "n" ) {
21
39
name = name . slice ( 2 ) . toLowerCase ( ) as Extract < keyof P , string >
22
40
if ( a ) dom . removeEventListener ( name , a )
@@ -28,7 +46,7 @@ export const updateElement = <P extends Attributes>(
28
46
} else {
29
47
dom . setAttribute ( name , b )
30
48
}
31
- }
49
+ } )
32
50
}
33
51
34
52
export const createElement = < P = Attributes > ( fiber : IFiber ) => {
0 commit comments