成人性生交大片免费看视频r_亚洲综合极品香蕉久久网_在线视频免费观看一区_亚洲精品亚洲人成人网在线播放_国产精品毛片av_久久久久国产精品www_亚洲国产一区二区三区在线播_日韩一区二区三区四区区区_亚洲精品国产无套在线观_国产免费www

主頁 > 知識庫 > HTML5錄音實踐總結(jié)(Preact)

HTML5錄音實踐總結(jié)(Preact)

熱門標簽:如何獲取地圖標注客戶 機器人外呼系統(tǒng)存在哪些能力 平?jīng)龅貓D標注位置怎么弄 電話機器人黑斑馬免費 電話機器人電銷系統(tǒng)掙話費 南昌仁和怎么申請開通400電話 只辦理400電話 高德地圖標注地點糾錯 拓展地圖標注

獲取 PCM 數(shù)據(jù)

處理 PCM 數(shù)據(jù)

Float32 轉(zhuǎn) Int16

ArrayBuffer 轉(zhuǎn) Base64

PCM 文件播放

重采樣

PCM 轉(zhuǎn) MP3

PCM 轉(zhuǎn) WAV

短時能量計算

Web Worker優(yōu)化性能

音頻存儲(IndexedDB)

WebView 開啟 WebRTC

獲取 PCM 數(shù)據(jù)

查看 DEMO

https://github.com/deepkolos/pc-pcm-wave

樣例代碼:

const mediaStream = await window.navigator.mediaDevices.getUserMedia({
    audio: {
		// sampleRate: 44100, // 采樣率 不生效需要手動重采樣
        channelCount: 1, // 聲道
        // echoCancellation: true,
        // noiseSuppression: true, // 降噪 實測效果不錯
    },
})
const audioContext = new window.AudioContext()
const inputSampleRate = audioContext.sampleRate
const mediaNode = audioContext.createMediaStreamSource(mediaStream)

if (!audioContext.createScriptProcessor) {
	audioContext.createScriptProcessor = audioContext.createJavaScriptNode
}
// 創(chuàng)建一個jsNode
const jsNode = audioContext.createScriptProcessor(4096, 1, 1)
jsNode.connect(audioContext.destination)
jsNode.onaudioprocess = (e) => {
    // e.inputBuffer.getChannelData(0) (left)
    // 雙通道通過e.inputBuffer.getChannelData(1)獲取 (right)
}
mediaNode.connect(jsNode)

簡要流程如下:

start=>start: 開始
getUserMedia=>operation: 獲取MediaStream
audioContext=>operation: 創(chuàng)建AudioContext
scriptNode=>operation: 創(chuàng)建scriptNode并關(guān)聯(lián)AudioContext
onaudioprocess=>operation: 設(shè)置onaudioprocess并處理數(shù)據(jù)
end=>end: 結(jié)束

start->getUserMedia->audioContext->scriptNode->onaudioprocess->end

停止錄制只需要把 audioContext 掛在的 node 卸載即可,然后把存儲的每一幀數(shù)據(jù)合并即可產(chǎn)出 PCM 數(shù)據(jù)

jsNode.disconnect()
mediaNode.disconnect()
jsNode.onaudioprocess = null

PCM 數(shù)據(jù)處理

通過 WebRTC 獲取的 PCM 數(shù)據(jù)格式是 Float32 的, 如果是雙通道錄音的話, 還需要增加合并通道

const leftDataList = [];
const rightDataList = [];
function onAudioProcess(event) {
  // 一幀的音頻PCM數(shù)據(jù)
  let audioBuffer = event.inputBuffer;
  leftDataList.push(audioBuffer.getChannelData(0).slice(0));
  rightDataList.push(audioBuffer.getChannelData(1).slice(0));
}

// 交叉合并左右聲道的數(shù)據(jù)
function interleaveLeftAndRight(left, right) {
  let totalLength = left.length + right.length;
  let data = new Float32Array(totalLength);
  for (let i = 0; i < left.length; i++) {
    let k = i * 2;
    data[k] = left[i];
    data[k + 1] = right[i];
  }
  return data;
}

Float32 轉(zhuǎn) Int16

const float32 = new Float32Array(1)
const int16 = Int16Array.from(
	float32.map(x => (x > 0 ? x * 0x7fff : x * 0x8000)),
)

arrayBuffer 轉(zhuǎn) Base64

注意: 在瀏覽器上有個 btoa() 函數(shù)也是可以轉(zhuǎn)換為 Base64 但是輸入?yún)?shù)必須為字符串, 如果傳遞 buffer 參數(shù)會先被 toString() 然后再 Base64 , 使用 ffplay 播放反序列化的 Base64 , 會比較刺耳

使用 base64-arraybuffer 即可完成

import { encode } from 'base64-arraybuffer'

const float32 = new Float32Array(1)
const int16 = Int16Array.from(
	float32.map(x => (x > 0 ? x * 0x7fff : x * 0x8000)),
)
console.log(encode(int16.buffer))

驗證 Base64 是否正確, 可以在 node 下把產(chǎn)出的 Base64 轉(zhuǎn)換為 Int16 的 PCM 文件, 然后使用 FFPlay 播放, 看看音頻是否正常播放

PCM 文件播放

# 單通道 采樣率:16000 Int16
ffplay -f s16le -ar 16k -ac 1 test.pcm

# 雙通道 采樣率:48000 Float32
ffplay -f f32le -ar 48000 -ac 2 test.pcm

重采樣/調(diào)整采樣率

雖然 getUserMedia 參數(shù)可設(shè)置采樣率, 但是在最新Chrome也不生效, 所以需要手動做個重采樣

const mediaStream = await window.navigator.mediaDevices.getUserMedia({
    audio: {
    	// sampleRate: 44100, // 采樣率 設(shè)置不生效
        channelCount: 1, // 聲道
        // echoCancellation: true, // 減低回音
        // noiseSuppression: true, // 降噪, 實測效果不錯
    },
})

使用 wave-resampler 即可完成

import { resample } from 'wave-resampler'

const inputSampleRate =  44100
const outputSampleRate = 16000
const resampledBuffers = resample(
    // 需要onAudioProcess每一幀的buffer合并后的數(shù)組
	mergeArray(audioBuffers),
	inputSampleRate,
	outputSampleRate,
)

PCM 轉(zhuǎn) MP3

import { Mp3Encoder } from 'lamejs'

let mp3buf
const mp3Data = []
const sampleBlockSize = 576 * 10 // 工作緩存區(qū), 576的倍數(shù)
const mp3Encoder = new Mp3Encoder(1, outputSampleRate, kbps)
const samples = float32ToInt16(
  audioBuffers,
  inputSampleRate,
  outputSampleRate,
)

let remaining = samples.length
for (let i = 0; remaining >= 0; i += sampleBlockSize) {
  const left = samples.subarray(i, i + sampleBlockSize)
  mp3buf = mp3Encoder.encodeBuffer(left)
  mp3Data.push(new Int8Array(mp3buf))
  remaining -= sampleBlockSize
}

mp3Data.push(new Int8Array(mp3Encoder.flush()))
console.log(mp3Data)

// 工具函數(shù)
function float32ToInt16(audioBuffers, inputSampleRate, outputSampleRate) {
  const float32 = resample(
    // 需要onAudioProcess每一幀的buffer合并后的數(shù)組
    mergeArray(audioBuffers),
    inputSampleRate,
    outputSampleRate,
  )
  const int16 = Int16Array.from(
    float32.map(x => (x > 0 ? x * 0x7fff : x * 0x8000)),
  )
  return int16
}

使用 lamejs 即可, 但是體積較大(160+KB), 如果沒有存儲需求可使用 WAV 格式

> ls -alh
-rwxrwxrwx 1 root root  95K  4月 22 12:45 12s.mp3*
-rwxrwxrwx 1 root root 1.1M  4月 22 12:44 12s.wav*
-rwxrwxrwx 1 root root 235K  4月 22 12:41 30s.mp3*
-rwxrwxrwx 1 root root 2.6M  4月 22 12:40 30s.wav*
-rwxrwxrwx 1 root root  63K  4月 22 12:49 8s.mp3*
-rwxrwxrwx 1 root root 689K  4月 22 12:48 8s.wav*

PCM 轉(zhuǎn) WAV

function mergeArray(list) {
  const length = list.length * list[0].length
  const data = new Float32Array(length)
  let offset = 0
  for (let i = 0; i < list.length; i++) {
    data.set(list[i], offset)
    offset += list[i].length
  }
  return data
}

function writeUTFBytes(view, offset, string) {
  var lng = string.length
  for (let i = 0; i < lng; i++) {
    view.setUint8(offset + i, string.charCodeAt(i))
  }
}

function createWavBuffer(audioData, sampleRate = 44100, channels = 1) {
  const WAV_HEAD_SIZE = 44
  const buffer = new ArrayBuffer(audioData.length * 2 + WAV_HEAD_SIZE)
  // 需要用一個view來操控buffer
  const view = new DataView(buffer)
  // 寫入wav頭部信息
  // RIFF chunk descriptor/identifier
  writeUTFBytes(view, 0, 'RIFF')
  // RIFF chunk length
  view.setUint32(4, 44 + audioData.length * 2, true)
  // RIFF type
  writeUTFBytes(view, 8, 'WAVE')
  // format chunk identifier
  // FMT sub-chunk
  writeUTFBytes(view, 12, 'fmt')
  // format chunk length
  view.setUint32(16, 16, true)
  // sample format (raw)
  view.setUint16(20, 1, true)
  // stereo (2 channels)
  view.setUint16(22, channels, true)
  // sample rate
  view.setUint32(24, sampleRate, true)
  // byte rate (sample rate * block align)
  view.setUint32(28, sampleRate * 2, true)
  // block align (channel count * bytes per sample)
  view.setUint16(32, channels * 2, true)
  // bits per sample
  view.setUint16(34, 16, true)
  // data sub-chunk
  // data chunk identifier
  writeUTFBytes(view, 36, 'data')
  // data chunk length
  view.setUint32(40, audioData.length * 2, true)

  // 寫入PCM數(shù)據(jù)
  let index = 44
  const volume = 1
  const { length } = audioData
  for (let i = 0; i < length; i++) {
    view.setInt16(index, audioData[i] * (0x7fff * volume), true)
    index += 2
  }
  return buffer
}

// 需要onAudioProcess每一幀的buffer合并后的數(shù)組
createWavBuffer(mergeArray(audioBuffers))

WAV 基本上是 PCM 加上一些音頻信息

簡單的短時能量計算

function shortTimeEnergy(audioData) {
  let sum = 0
  const energy = []
  const { length } = audioData
  for (let i = 0; i < length; i++) {
    sum += audioData[i] ** 2

    if ((i + 1) % 256 === 0) {
      energy.push(sum)
      sum = 0
    } else if (i === length - 1) {
      energy.push(sum)
    }
  }
  return energy
}

由于計算結(jié)果有會因設(shè)備的錄音增益差異較大, 計算出數(shù)據(jù)也較大, 所以使用比值簡單區(qū)分人聲和噪音

查看 DEMO

const NoiseVoiceWatershedWave = 2.3
const energy = shortTimeEnergy(e.inputBuffer.getChannelData(0).slice(0))
const avg = energy.reduce((a, b) => a + b) / energy.length

const nextState = Math.max(...energy) / avg > NoiseVoiceWatershedWave ? 'voice' : 'noise'

Web Worker 優(yōu)化性能

音頻數(shù)據(jù)數(shù)據(jù)量較大, 所以可以使用 Web Worker 進行優(yōu)化, 不卡 UI 線程

在 Webpack 項目里 Web Worker 比較簡單, 安裝 worker-loader 即可

preact.config.js

export default (config, env, helpers) => {
    config.module.rules.push({
        test: /\.worker\.js$/,
        use: { loader: 'worker-loader', options: { inline: true } },
      })
}

recorder.worker.js

self.addEventListener('message', event => {
  console.log(event.data)
  // 轉(zhuǎn)MP3/轉(zhuǎn)Base64/轉(zhuǎn)WAV等等
  const output = ''
  self.postMessage(output)
}

使用 Worker

async function toMP3(audioBuffers, inputSampleRate, outputSampleRate = 16000) {
  const { default: Worker } = await import('./recorder.worker')
  const worker = new Worker()
  // 簡單使用, 項目可以在recorder實例化的時候創(chuàng)建worker實例, 有并法需求可多個實例

  return new Promise(resolve => {
    worker.postMessage({
      audioBuffers: audioBuffers,
      inputSampleRate: inputSampleRate,
      outputSampleRate: outputSampleRate,
      type: 'mp3',
    })
    worker.onmessage = event => resolve(event.data)
  })
}

音頻的存儲

瀏覽器持久化儲存的地方有 LocalStorage 和 IndexedDB , 其中 LocalStorage 較為常用, 但是只能儲存字符串, 而 IndexedDB 可直接儲存 Blob , 所以優(yōu)先選擇 IndexedDB ,使用 LocalStorage 則需要轉(zhuǎn) Base64 體積將會更大

所以為了避免占用用戶太多空間, 所以選擇MP3格式進行存儲

> ls -alh
-rwxrwxrwx 1 root root  95K  4月 22 12:45 12s.mp3*
-rwxrwxrwx 1 root root 1.1M  4月 22 12:44 12s.wav*
-rwxrwxrwx 1 root root 235K  4月 22 12:41 30s.mp3*
-rwxrwxrwx 1 root root 2.6M  4月 22 12:40 30s.wav*
-rwxrwxrwx 1 root root  63K  4月 22 12:49 8s.mp3*
-rwxrwxrwx 1 root root 689K  4月 22 12:48 8s.wav*

IndexedDB 簡單封裝如下, 熟悉后臺的同學(xué)可以找個 ORM 庫方便數(shù)據(jù)讀寫

const indexedDB =
  window.indexedDB ||
  window.webkitIndexedDB ||
  window.mozIndexedDB ||
  window.OIndexedDB ||
  window.msIndexedDB

const IDBTransaction =
  window.IDBTransaction ||
  window.webkitIDBTransaction ||
  window.OIDBTransaction ||
  window.msIDBTransaction

const readWriteMode =
  typeof IDBTransaction.READ_WRITE === 'undefined'
    ? 'readwrite'
    : IDBTransaction.READ_WRITE

const dbVersion = 1
const storeDefault = 'mp3'

let dbLink

function initDB(store) {
  return new Promise((resolve, reject) => {
    if (dbLink) resolve(dbLink)

    // Create/open database
    const request = indexedDB.open('audio', dbVersion)

    request.onsuccess = event => {
      const db = request.result

      db.onerror = event => {
        reject(event)
      }

      if (db.version === dbVersion) resolve(db)
    }

    request.onerror = event => {
      reject(event)
    }

    // For future use. Currently only in latest Firefox versions
    request.onupgradeneeded = event => {
      dbLink = event.target.result
      const { transaction } = event.target

      if (!dbLink.objectStoreNames.contains(store)) {
        dbLink.createObjectStore(store)
      }

      transaction.oncomplete = event => {
        // Now store is available to be populated
        resolve(dbLink)
      }
    }
  })
}

export const writeIDB = async (name, blob, store = storeDefault) => {
  const db = await initDB(store)

  const transaction = db.transaction([store], readWriteMode)
  const objStore = transaction.objectStore(store)

  return new Promise((resolve, reject) => {
    const request = objStore.put(blob, name)
    request.onsuccess = event => resolve(event)
    request.onerror = event => reject(event)
    transaction.commit && transaction.commit()
  })
}

export const readIDB = async (name, store = storeDefault) => {
  const db = await initDB(store)

  const transaction = db.transaction([store], readWriteMode)
  const objStore = transaction.objectStore(store)

  return new Promise((resolve, reject) => {
    const request = objStore.get(name)
    request.onsuccess = event => resolve(event.target.result)
    request.onerror = event => reject(event)
    transaction.commit && transaction.commit()
  })
}

export const clearIDB = async (store = storeDefault) => {
  const db = await initDB(store)

  const transaction = db.transaction([store], readWriteMode)
  const objStore = transaction.objectStore(store)
  return new Promise((resolve, reject) => {
    const request = objStore.clear()
    request.onsuccess = event => resolve(event)
    request.onerror = event => reject(event)
    transaction.commit && transaction.commit()
  })
}

WebView 開啟 WebRTC

見 WebView WebRTC not working

webView.setWebChromeClient(new WebChromeClient(){
	@TargetApi(Build.VERSION_CODES.LOLLIPOP)
	@Override
	public void onPermissionRequest(final PermissionRequest request) {
		request.grant(request.getResources());
	}
});

到此這篇關(guān)于HTML5錄音實踐總結(jié)(Preact)的文章就介紹到這了,更多相關(guān)html5錄音內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持腳本之家!

標簽:遼源 漯河 青島 西藏 棗莊 新疆 永州 池州

巨人網(wǎng)絡(luò)通訊聲明:本文標題《HTML5錄音實踐總結(jié)(Preact)》,本文關(guān)鍵詞  HTML5,錄音,實踐,總結(jié),Preact,;如發(fā)現(xiàn)本文內(nèi)容存在版權(quán)問題,煩請?zhí)峁┫嚓P(guān)信息告之我們,我們將及時溝通與處理。本站內(nèi)容系統(tǒng)采集于網(wǎng)絡(luò),涉及言論、版權(quán)與本站無關(guān)。
  • 相關(guān)文章
  • 下面列出與本文章《HTML5錄音實踐總結(jié)(Preact)》相關(guān)的同類信息!
  • 本頁收集關(guān)于HTML5錄音實踐總結(jié)(Preact)的相關(guān)信息資訊供網(wǎng)民參考!
  • 推薦文章
    91超碰在线观看| 在线观看中文字幕亚洲| 北条麻妃99精品青青久久| 亚洲资源视频| 神马久久av| 久久久久久国产精品美女| 国产日韩欧美一区二区三区在线观看| 黄色正能量网站| 亚洲视频免费观看| 久久精品国产亚洲精品| 婷婷激情5月天| 美女免费观看一区二区三区| 精品久久久久久久| 中文在线а天堂av| 国产一级片免费| avove在线播放| 劲爆欧美第一页| 日韩欧美成人免费视频| 亚洲已满18点击进入在线看片| 日本高清中文字幕二区在线| 春日野结衣av| 日本蜜桃在线观看视频| 五月天激情开心网| 麻豆av观看| 成人精品一二三区| 国产高清无密码一区二区三区| 欧美精品一区二区三区视频| 亚洲激情播播| 国产色在线视频| 久久久91精品国产一区二区精品| 国产精品久久久久久久久久久久午夜片| 在线看日韩av| 中文字幕人成高视频| 亚洲自拍另类综合| 五月天婷婷视频| 88xx成人免费观看视频库| 成人香蕉社区| 男人天堂手机在线视频| 99久久婷婷国产| 欧美伦理片在线观看| 中国色在线观看另类| 欧美一区二区在线免费播放| 刘亦菲国产毛片bd| 日本成人伦理电影| 欧美系列日韩一区| 国产精华一区二区三区| 亚洲成人中文在线| 欧美香蕉爽爽人人爽| 国产精品一品二区三区的使用体验| 蜜桃网站成人| 成人性生交大免费看| 日本男人操女人| ww亚洲ww在线观看国产| 日本护士做爰视频| 91精品国产一区二区三区| 少妇高潮一区二区三区99| fc2人成共享视频在线观看| 韩国版免费三体| 色操视频在线| 超碰人人人人人人人| 17婷婷久久www| 老司机午夜性大片| 九九国产精品视频| 日韩国产一区二| 久久精品国产亚洲AV成人婷婷| 国产精品久久国产精品| 国产一区二区三区精品欧美日韩一区二区三区| 性色av一区二区咪爱| 视频国产一区二区| 精品自拍偷拍| 黄瓜视频免费观看在线观看www| 国产女主播喷水高潮网红在线| 成人黄色av网站| 国产精选在线视频拍拍拍| 亚洲插插视频| 中文字幕一区二区三区不卡| 婷婷五月综合激情| gogo高清午夜人体在线| 香蕉av福利精品导航| 日本精品在线视频| 成人欧美日韩| 天天躁日日躁aaaxxⅹ| 国内自拍视频在线播放| 欧美一区二区三区白人| 无码人妻丰满熟妇区五十路| 人人妻人人澡人人爽人人精品| 欧美做爰爽爽爽爽爽爽| 亚洲欧美一区二区三区久本道91| 欧美国产日韩在线观看成人| 黄色污污视频在线观看| 久久亚洲一区二区三区明星换脸| 亚洲成av人影院| 中文在线观看免费高清| 欧美色区777第一页| 国产美女福利视频| 视频一区在线免费观看| 亚洲天堂精品一区| 蜜桃日韩视频| 亚洲最大最好的私人影剧院| 国产精品热视频| 亚洲视频精品在线| 精品一区二区三区av| 丁香花视频在线观看| 国产欧美一区二区三区不卡高清| 国产黄色一级电影| а√最新版地址在线天堂| 97久久人人超碰caoprom欧美| 欧美视频导航| 色素色在线综合| 51精品在线观看| 亚洲制服丝袜在线播放| 视频一区视频二区视频三区高| 欧美在线观看视频免费| 国产精品电影久久久久电影网| 最好看的2019年中文视频| 大桥未久在线播放| 精品国产免费一区二区三区香蕉| 欧美成人国产一区二区| 国产电影精品久久禁18| 亚洲成人亚洲激情| 欧美日韩一区二区三区| 亚洲人成伊人成综合网小说| 你懂的视频网| 国自产拍偷拍精品啪啪一区二区| 日本道色综合久久| 亚洲免费在线视频| 狠狠操天天操夜夜操| 日韩欧美一区二| 91视频国产一区| 欧美猛男做受videos| 成人污污www网站免费丝瓜| 精品免费视频123区| 一本色道久久综合亚洲精品不卡| 精品亚洲免a| 日韩精品一区二区三区在线| 在线成人黄色| 国产小视频在线观看| 国产欧美日韩综合一区在线观看| 日韩精品福利| 亚洲成年人电影网站| av日韩一区| 久久精品国产精品青草| 欧美中文字幕在线观看视频| 亚洲精品成人少妇| 欧美日韩一区二区三区在线电影| 成年人网站免费观看| 最近2018年在线中文字幕高清| 国产精品久久久久av电视剧| 老司机很黄的视频免费| 韩国福利在线| 国产交换配乱淫视频免费| 精品久久久无码中文字幕| 国产精品免费观看在线| 99热这里只有精品首页| 国产欧美日韩在线观看视频| 亚洲国产精品热久久| 黄色一级视频网站| 国产精品第七影院| 日本成人在线网站| 亚洲美女啪啪| 中文字幕免费精品| 欧美亚洲视频一区二区| 波多野结衣在线电影| 国产777精品精品热热热一区二区| 亚洲成人天堂| 国产69精品久久久久9999人| 亚洲一二三四在线观看| 一本色道久久综合狠狠躁篇怎么玩| 美女视频黄a大片欧美| 丁香影院在线| 又紧又大又爽精品一区二区| 亚洲色图另类图片| 国产一区二区三区视频免费| 精品亚洲国内自在自线福利| 一级黄色片网站| 蜜桃av中文字幕| 无码av中文一区二区三区桃花岛| 在线免费观看av网站| 一级片手机在线观看| 中文字幕亚洲欧美日韩2019| 99欧美视频| 欧美床上激情在线观看| 图片区小说区亚洲| 国产精品电影久久久久电影网| 手机在线成人av| 超碰在线首页| 色综合久久久久久久| 国产女人高潮毛片| 国产成人免费看一级大黄| 91精品久久久久久久久久入口| 欧美一区二区在线免费观看| 在线观看成人动漫| 国产黄色片在线| 亚洲国产成人av在线| 国产精品999久久久| 制服丝袜av成人在线看| 免费黄色网址在线| 亚洲欧美中文在线视频| 免费在线稳定资源站| 久久精品青草| av每日在线更新| 中文字幕人妻无码系列第三区| 黄色免费一级视频| 欧美性开放视频| 久久久久无码精品国产| 国产精品永久| 欧美洲成人男女午夜视频| 亚洲精品在线免费观看视频| 佐佐木明希电影| 亚洲aⅴ优女av综合久久久| 欧美男人亚洲天堂| 国产一卡二卡3卡4卡四卡在线| 在线日韩网站| 无码小电影在线观看网站免费| 亚洲国产综合91精品麻豆| www.看毛片| 精品国产第一福利网站| 欧美福利第一页| 成人免费毛片播放| 亚洲电影一区二区| 国产精品久久久久久久第一福利| 性色av一区二区三区免费| 秋霞毛片久久久久久久久| 欧美理论在线| 超免费在线视频| 99精品欧美一区| 92精品国产成人观看免费| 欧洲杯半决赛直播| 国产在线精品一区二区三区| 欧美 变态 另类 人妖| а√中文在线天堂精品| 涩涩网站在线看| 九九视频免费看| 亚洲国产欧美一区二区丝袜黑人| 999精品网站| 日本xxxx裸体xxxx| 欧美日韩精品一区视频| 一卡二卡在线观看| 人妻互换一二三区激情视频| 日本二区三区视频| 亚洲高清在线观看视频| 超碰在线观看免费版| 国产精伦一区二区三区| 免费99精品国产自在在线| a毛片在线观看| 国产乱子伦三级在线播放| 精品高清一区二区三区| 欧美国产在线看| 亚洲专区一区二区三区| 中文字幕人成乱码在线观看| 韩国av免费观看| 男人天堂视频网| 久久99精品久久久久久久久久久久| 中文字幕观看在线| 日韩在线观看高清| av福利在线观看| a级片在线播放| 污污的网站在线看| 国产尤物久久久| 亚洲精品乱码久久久久久不卡| 8x8x国产| aaaaaa亚洲| 欧美黄视频在线观看| 欧美激情亚洲综合一区| 久久久久www| 精品欧美色视频网站在线观看| 日本视频中文字幕一区二区三区| y97精品国产97久久久久久| 中文字幕久久亚洲| 欧美日韩一区二区三区四区五区六区| 制服影音先锋| 久久婷婷人人澡人人喊人人爽| 国产亚洲精品久久久久久牛牛| 欧美绝顶高潮抽搐喷水合集| 久久婷婷一区| 欧美二区在线| 中文字幕在线中文字幕日亚韩一区| 免费国产自线拍一欧美视频| 女人被狂躁c到高潮| 欧洲金发美女大战黑人| 亚洲天天综合| 国产污片在线观看| 一区二区xxx| 亚洲国产精品视频| 国产系列第一页| 精品无人乱码一区二区三区| 五月婷婷激情视频| 亚洲伊人伊色伊影伊综合网| 亚洲欧美成人一区二区在线电影| 九色自拍视频| 正在播放一区二区| 国产无限制自拍| 日韩电影免费观看| 色八戒一区二区三区| 在线欧美日韩国产| av在线1区2区| 黑人巨大精品欧美一区二区奶水| 久久老司机精品视频| 欧美多人乱p欧美4p久久| 亚洲欧洲精品视频| 国产精品盗摄久久久| 五月激情丁香一区二区三区| 黑人精品一区二区三区| 欧美粗暴jizz性欧美20| 国产永久免费| 国产探花一区| 国产不卡一二三区| 国产91porn| 黑人玩欧美人三根一起进| 欧美一级视频在线播放| 中文字幕在线影院| 污污网站在线观看视频| av在线导航| 精品久久久久久久久久ntr影视| 婷婷综合久久一区二区三区| 国产乱子伦三级在线播放| 免费视频最近日韩| 99re8这里只有精品| 国产成人精品久久一区二区小说| 男人本色网站| 久久婷婷丁香| 久久久精品久久久久| 一区二区三区在线免费观看视频| 国产精品久久久久久久免费观看| 亚洲天堂av在线播放| 51精品秘密在线观看| 国产一区二区三区播放| 欧美自拍丝袜亚洲|