vue.js 源代码学习笔记 ----- codegenEvents.js

/* @flow */

const fnExpRE = /^\s*([\w$_]+|\([^)]*?\))\s*=>|^function\s*\(/
const simplePathRE = /^\s*[A-Za-z_$][\w$]*(?:\.[A-Za-z_$][\w$]*|\[‘.*?‘]|\[".*?"]|\[\d+]|\[[A-Za-z_$][\w$]*])*\s*$/

// keyCode aliases
const keyCodes = {
  esc: 27,
  tab: 9,
  enter: 13,
  space: 32,
  up: 38,
  left: 37,
  right: 39,
  down: 40,
  ‘delete‘: [8, 46]
}

const modifierCode = {
  stop: ‘$event.stopPropagation();‘,
  prevent: ‘$event.preventDefault();‘,
  self: ‘if($event.target !== $event.currentTarget)return;‘
}

const isMouseEventRE = /^mouse|^pointer|^(click|dblclick|contextmenu|wheel)$/
const mouseEventModifierCode = {
  ctrl: ‘if(!$event.ctrlKey)return;‘,
  shift: ‘if(!$event.shiftKey)return;‘,
  alt: ‘if(!$event.altKey)return;‘,
  meta: ‘if(!$event.metaKey)return;‘
}

export function genHandlers (events: ASTElementHandlers, native?: boolean): string {
  let res = native ? ‘nativeOn:{‘ : ‘on:{‘
  for (const name in events) {
    res += `"${name}":${genHandler(name, events[name])},`
  }
  return res.slice(0, -1) + ‘}‘
}

function genHandler (
  name: string,
  handler: ASTElementHandler | Array<ASTElementHandler>
): string {
  if (!handler) {
    return ‘function(){}‘
  } else if (Array.isArray(handler)) {
    return `[${handler.map(handler => genHandler(name, handler)).join(‘,‘)}]`
  } else if (!handler.modifiers) {
    return fnExpRE.test(handler.value) || simplePathRE.test(handler.value)
      ? handler.value
      : `function($event){${handler.value}}`
  } else {
    let code = ‘‘
    const keys = []
    const isMouseEvnet = isMouseEventRE.test(name)
    for (const key in handler.modifiers) {
      if (modifierCode[key]) {
        code += modifierCode[key]
      } else if (isMouseEvnet && mouseEventModifierCode[key]) {
        code += mouseEventModifierCode[key]
      } else {
        keys.push(key)
      }
    }
    if (keys.length) {
      code = genKeyFilter(keys) + code
    }
    const handlerCode = simplePathRE.test(handler.value)
      ? handler.value + ‘($event)‘
      : handler.value
    return ‘function($event){‘ + code + handlerCode + ‘}‘
  }
}

function genKeyFilter (keys: Array<string>): string {
  const code = keys.length === 1
    ? normalizeKeyCode(keys[0])
    : Array.prototype.concat.apply([], keys.map(normalizeKeyCode))
  if (Array.isArray(code)) {
    return `if(${code.map(c => `$event.keyCode!==${c}`).join(‘&&‘)})return;`
  } else {
    return `if($event.keyCode!==${code})return;`
  }
}

function normalizeKeyCode (key) {
  return (
    parseInt(key, 10) || // number keyCode
    keyCodes[key] || // built-in alias
    `_k(${JSON.stringify(key)})` // custom alias
  )
}
时间: 2024-11-05 14:47:10

vue.js 源代码学习笔记 ----- codegenEvents.js的相关文章

vue.js 源代码学习笔记 ----- helpers.js

/* @flow */ import { parseFilters } from './parser/filter-parser' export function baseWarn (msg: string) { console.error(`[Vue parser]: ${msg}`) } export function pluckModuleFunction ( modules: ?Array<Object>, key: string ): Array<Function> {

vue.js 源代码学习笔记 ----- fillter-parse.js

/* @flow */ export function parseFilters (exp: string): string { let inSingle = false let inDouble = false let inTemplateString = false let inRegex = false let curly = 0 let square = 0 let paren = 0 let lastFilterIndex = 0 let c, prev, i, expression,

vue.js 源代码学习笔记 ----- core lifecycle

/* @flow */ import config from '../config' import Watcher from '../observer/watcher' import { mark, measure } from '../util/perf' import { createEmptyVNode } from '../vdom/vnode' import { observerState } from '../observer/index' import { updateCompon

vue.js 源代码学习笔记 ----- keep-alives

/* @flow */ import { callHook } from 'core/instance/lifecycle' import { getFirstComponentChild } from 'core/vdom/helpers/index' const patternTypes = [String, RegExp] function matches (pattern: string | RegExp, name: string): boolean { if (typeof patt

vue.js 源代码学习笔记 ----- decoder

/* @flow */ let decoder export function decode (html: string): string { decoder = decoder || document.createElement('div') decoder.innerHTML = html return decoder.textContent }

vue.js 源代码学习笔记 ----- Dep

/* @flow */ import type Watcher from './watcher' import { remove } from '../util/index' let uid = 0 /** * A dep is an observable that can have multiple * directives subscribing to it. */ export default class Dep { static target: ?Watcher; id: number;

分享:json2.js源代码解读笔记

1. 怎样理解"json" 首先应该意识到,json是一种数据转换格式,既然是个"格式",就是个抽象的东西.它不是js对象,也不是字符串,它仅仅是一种格式,一种规定而已. 这个格式规定了如何将js对象转换成字符串.以及转换成如何的字符串--序列化 -- JSON.stringify 接口: 以及怎样将一个有效字符串转换成js对象--反序列化-- JSON.parse 接口: 2. 关于作者 json作者是 道格拉斯.克劳福德 ,是一位js大牛,写过一本<jav

【JS学习笔记】js中关于传地址的问题

我觉得初学者应该会遇到很多这样的问题 条件1.不想定义全局变量的时候 条件2.定义了外围变量却又要引用并且修改其中内容的时候 以下转一篇文章 -------------------------------------------------------------------------------------------------------------------------------------------------------- 很多人,包括我,受书本知识消化不彻底的影响,认为 J

js基础学习笔记(二)

2.1  输出内容(document.write) document.write() 可用于直接向 HTML 输出流写内容.简单的说就是直接在网页中输出内容. 第一种:输出内容用“”括起,直接输出""号内的内容. <script type="text/javascript"> document.write("I love JavaScript!"); //内容用""括起来,""里的内容直接输出.