青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

天行健 君子當自強而不息

D3D中的模板緩存(3)

8.3實例程序:平面陰影

在場景中被燈光照射的地方會產生陰影,這將使場景變的更真實。在這一部分我們將演示怎樣實現平面陰影,即在平面上的陰影(如圖8.5)。

使用這種陰影只是一種權宜之計,雖然它增強了場景的真實效果,但是這并不是現實中的陰影。

為了實現平面陰影,我們首先必須找到物體投射到平面上的陰影并進行幾何建模以便我們能夠渲染它,用一些3D數學就能很容易的實現它,然后我們用50%透明度的黑色材質來渲染描述陰影的多邊形。渲染陰影時可能出現“雙倍混合”,我們將用一小部分進行解釋,并使用模板緩存來防止雙倍混合發生。

 

8.3.1平行光陰影

圖8.6顯示了物體在平行光照射下得到的陰影。光線是從平行光源放射出的,它的方向是L,通過頂點p得到r(t) = p + tL。光線r(t)和平面n * p + d = 0 相交得到 s

An intersection point s is easily found with a ray/plane intersection test:

8.3.2點光源陰影

圖8.7顯示了物體在點光源照射下得到的陰影。點光源的位置是L。光線通過頂點p,則得到 r(t) = p + t ( pL )。光線r(t)和平面n * p + d = 0 相交得到 s 。用8.3.1同樣的方法我們可以得到s

注意:在點光源和平行光中的L是不同的。對于點光源,我們用L來表示點光源的位置。而對于平行光,我們則是用L來表示平行光的照射方向。

 

8.3.3陰影矩陣

注意圖8.6中所示的平行光,影子本質上是把物體按照燈光照射方向平行地投射到平面n*p+d=0之上。同樣的,圖8.7中所示的點光源,影子本質上是把物體按照透視畫法從光源投射到平面n*p+d=0之上。

我們能夠使用一個矩陣來表示從一個頂點p變換到平面n*p=d=0上的s的變化。而且,我們能夠用同一個矩陣來表現正交投影和透視投影。

我們用一個4D向量(nx, ny, nz, d)來表示將要用于投射陰影平面的平面等式中的各個系數。讓4D向量L=(Lx, Ly, Lz, Lw)來表示平行光的照射方向或點光源的位置。我們用w來區別:

1.假如w=0,那么L表示平行光的照射方向。

2.假如w=1 ,那么L表示點光源的位置。

假定平面的法向量已經單位化,我們讓k=(nx, ny, nz, d)*(Lx, Ly, Lz, Lw)= nxLx+nyLy+nzLz+dLw

那么我們就可得到表示點p到點s的變換矩陣,即陰影矩陣:

因為在其他地方已經被推導出來了,對于我們來說推導它并沒有重大的意義,在這里我們就不再演示推導怎樣得到這個矩陣的過程了。但是對與感興趣的讀者可以自己到網上查找相應的信息。

D3DX庫中已經給我們提供了一個建立陰影矩陣的函數。其中當w=0時表示平行光,當w=1時表示點光源:

Builds a matrix that flattens geometry into a plane.

D3DXMATRIX * D3DXMatrixShadow(
D3DXMATRIX * pOut,
CONST D3DXVECTOR4 * pLight,
CONST D3DXPLANE * pPlane
);

Parameters

pOut
[in, out] Pointer to the D3DXMATRIX structure that is the result of the operation.
pLight
[in] Pointer to a D3DXVECTOR4 structure describing the light's position.
pPlane
[in] Pointer to the source D3DXPLANE structure.

Return Values

Pointer to a D3DXMATRIX structure that flattens geometry into a plane.

Remarks

The D3DXMatrixShadow function flattens geometry into a plane, as if casting a shadow from a light.

The return value for this function is the same value returned in the pOut parameter. In this way, the D3DXMatrixShadow function can be used as a parameter for another function.

This function uses the following formula to compute the returned matrix.

P = normalize(Plane);
L = Light;
d = dot(P, L)

P.a * L.x + d P.a * L.y P.a * L.z P.a * L.w
P.b * L.x P.b * L.y + d P.b * L.z P.b * L.w
P.c * L.x P.c * L.y P.c * L.z + d P.c * L.w
P.d * L.x P.d * L.y P.d * L.z P.d * L.w + d

If the light's w-component is 0, the ray from the origin to the light represents a directional light. If it is 1, the light is a point light.

8.3.4用模板緩存防止雙倍混合

幾何學上,當我們將一個物體投影到一個平面上時,很可能會有兩個或者更多的投影三角形被重疊到一起。若我們就這樣渲染,那么有重疊三角形的地方就會被多次混合以至這些地方將會變得更黑。圖8.8就是這種情況。

使用模板緩存來解決這個問題,設置模板測試為允許像素第一次被渲染。即,當把影子像素渲染到后臺緩存時,我們同時在模板緩存中做好標記。然后,如果試圖把像素向一個已經渲染過的地方寫,那么模板測試將會失敗。這樣,我們就防止了重復寫像素也就是防止了二次融合的發生。

 

8.3.5代碼和解釋

下面的代碼就是講解影子例子。本例的相關代碼都在RenderShadow函數中。注意我們假設模板緩存都已經被清除為0了。

首先設置模板渲染狀態。將模板比較運算設為D3DCMP_EQUAL且將D3DRS_STENCILREF渲染狀態設置為0x0,因此假如在模板緩存中相應的值為0x0,那么就指定渲染陰影到后臺緩存中。

因為模板緩存是被清除為0x0的,所以我們第一次將影子像素寫入的時候總是正確的;不過因為我們設置D3DRS_STENCILPASS為D3DSTENCILOP_INCR,假如你試圖將已經寫過的像素寫入的話,這個測試將會失敗。在第一次寫入的時候模板像素已經被寫成了0x1,因此假如你再一次寫入,模板測試將會失敗。因此,我們避免了重復寫像素,也避免了二次融合。

void RenderShadow()

{

       Device->SetRenderState(D3DRS_STENCILENABLE, true);

       Device->SetRenderState(D3DRS_STENCILFUNC, D3DCMP_EQUAL);

       Device->SetRenderState(D3DRS_STENCILREF, 0x0);

       Device->SetRenderState(D3DRS_STENCILMASK, 0xffffffff);

       Device->SetRenderState(D3DRS_STENCILWRITEMASK, 0xffffffff);

       Device->SetRenderState(D3DRS_STENCILZFAIL, D3DSTENCILOP_KEEP);

       Device->SetRenderState(D3DRS_STENCILFAIL, D3DSTENCILOP_KEEP);

Device->SetRenderState(D3DRS_STENCILPASS, D3DSTENCILOP_INCR);

 

下一步,我們計算陰影變換并將它放置到場景中適當的位置。

       // compute the transformation to flatten the teapot into a shadow.

       D3DXVECTOR4 lightDirection(0.707f, -0.707f, 0.707f, 0.0f);

       D3DXPLANE groundPlane(0.0f, -1.0f, 0.0f, 0.0f);

       D3DXMATRIX S;

       D3DXMatrixShadow(&S, &lightDirection, &groundPlane);

       D3DXMATRIX T;

       D3DXMatrixTranslation(&T, TeapotPosition.x, TeapotPosition.y, TeapotPosition.z);

       D3DXMATRIX W = T * S;

Device->SetTransform(D3DTS_WORLD, &W);

 

最后,我們設置一個50%透明度的黑色材質,關閉深度測試,渲染陰影,然后開啟深度緩存同時關閉alpha混合和模板測試。我們關閉深度緩存來防止z-fighting,它是當兩個不同的表面在深度緩存中有同樣的深度值時出現的現象;深度緩存不知道那一個是在前面,此時就會產生討厭的閃動。因為陰影和地板是在同一個平面上,z-fighting很可能就會出現。通過先渲染地板然后禁用深度測試并繪制陰影,這樣我們就能夠保證陰影將繪制在地面只之上。

       Device->SetRenderState(D3DRS_ALPHABLENDENABLE, true);

       Device->SetRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA);

       Device->SetRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA);

       D3DMATERIAL9 mtrl = d3d::InitMtrl(d3d::BLACK, d3d::BLACK,

       d3d::BLACK, d3d::BLACK, 0.0f);

       mtrl.Diffuse.a = 0.5f; // 50% transparency.

       // Disable depth buffer so that z-fighting doesn't occur when we

       // render the shadow on top of the floor.

       Device->SetRenderState(D3DRS_ZENABLE, false);

       Device->SetMaterial(&mtrl);

       Device->SetTexture(0, 0);

       Teapot->DrawSubset(0);

       Device->SetRenderState(D3DRS_ZENABLE, true);

       Device->SetRenderState(D3DRS_ALPHABLENDENABLE, false);

       Device->SetRenderState(D3DRS_STENCILENABLE, false);

}//end RenderShadow()

 

主程序:

 

/**************************************************************************************
  Demonstrates shadows with stencils.  
  Use the arrow keys and the 'A' and 'S' key to navigate the scene and translate the teapot. 
 *************************************************************************************
*/

#include 
"d3dUtility.h"

#pragma warning(disable : 
4100)

class cTextureVertex
{
public:
    
float _x, _y, _z;
    
float _nx, _ny, _nz;
    
float _u, _v;

    cTextureVertex() { }

    cTextureVertex(
float x, float y, float z, 
                   
float nx, float ny, float nz,
                   
float u, float v)
    {
        _x  
= x;  _y  = y;  _z  = z;
        _nx 
= nx; _ny = ny; _nz = nz;
        _u  
= u;  _v  = v;
    }    
};

const DWORD TEXTURE_VERTEX_FVF = D3DFVF_XYZ | D3DFVF_NORMAL | D3DFVF_TEX1;

////////////////////////////////////////////////////////////////////////////////////////////////////

const int WIDTH  = 640;
const int HEIGHT = 480;

IDirect3DDevice9
*        g_d3d_device;
IDirect3DVertexBuffer9
*    g_vertex_buffer;

IDirect3DTexture9
*        g_floor_texture;
IDirect3DTexture9
*        g_wall_texture;
IDirect3DTexture9
*        g_mirror_texture;

D3DMATERIAL9    g_floor_material  
= WHITE_MATERIAL;
D3DMATERIAL9    g_wall_material   
= WHITE_MATERIAL;
D3DMATERIAL9    g_mirror_material 
= WHITE_MATERIAL;

ID3DXMesh
*        g_teapot_mesh;
D3DXVECTOR3        g_teapot_pos(
0.0f3.0f-7.5f);
D3DMATERIAL9    g_teapot_material 
= YELLOW_MATERIAL;

void render_scene();
void render_shadow();

////////////////////////////////////////////////////////////////////////////////////////////////////

bool setup()
{    
    
// make walls have low specular reflectance - 20%
    g_wall_material.Specular = WHITE * 0.2f;    

    D3DXCreateTeapot(g_d3d_device, 
&g_teapot_mesh, NULL);

    
// Create and specify geometry.  For this sample we draw a floor and a wall with a mirror on it.  
    
// We put the floor, wall, and mirror geometry in one vertex buffer.
    
//
    
//   |----|----|----|
    
//   |Wall|Mirr|Wall|
    
//   |    | or |    |
    
//   /--------------/
    
//  /   Floor      /
    
// /--------------/

    g_d3d_device
->CreateVertexBuffer(24 * sizeof(cTextureVertex), 0, TEXTURE_VERTEX_FVF, D3DPOOL_MANAGED,
                                     
&g_vertex_buffer, NULL);

    cTextureVertex
* v;

    g_vertex_buffer
->Lock(00, (void**)&v, 0);

    
// floor
    v[0= cTextureVertex(-7.5f0.0f-10.0f0.0f1.0f0.0f0.0f1.0f);
    v[
1= cTextureVertex(-7.5f0.0f,   0.0f0.0f1.0f0.0f0.0f0.0f);
    v[
2= cTextureVertex( 7.5f0.0f,   0.0f0.0f1.0f0.0f1.0f0.0f);
    
    v[
3= cTextureVertex(-7.5f0.0f-10.0f0.0f1.0f0.0f0.0f1.0f);
    v[
4= cTextureVertex( 7.5f0.0f,   0.0f0.0f1.0f0.0f1.0f0.0f);
    v[
5= cTextureVertex( 7.5f0.0f-10.0f0.0f1.0f0.0f1.0f1.0f);

    
// wall
    v[6]  = cTextureVertex(-7.5f0.0f0.0f0.0f0.0f-1.0f0.0f1.0f);
    v[
7]  = cTextureVertex(-7.5f5.0f0.0f0.0f0.0f-1.0f0.0f0.0f);
    v[
8]  = cTextureVertex(-2.5f5.0f0.0f0.0f0.0f-1.0f1.0f0.0f);
    
    v[
9]  = cTextureVertex(-7.5f0.0f0.0f0.0f0.0f-1.0f0.0f1.0f);
    v[
10= cTextureVertex(-2.5f5.0f0.0f0.0f0.0f-1.0f1.0f0.0f);
    v[
11= cTextureVertex(-2.5f0.0f0.0f0.0f0.0f-1.0f1.0f1.0f);

    
// Note: We leave gap in middle of walls for mirror

    v[
12= cTextureVertex(2.5f0.0f0.0f0.0f0.0f-1.0f0.0f1.0f);
    v[
13= cTextureVertex(2.5f5.0f0.0f0.0f0.0f-1.0f0.0f0.0f);
    v[
14= cTextureVertex(7.5f5.0f0.0f0.0f0.0f-1.0f1.0f0.0f);
    
    v[
15= cTextureVertex(2.5f0.0f0.0f0.0f0.0f-1.0f0.0f1.0f);
    v[
16= cTextureVertex(7.5f5.0f0.0f0.0f0.0f-1.0f1.0f0.0f);
    v[
17= cTextureVertex(7.5f0.0f0.0f0.0f0.0f-1.0f1.0f1.0f);

    
// mirror
    v[18= cTextureVertex(-2.5f0.0f0.0f0.0f0.0f-1.0f0.0f1.0f);
    v[
19= cTextureVertex(-2.5f5.0f0.0f0.0f0.0f-1.0f0.0f0.0f);
    v[
20= cTextureVertex( 2.5f5.0f0.0f0.0f0.0f-1.0f1.0f0.0f);
    
    v[
21= cTextureVertex(-2.5f0.0f0.0f0.0f0.0f-1.0f0.0f1.0f);
    v[
22= cTextureVertex( 2.5f5.0f0.0f0.0f0.0f-1.0f1.0f0.0f);
    v[
23= cTextureVertex( 2.5f0.0f0.0f0.0f0.0f-1.0f1.0f1.0f);

    g_vertex_buffer
->Unlock();

    
// create the texture and set filters

    D3DXCreateTextureFromFile(g_d3d_device, 
"checker.jpg",    &g_floor_texture);
    D3DXCreateTextureFromFile(g_d3d_device, 
"brick0.jpg",    &g_wall_texture);
    D3DXCreateTextureFromFile(g_d3d_device, 
"ice.bmp",        &g_mirror_texture);

    g_d3d_device
->SetSamplerState(0, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR);
    g_d3d_device
->SetSamplerState(0, D3DSAMP_MINFILTER, D3DTEXF_LINEAR);
    g_d3d_device
->SetSamplerState(0, D3DSAMP_MIPFILTER, D3DTEXF_POINT);

    
// lights

    D3DXVECTOR3 light_dir(
0.707f-0.707f0.707f);
    D3DXCOLOR color(
1.0f1.0f1.0f1.0f);
    D3DLIGHT9 light 
= init_directional_light(&light_dir, &color);

    g_d3d_device
->SetLight(0&light);
    g_d3d_device
->LightEnable(0, TRUE);

    g_d3d_device
->SetRenderState(D3DRS_NORMALIZENORMALS, TRUE);
    g_d3d_device
->SetRenderState(D3DRS_SPECULARENABLE, TRUE);

    
// set the projection matrix
    D3DXMATRIX proj;
    D3DXMatrixPerspectiveFovLH(
&proj, D3DX_PI/4.0f, (float)WIDTH/HEIGHT, 1.0f1000.0f);
    g_d3d_device
->SetTransform(D3DTS_PROJECTION, &proj);
    
    
return true;
}

///////////////////////////////////////////////////////////////////////////////////////////////////////

void cleanup()
{    
    safe_release
<IDirect3DVertexBuffer9*>(g_vertex_buffer);
    safe_release
<IDirect3DTexture9*>(g_floor_texture);
    safe_release
<IDirect3DTexture9*>(g_wall_texture);
    safe_release
<IDirect3DTexture9*>(g_mirror_texture);
    safe_release
<ID3DXMesh*>(g_teapot_mesh);    
}

///////////////////////////////////////////////////////////////////////////////////////////////////////

bool display(float time_delta)
{
    
// update the scene

    
if(GetAsyncKeyState(VK_LEFT) & 0x80000f)
        g_teapot_pos.x 
-= 3.0f * time_delta;

    
if(GetAsyncKeyState(VK_RIGHT) & 0x80000f)
        g_teapot_pos.x 
+= 3.0f * time_delta;

    
static float radius = 20.0f;

    
if(GetAsyncKeyState(VK_UP) & 0x80000f)
        radius 
-= 2.0f * time_delta;

    
if(GetAsyncKeyState(VK_DOWN) & 0x80000f)
        radius 
+= 2.0f * time_delta;

    
static float angle = (3.0f * D3DX_PI) / 2.0f;

    
if(GetAsyncKeyState('A'& 0x80000f)
        angle 
-= 0.5f * time_delta;

    
if(GetAsyncKeyState('S'& 0x80000f)
        angle 
+= 0.5f * time_delta;

    D3DXVECTOR3 position(cosf(angle) 
* radius, 3.0f, sinf(angle) * radius);
    D3DXVECTOR3 target(
0.0f0.0f0.0f);
    D3DXVECTOR3 up(
0.0f1.0f0.0f);

    D3DXMATRIX view_matrix;
    D3DXMatrixLookAtLH(
&view_matrix, &position, &target, &up);
    g_d3d_device
->SetTransform(D3DTS_VIEW, &view_matrix);

    
// render now

    g_d3d_device
->Clear(0, NULL, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER | D3DCLEAR_STENCIL, 0xff0000001.0f0);

    g_d3d_device
->BeginScene();
    render_scene();
    render_shadow();
    g_d3d_device
->EndScene();

    g_d3d_device
->Present(NULL, NULL, NULL, NULL);

    
return true;
}

///////////////////////////////////////////////////////////////////////////////////////////////////////

void render_scene()
{
    D3DXMATRIX identity_matrix;
    D3DXMatrixIdentity(
&identity_matrix);
    g_d3d_device
->SetTransform(D3DTS_WORLD, &identity_matrix);

    g_d3d_device
->SetStreamSource(0, g_vertex_buffer, 0sizeof(cTextureVertex));
    g_d3d_device
->SetFVF(TEXTURE_VERTEX_FVF);

    
// draw the floor
    g_d3d_device->SetMaterial(&g_floor_material);
    g_d3d_device
->SetTexture(0, g_floor_texture);
    g_d3d_device
->DrawPrimitive(D3DPT_TRIANGLELIST, 02);

    
// draw the walls
    g_d3d_device->SetMaterial(&g_wall_material);
    g_d3d_device
->SetTexture(0, g_wall_texture);
    g_d3d_device
->DrawPrimitive(D3DPT_TRIANGLELIST, 64);

    
// draw the mirror
    g_d3d_device->SetMaterial(&g_mirror_material);
    g_d3d_device
->SetTexture(0, g_mirror_texture);
    g_d3d_device
->DrawPrimitive(D3DPT_TRIANGLELIST, 182);

    
// draw teapot

    g_d3d_device
->SetMaterial(&g_teapot_material);
    g_d3d_device
->SetTexture(0, NULL);

    D3DXMATRIX world_matrix;
    D3DXMatrixTranslation(
&world_matrix, g_teapot_pos.x, g_teapot_pos.y, g_teapot_pos.z);
    g_d3d_device
->SetTransform(D3DTS_WORLD, &world_matrix);

    g_teapot_mesh
->DrawSubset(0);
}

///////////////////////////////////////////////////////////////////////////////////////////////////////

void render_shadow()
{    
    g_d3d_device
->SetRenderState(D3DRS_STENCILENABLE,        TRUE);
    g_d3d_device
->SetRenderState(D3DRS_STENCILFUNC,            D3DCMP_EQUAL);
    g_d3d_device
->SetRenderState(D3DRS_STENCILREF,            0x0);
    g_d3d_device
->SetRenderState(D3DRS_STENCILMASK,            0xffffffff);
    g_d3d_device
->SetRenderState(D3DRS_STENCILWRITEMASK,    0xffffffff);
    g_d3d_device
->SetRenderState(D3DRS_STENCILZFAIL,        D3DSTENCILOP_KEEP);
    g_d3d_device
->SetRenderState(D3DRS_STENCILFAIL,            D3DSTENCILOP_KEEP);
    g_d3d_device
->SetRenderState(D3DRS_STENCILPASS,            D3DSTENCILOP_INCR);    // increment to 1

    
// position shadow
    D3DXVECTOR4 light_dir(0.707f-0.707f0.707f0.0f);
    D3DXPLANE    ground_plane(
0.0f-1.0f0.0f0.0f);    // xz plane

    D3DXMATRIX shadow_matrix;
    D3DXMatrixShadow(
&shadow_matrix, &light_dir, &ground_plane);

    D3DXMATRIX tran_matrix;
    D3DXMatrixTranslation(
&tran_matrix, g_teapot_pos.x, g_teapot_pos.y, g_teapot_pos.z);

    D3DXMATRIX world_matrix 
= tran_matrix * shadow_matrix;
    g_d3d_device
->SetTransform(D3DTS_WORLD, &world_matrix);

    
// alpha blend the shadow
    g_d3d_device->SetRenderState(D3DRS_ALPHABLENDENABLE,    TRUE);
    g_d3d_device
->SetRenderState(D3DRS_SRCBLEND,            D3DBLEND_SRCALPHA);
    g_d3d_device
->SetRenderState(D3DRS_DESTBLEND,            D3DBLEND_INVSRCALPHA);

    D3DMATERIAL9 material 
= init_material(BLACK, BLACK, BLACK, BLACK, 0.0f);
    material.Diffuse.a 
= 0.5f;    // 50% transparancy

    
// disable depth buffer so that z-fighting doesn't occur when we render the shadow
    
// on top of the floor.
    g_d3d_device->SetRenderState(D3DRS_ZENABLE, FALSE);
    
    g_d3d_device
->SetMaterial(&material);
    g_d3d_device
->SetTexture(0, NULL);

    g_teapot_mesh
->DrawSubset(0);

    
// restore render states
    g_d3d_device->SetRenderState(D3DRS_ZENABLE, TRUE);
    g_d3d_device
->SetRenderState(D3DRS_ALPHABLENDENABLE, FALSE);
    g_d3d_device
->SetRenderState(D3DRS_STENCILENABLE,     FALSE);    
}

///////////////////////////////////////////////////////////////////////////////////////////////////////

LRESULT CALLBACK wnd_proc(HWND hwnd, UINT msg, WPARAM word_param, LPARAM long_param)
{
    
switch(msg)
    {
    
case WM_DESTROY:
        PostQuitMessage(
0);
        
break;

    
case WM_KEYDOWN:
        
if(word_param == VK_ESCAPE)
            DestroyWindow(hwnd);
        
break;
    }

    
return DefWindowProc(hwnd, msg, word_param, long_param);
}

///////////////////////////////////////////////////////////////////////////////////////////////////////

int WINAPI WinMain(HINSTANCE inst, HINSTANCE, PSTR cmd_line, int cmd_show)
{
    
if(! init_d3d(inst, WIDTH, HEIGHT, true, D3DDEVTYPE_HAL, &g_d3d_device))
    {
        MessageBox(NULL, 
"init_d3d() - failed."0, MB_OK);
        
return 0;
    }

    
if(! setup())
    {
        MessageBox(NULL, 
"Steup() - failed."0, MB_OK);
        
return 0;
    }

    enter_msg_loop(display);

    cleanup();
    g_d3d_device
->Release();

    
return 0;
}

 

下載源程序


posted on 2008-03-25 10:37 lovedday 閱讀(1832) 評論(0)  編輯 收藏 引用


只有注冊用戶登錄后才能發表評論。
網站導航: 博客園   IT新聞   BlogJava   博問   Chat2DB   管理


公告

導航

統計

常用鏈接

隨筆分類(178)

3D游戲編程相關鏈接

搜索

最新評論

青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            91久久精品国产91久久性色| 亚洲国产岛国毛片在线| 在线亚洲观看| 国产精品国产三级国产普通话三级 | 老色鬼精品视频在线观看播放| 午夜一区二区三视频在线观看 | 久久久久久久久岛国免费| 狠狠v欧美v日韩v亚洲ⅴ| 另类尿喷潮videofree| 久久亚洲精品欧美| 99re这里只有精品6| 一区二区欧美亚洲| 国产午夜精品久久| 欧美激情一区二区在线| 欧美午夜片在线观看| 欧美在线观看一区二区三区| 久久福利一区| 一本到高清视频免费精品| 亚洲在线观看免费| 亚洲国产毛片完整版| 夜夜夜久久久| 1024成人| 亚洲一区二区欧美日韩| 亚洲国产天堂久久综合网| 日韩亚洲欧美在线观看| 狠狠色综合色综合网络| 99视频在线精品国自产拍免费观看| 国产精品中文字幕欧美| 欧美激情精品久久久六区热门| 欧美午夜电影完整版| 免费久久99精品国产| 国产精品xnxxcom| 欧美成人免费va影院高清| 国产精品久久久久三级| 亚洲大黄网站| 国产午夜精品美女毛片视频| 亚洲精品乱码| 亚洲第一综合天堂另类专| 亚洲一二区在线| 日韩西西人体444www| 久久精品国产99国产精品| 亚洲无玛一区| 欧美经典一区二区| 欧美国产激情| 在线观看日韩av先锋影音电影院| 亚洲无线一线二线三线区别av| 亚洲国内精品在线| 国产一二三精品| 亚洲无线一线二线三线区别av| 亚洲精品三级| 久久午夜电影网| 久久综合五月| 合欧美一区二区三区| 亚洲欧美国产一区二区三区| 中文日韩欧美| 欧美色视频日本高清在线观看| 欧美成人精品高清在线播放| 一区二区三区无毛| 久久狠狠亚洲综合| 久久久久久久欧美精品| 国产精品有限公司| 亚洲欧美区自拍先锋| 欧美一区二区视频免费观看| 国产精品高潮呻吟久久av无限| 亚洲美女啪啪| 亚洲一区日本| 国产精品综合久久久| 亚洲一区二区三区在线| 性视频1819p久久| 国产日韩一区二区三区在线播放| 亚洲影视综合| 久久久久国产精品麻豆ai换脸| 国产一区二区三区高清播放| 久久爱另类一区二区小说| 久久另类ts人妖一区二区| 国内一区二区三区在线视频| 久久精品国产免费观看| 免费亚洲网站| 99精品视频免费全部在线| 欧美日韩你懂的| 亚洲影院免费观看| 久久精品一区中文字幕| 亚洲第一精品夜夜躁人人躁| 男男成人高潮片免费网站| 亚洲乱码国产乱码精品精天堂 | 亚洲午夜一区二区| 国产精品丝袜xxxxxxx| 欧美一级久久久久久久大片| 老色批av在线精品| 亚洲黄页一区| 国产精品人人做人人爽| 久久riav二区三区| 亚洲激情在线观看| 午夜精品久久久久久99热| 黑人巨大精品欧美一区二区小视频 | 亚洲二区免费| 亚洲免费视频成人| 影音先锋久久| 欧美体内she精视频| 性色av一区二区三区在线观看| 欧美成ee人免费视频| 亚洲图片在线| 亚洲第一网站| 国产伦精品免费视频| 免费成人性网站| 亚洲欧美日韩天堂| 最新国产精品拍自在线播放| 欧美一级在线视频| 99精品国产一区二区青青牛奶| 国产欧美三级| 欧美日产一区二区三区在线观看 | 一本色道久久综合亚洲精品婷婷 | 老司机免费视频一区二区三区| 亚洲精品日韩综合观看成人91| 国产精品三区www17con| 欧美大学生性色视频| 午夜欧美精品| 99在线精品视频在线观看| 欧美成年网站| 久久国产精品99国产精| 亚洲视屏在线播放| 亚洲欧洲日本一区二区三区| 国产午夜精品视频| 国产精品美女在线| 欧美视频一区二区三区…| 欧美成人亚洲成人| 久久色中文字幕| 久久精品国产91精品亚洲| 亚洲午夜未删减在线观看| 亚洲精品一区在线观看| 欧美国产欧美亚洲国产日韩mv天天看完整 | 99re8这里有精品热视频免费| 狠狠色狠狠色综合日日五| 国产精品专区第二| 国产精品视频不卡| 国产精品xnxxcom| 欧美视频日韩视频在线观看| 欧美精品一卡二卡| 欧美国产日韩亚洲一区| 免费久久精品视频| 男女视频一区二区| 美女免费视频一区| 欧美成人精品激情在线观看| 久久一区二区三区四区| 久久久久久穴| 免费欧美在线| 欧美女主播在线| 欧美日韩中文字幕| 国产精品久久久久aaaa九色| 欧美性大战久久久久久久蜜臀 | 久久久99爱| 久久久久一区| 欧美3dxxxxhd| 欧美日韩日韩| 国产麻豆一精品一av一免费| 国产精品永久入口久久久| 国产日韩欧美一区二区三区四区| 国产欧美在线视频| 精品动漫3d一区二区三区免费| 激情文学一区| 亚洲欧洲精品一区| 亚洲视频在线观看视频| 午夜精品一区二区三区在线播放| 欧美一区二区在线| 免费不卡中文字幕视频| 亚洲高清免费视频| 国产精品99久久久久久www| 亚洲欧美日韩国产精品| 久久久久久久激情视频| 欧美国产精品| 国产精品日韩久久久久| 激情欧美亚洲| 国产精品99久久久久久白浆小说| 性欧美超级视频| 免费视频久久| 一本到12不卡视频在线dvd| 性欧美8khd高清极品| 欧美承认网站| 国产欧美视频一区二区三区| 亚洲黄色影片| 久久aⅴ国产紧身牛仔裤| 欧美国产成人在线| 亚洲在线视频免费观看| 男同欧美伦乱| 国产午夜久久久久| 99在线精品免费视频九九视| 久久riav二区三区| 亚洲精品欧美日韩专区| 欧美中文字幕| 国产精品vip| 亚洲精品之草原avav久久| 久久av资源网| 夜夜爽夜夜爽精品视频| 巨胸喷奶水www久久久免费动漫| 欧美日韩在线影院| 最新日韩av| 久久综合色婷婷| 西西裸体人体做爰大胆久久久| 欧美激情女人20p| 在线不卡亚洲|