当前位置: 首页 > news >正文

长沙百度做网站多少钱网站建设外包发展情况

长沙百度做网站多少钱,网站建设外包发展情况,天津 交友 网站建设,wdcp 网站备份3.1 从一个外观着色器程序谈起 新建名为basic_diffuse.shader的文件#xff0c;被一个名为basic_diffuse.mat的材质文件所引用#xff0c;而basic_diffuse.mat文件则被场景中名为Sphere的game object的MeshRenderer组件所使用。 basic_diffuse.shader代码文件的内容如下所示…3.1 从一个外观着色器程序谈起 新建名为basic_diffuse.shader的文件被一个名为basic_diffuse.mat的材质文件所引用而basic_diffuse.mat文件则被场景中名为Sphere的game object的MeshRenderer组件所使用。 basic_diffuse.shader代码文件的内容如下所示。 Shader Custom/BasicDiffuse{Properties{_EmissiveColor (Emissive Color, Color) (1,1,1,1)_MainTex (Main Texture, 2D) white{}}SubShader{Tags { RenderTypeOpaque RenderTypeOpaque }LOD 200CGPROGRAM#pragma surface surf BasicDiffuse vertex:vert finalcolor:final noforwardadd#pragma debug// 指定自身的自发光颜色float4_EmissiveColor;// 指定第一层纹理的映射坐标sampler2D_MainTex;// 由顶点着色器主入口函数在调用vert函数时获取到// 由片元着色器主入口函数在调用surf函数时作为参数传入structInput{float2uv_MainTex;};// 本函数在顶点着色器主入口函数中被调用voidvert(inoutappdata_full v// appdata_full类型的参数是Unity 3D预定义的数据类型outInput o) // 由本函数返回并在顶点着色器主入口函数中用来初始//化一个v2f_surf变量{o.uv_MainTex v.texcoord.xy;}// 本函数在片元着色器主入口函数中被调用voidsurf (Input IN, // 根据传递给片元着色器主入口函数的v2f_surf类型的参数变量初始化而成inoutSurfaceOutput o) // 本函数内赋值完成后返回{o.Albedo (_EmissiveColor.rgb tex2D(_MainTex, IN.uv_MainTex).rgb);o.Alpha _EmissiveColor.a;}// 本函数在片元着色器主入口函数中被调用inline float4LightingBasicDiffuse (SurfaceOutput s, // 此变量在片元着色器入口主函数内调用surf获取到fixed3lightDir, // 光源到本片元的位置连线向量由着色器编译器展开计算生成// 计算得到此变量的代码在片元着// 色器主入口函数中fixedatten) // 光线的衰减值由着色器编译器展开计算生成// 计算得到此变量的代码在片元着色器主入口函数中{floatangle_cos max(0, dot(s.Normal, lightDir));float4col;col.rgb s.Albedo.rgb * _LightColor0.rgb * angle_cos * atten;col.a s.Alpha;returncol;}voidfinal(Input IN, SurfaceOutput o, inoutfixed4 color){}ENDCG}FallBack Diffuse} 观察效果。 3.1.1 BasicDiffuse着色器展开后的代码分析 1. BasicDiffuse着色器的生成代码原始着色器中定义的函数和变量 在每个编译完成的着色器的Inspector面板上都有一个Show generated code按钮单击Show generated code按钮后原始着色器中定义的变量和函数也会被植入生成的代码中。代码略可自行生成查看 2. BasicDiffuse着色器的生成代码顶点着色器传递给片元着色器的数据 引擎会针对在原始的外观着色器中定义的Input内容依据各种编译指示符指定的光照模型和其他参数对应生成一个v2f_surf结构体。该结构体由顶点着色器返回传递给片元着色器。 如下述代码所示 // 从顶点着色器传递给片元着色器的数据结构体 #ifndef LIGHTMAP_ON // 不使用烘焙光照贴图时的顶点着色器传递给片元着色器的数据结构体structv2f_surf{UNITY_POSITION(pos);float2pack0 : TEXCOORD0; // _MainTexhalf3worldNormal : TEXCOORD1;float3worldPos : TEXCOORD2;fixed3vlight : TEXCOORD3; // ambient/SH/vertexlightsUNITY_SHADOW_COORDS(4)#if SHADER_TARGET 30float4lmap : TEXCOORD5;#endifUNITY_VERTEX_INPUT_INSTANCE_IDUNITY_VERTEX_OUTPUT_STEREO}; #endif #ifdef LIGHTMAP_ON // 使用烘焙光照贴图时的顶点着色器传递给片元着色器的数据结构体structv2f_surf{UNITY_POSITION(pos);float2pack0 : TEXCOORD0; // _MainTexhalf3worldNormal : TEXCOORD1;float3worldPos : TEXCOORD2;float4lmap : TEXCOORD3;UNITY_SHADOW_COORDS(4)#ifdef DIRLIGHTMAP_COMBINEDfixed3tSpace0 : TEXCOORD5;fixed3tSpace1 : TEXCOORD6;fixed3tSpace2 : TEXCOORD7;#endifUNITY_VERTEX_INPUT_INSTANCE_IDUNITY_VERTEX_OUTPUT_STEREO}; #endif 3. BasicDiffuse着色器的生成代码顶点着色器入口函数 引擎会对应生成一个顶点着色器入口主函数vert_surf该函数使用一个内置的顶点格式描述结构体appdata_full作为传入参数。在把顶点变换到裁剪空间之前会用用户定义的vert函数对顶点进行操作。顶点着色器根据原始的外观着色器中各种编译指示符指定的光照模型和其他的参数在里面进行顶点变换和光照处理然后生成一个v2f_surf结构体返回。 4. BasicDiffuse着色器的生成代码片元着色器入口函数 引擎会对应生成一个片元着色器入口主函数frag_surf该函数使用顶点着色器返回的v2f_surf结构体作为传入参数。根据原始的外观着色器中各种编译指示符指定的光照模型和其他参数在里面依次调用用户定义的surf函数、LightingBasicDiffuse函数和final函数进行光照和阴影处理。 Unity 3D着色器代码的编译指示符compile directive。编译指示符的一般格式如下。 #pragma surface surfaceFunction lightModel [optionalparams] 5. SurfaceOutput结构体 SurfaceOutput结构体的定义如以下代码所示。 // 所在文件lighting.cginc代码// 所在目录CGIncludes// 从原文件第10行开始至第17行结束structSurfaceOutput{fixed3Albedo; // 物体表面的漫反射颜色fixed3Normal; // 物体表面的法线fixed3Emission;// 物体的自发光颜色halfSpecular; // 物体的镜面反射系数在[0,1]范围fixedGloss; // 物体的镜面高光亮度值fixedAlpha; // 物体的透明值}; lightModel即光照模型此模型指明了经过surfaceFunction处理过的表面片元信息之后如何利用这些片元信息进行光照计算。光照模型可以使用Unity 3D自带的光照函数如Lambert模型也可以使用自定义的光照函数。这些光照函数的命名规则是Lighting××××即如果在编译指令中指定的光照模型名为××××则定义此光照模型的光照函数名为Lighting×××× 以引擎自带的Lambert模型为例此光照模型函数则是在Lighting.cginc文件中定义的Lighting Lambert如下所示。 inline fixed4LightingLambert (SurfaceOutput s, UnityGI gi){fixed4c;c UnityLambertLight(s, gi.light);#ifdef UNITY_LIGHT_FUNCTION_APPLY_INDIRECTc.rgb s.Albedo * gi.indirect.diffuse;#endifreturnc;} 6. UnityLambertLight函数 UnityLambertLight函数的定义如下。 // 所在文件lighting.cginc代码// 所在目录CGIncludes// 从原文件第29行开始至第37行结束inline fixed4UnityLambertLight (SurfaceOutput s, UnityLight light){fixeddiff max(0, dot(s.Normal, light.dir));fixed4c;c.rgb s.Albedo * light.color * diff;c.a s.Alpha;returnc;} 7. UnityLight、UnityIndirect和UnityGI结构体的定义 UnityLight、UnityIndirect和UnityGI结构体的定义如下。 // 所在文件UnityLightingCommon.cginc代码// 所在目录CGIncludes// 从原文件第9行开始至第26行结束structUnityLight{half3color; // 直接光照光的颜色half3dir; // 直接光照的方向half ndotl; // 法线方向向量和光照方向向量的点积值此值已经不使用了故在开发中不要再用// 在开发中不要再用};structUnityIndirect{half3diffuse; // 间接光照的漫反射贡献量half3specular;// 间接光照的镜面反射贡献量};structUnityGI{UnityLight light;UnityIndirect indirect;}; 除了上述的surfaceFuntion和lightModel还可以自定义两种函数vertex:VertexFunction和finalcolor:ColorFunction。 一个外观着色器在整个渲染流水线中的执行流程如图3-3所示。 ▲图3-3 外观着色器在整个渲染流水线中的执行流程 3.1.2 外观着色器的编译指示符 外观着色器的功能性代码需要放在CGPROGRAM和ENDCG两个指令之间。 着色器代码段必须放在SubShader块中间而不能放在Pass块内编译器会将它编译到多个渲染通路render pass内。 必须使用#pragma surface指示符去指明本着色器是一个外观着色器。格式如下 #pragma surface surfaceFunction lightModel [optionalparams] ▲表3-1 外观着色器必需的编译指示符与参数 ▲ 表3-2 和Alpha混合及Alpha测试相关的编译指示符与参数 ▲ 表3-3 和自定义操作顶点与片元着色器相关的指示符与参数 ▲表3-4 和阴影操作和顶点镶嵌操作相关的指示符与参数 ▲表3-5 精简着色器代码的指示符与参数 ▲表3-6 其他杂项相关的指示符与参数 3.1.3 传给外观着色器函数的参数 传给外观着色器的输入结构通常可以包含任意着色器所需的纹理映射坐标。定义一个结构体分量去描述纹理映射坐标时该分量务必以uv开头然后后面加上分量名字如uv_diffuse、uv_bumpmap等如果是第二层纹理映射坐标则使用uv2开头其他层依此类推。 ▲表3-7 引擎内建支持的外观着色器光照函数的输入结构体的各属性分量 3.2 直接编写顶点着色器和片元着色器 通过使用Cg语言在ShaderLab的Pass代码段中在CGPROGRAM语句之后ENDCG语句之前嵌入一些着色器代码片段snippets便可以采用直接编写顶点着色器和片元着色器的实现代码这种传统的着色器编写方式去实现着色器。这种编写方式的代码结构通常如下所示。 Pass { // 此处的代码和普通的Pass的设置一样 CGPROGRAM // 本代码片段所需要的编译指示符 #pragma vertex vert // 指定顶点着色器的主入口函数主入口函数名为vert #pragma fragment frag // 指定片元着色器的主入口函数主入口函数名为frag // 具体的着色器实现代码在这里 ENDCG // 此处的代码和普通的Pass的设置一样 } 3.2.1 用Cg语言编写的包含着色器功能的代码片段 如果使用CGPROGRAM和ENDCG关键字编译器在编译代码时会自动包含HLSLSupport文件和UnityShaderVariables文件如果启用了HLSLPROGRAM和ENDHLSL语句就不会自动包含。 ▲表3-8 控制Cg代码片段的编译和优化指示符 3.2.2 声明目标渲染器 默认情况下所有着色器源代码都被编译到所有引擎能支持的渲染器中。使用#pragma only_renderers或#pragma exclude_renderers编译指示符可以明确地告诉引擎把着色器源代码编译成只能给指定渲染器执行的版本。其他没有指定的渲染器即使特性都支持也都不编译。 ▲Unity 3D支持的渲染器名称和对应的渲染接口如表3-9所示。 3.2.3 着色器的语义 着色器语言中的语义semantics用来说明在输入顶点的结构体中以及顶点着色器传递给片元着色器中的数据称为varying数据结构体中各数据成员的预期用途如说明某数据是位置信息还是法向量信息是纹理映射坐标还是雾化因子等。语义也表明这些图元数据存放的硬件资源是什么如是寄存器还是纹理缓冲区等。如代码中的POSITION、NORMAL、TAGENT、TEXCOORD0便是语义词。 1. 顶点着色器的输入语义 ▲表3-10是常见的顶点着色器中支持的输入语义其中n是一个从0到系统所支持的最大个数 语义词的使用示例说明如下所示 Pass{// 此处的代码和普通的Pass的设置一样CGPROGRAM// 本代码片段所需要的编译指示符#pragma vertex vert // 指定顶点着色器的主入口函数主入口函数名为vert#pragma fragment frag // 指定片元着色器的主入口函数主入口函数名为frag// 具体的着色器实现代码在这里ENDCG// 此处的代码和普通的Pass的设置一样}in float4modelPos: POSITION 2. 顶点着色器的输出语义 ▲表3-11 常用的顶点着色器中支持的输出语义 顶点着色器的输出数据被传入片元着色器中所以顶点着色器的输出语义通常也是片元着色器的输入语义但是语义POSITION除外。顶点着色器必须声明一个输出变量并绑定POSITION语义。 3. 片元着色器的输入语义 ▲常用的片元着色器的输入语义 POSITION语义用于顶点着色器用来指定这些位置坐标值是变换前的顶点在模型空间中的坐标。SV_Position语义则用于片元着色器用来标识经过顶点着色器变换之后的顶点坐标。 在SV_Position的情况下如果它绑定在一个从顶点着色器输出的结构体上意味着该输出的结构体包含了最终转换过的并将用于光栅器的顶点坐标。或者如果将这个标志绑定到一个输入给片元着色器的结构体它会包含一个基于屏幕空间的像素坐标。 4. 在着色器中同时使用SV Position语义和VPOS语义 下面的代码展示了如何同时使用SV_Position语义和VPOS语义。 Shader Unlit/Screen Position{Properties{_MainTex (Texture, 2D) white {}}SubShader{Pass{CGPROGRAM#pragma vertex vert#pragma fragment frag#pragma target 3.0// 只定义了使用第0层纹理坐标的语义没有定义SV_Position语义到分量中structv2f {float2uv : TEXCOORD0;};v2f vert (// 输入给顶点着色器的顶点描述结构体float4vertex : POSITION, // 顶点坐标float2uv : TEXCOORD0, // 顶点使用的第0层纹理映射坐标// 不能在顶点到片元的结构体v2f中描述只能在顶点着色器的// 主入口函数中声明为out返回out float4outpos : SV_Position// 顶点在裁剪空间的位置坐标){v2f o;o.uv uv;// 调用Unity提供的工具函数把顶点从模型空间变换到裁剪空间outpos UnityObjectToClipPos(vertex);returno;}sampler2D_MainTex;fixed4frag (v2f i, UNITY_VPOS_TYPE screenPos : VPOS) : SV_Target{//SV_Position语义所指明的裁剪空间坐标的范围是[-1,1]而VPOS//语义所指明的坐标值就是像素坐标值假如视口的高宽分别是//1024像素和768像素则VPOS坐标的取值范围就是[0,1024]、[0,768]并且是整数值screenPos.xy floor(screenPos.xy * 0.25) * 0.5;floatchecker -frac(screenPos.r screenPos.g);//若不能通过检测就直接丢弃clip(checker);fixed4c tex2D(_MainTex, i.uv);returnc;}ENDCG}}} 5. 在着色器中使用VFACE语义 当多边形正向摄像机时VFACE绑定的变量是一个正值背向摄像机时该变量是一个负值。因为VFACE语义是在shader model 3.0时引入的所以要使用VFACE语义必须使用#pragma target 3.0编译指示符。 下面的代码展示了如何在着色器中使用VFACE语义。 Shader Unlit/Face Orientation{Properties{_ColorFront (Front Color, Color) (1,0.7,0.7,1)_ColorBack (Back Color, Color) (0.7,1,0.7,1)}SubShader{Pass{Cull Off // turn off backface cullingCGPROGRAM#pragma vertex vert#pragma fragment frag#pragma target 3.0float4vert (float4vertex : POSITION) : SV_Position{returnUnityObjectToClipPos(vertex);}fixed4_ColorFront;fixed4_ColorBack;fixed4frag (fixedfacing : VFACE) : SV_Target{// 依据VFACE语义变量facing的取值得到当前是正向还是背向摄像机显示不同颜色returnfacing 0 ? _ColorFront : _ColorBack;}ENDCG}}} 6. 片元着色器的输出语义 ▲表3-13是常见的片元着色器的输出语义。 在大多数情况下片元着色器将会输出一个颜色值这个颜色值通常指定为SV_Target语义。 除了以单个数值的形式返回之外片元着色器还支持以结构体的形式返回数据如下代码所示。 structfragOutput {fixed4color : SV_Target; }; fragOutput frag (v2f i) {fragOutput o;o.color fixed4(i.uv, 0, 0);returno; } 其他的语义项有SV_Target1、SV_Target2。SV_Target等同于SV_Target0大多数情况下对应于默认的帧缓冲区。 当使用多渲染目标multiple render targetsMRT技术一次性地向不止一个渲染目标render target中写入颜色数据时就需要利用SV_Target1、SV_Target2等一一对应去注明往哪个渲染目标去写入。多渲染目标在延迟渲染技术中会被普遍使用到。 3.3 在Cg代码中访问着色器属性块 Unity 3D着色器代码通过使用属性块properties block的方式声明着色器中要用到的材质属性。声明完材质属性后还需要在着色器的Cg/HLSL代码体内一一对应声明一次材质属性对应的着色器变量。 3.4 使用着色器多样体处理多种情况 每一段由编译条件控制编译与否的代码段称为着色器多样体shader variants#pragma multi_compile或者#pragma shader_feature指示符后面跟着的名字字符串称为多样体关键字variants keyword。 3.4.1 编译指示符multi_compile和shader_feature的使用方式与区别 如下所示是一个使用编译指示符定义多样体的语句。 #pragma multi_compile FANCY_STUFF_OFF FANCY_STUFF_ON 该语句将会生成两个着色器多样体一种就是启用了FANCY_STUFF_OFF另一种就是启用了FANCY_STUFF_ON。在运行时在C#语言层面调用Material类的成员函数EnableKeyword可以显式地激活其中一个着色器多样体如果没有一个多样体关键字被显式地启用那么将默认启用第一个多样体。#pragma multi_Compile指示符还可以定义多于两个的多样体关键字。 当使用完全由下画线“_”组成的多样体关键字时对应的多样体依然被编译但没有与之对应的预处理宏被定义比如以下代码。 #pragma multi_compile __ FOO_ON 使用这种匿名的方式定义多样体关键字其好处是可以节省多样体关键字的个数因为着色器编译器对多样体关键字的定义个数是有限制的。 #pragma shader_feature类似于#pragma multi_compile唯一的区别就是shader_feature指示符中声明的着色器多样体如果未被使用在构建游戏运行包game build时将不会被打包进去。 如果要在物体的材质中设置即调用Material类成员函数EnableKeyword去设置的多样体关键字用shader_feature指示符声明最好。如果要在全局范围中设置即调用Shader类静态成员函数EnableKeyword去设置的多样体关键字用multi_compile指示符声明最好。 3.4.2 多样体关键字的使用限制 当使用着色器多样体时要时刻切记Unity 3D有着只能使用256个多样体关键字的限制并且大约有60个关键字已经被内置的代码所使用了。所以在编写自定义的着色器代码时不能超出个数的限制。 3.4.3 内置的multi_compile指示符快捷使用方式 Unity 3D提供了若干快捷shortcut编译指示符可以用一个语句的方式代替需要多个编译指示符的声明引擎后台在编译着色器代码时会将其自动展开。以下是若干快捷编译指示符的作用。 ·        multi_compile_fwdbase编译指示符一次性开启所有在ForwardBase类型的渲染通路中所需的多样体这些多样体定义了不同的烘焙光照图的类型以及主要的有向平行光参与的光照计算中是否开启阴影计算。 ·         multi_compile_fwdadd编译指示符一次性开启所有在ForwardAdd类型的渲染通路中所需的多样体这些多样体将在渲染时控制操作场景中的有向光源、点光源和聚光灯光源的光照计算。 ·         multi_compile_fwdadd_fullshadows编译指示符除了处理控制操作场景中的有向光源、点光源和聚光灯光源的光照计算之外还会控制光源生成对应的实时阴影。 ·         multi_compile_fwdadd编译指示符将会根据当前选定的雾化因子对应去展开成各个不同的多样体定义。 在使用快捷编译指示符时如果想在快捷定义中同时生成的多样体中去除若干多样体可以使用skip_variants编译指示符如以下代码所示。 #pragma multi_compile_fwdadd // multi_compile_fwdadd指示符把POINT和POINT_COOKIE都开启了 // 现在不想启用这两个 #pragma skip_variants POINT POINT_COOKIE 3.5 多平台着色器代码的支持 ▲表3-14 编译指示符指定的目标渲染器和对应的宏 使用#pragma only_renderers或#pragma exclude_renderers编译指示符定义了如表3-9所示的目标渲染器后着色器编译器会根据所启用的目标渲染器定义上对应的宏。 3.6 确定着色器编译器的版本 3.6.1 和着色器编译器版本相关的宏 确定着色器使用版本的代码段如下 // 所在文件HLSLSupport.cginc代码// 所在目录CGIncludes// 从原文件第3行开始至第23行结束#ifndef HLSL_SUPPORT_INCLUDED#define HLSL_SUPPORT_INCLUDED// 根据各个宏的预定义情况确定底层使用哪个着色器编译器#if !defined(UNITY_COMPILER_CG) // 如果Cg编译器没有被指定启用!defined(UNITY_COMPILER_HLSL) // 如果HLSL编译器没有被指定启用!defined(UNITY_COMPILER_HLSL2GLSL) //HLSL转GLSL编译器没使用!defined(UNITY_COMPILER_HLSLCC)//如果HLSLCC编译器没被启用#if defined(SHADER_TARGET_SURFACE_ANALYSIS)//#define UNITY_COMPILER_CG#elif defined(SHADER_API_GLCORE) || defined(SHADER_API_GLES3)|| defined(SHADER_API_VULKAN)#define UNITY_COMPILER_HLSL#define UNITY_COMPILER_HLSLCC#elif defined(SHADER_API_D3D11) || defined(SHADER_API_D3D11_9X)|| defined(SHADER_API_D3D9) || defined(SHADER_API_XBOXONE)#define UNITY_COMPILER_HLSL#elif defined(SHADER_TARGET_GLSL) || defined(SHADER_API_WIIU)#define UNITY_COMPILER_HLSL2GLSL#else#define UNITY_COMPILER_CG#endif#endif 3.6.2 消除着色器代码中各平台的语义差异性 1.利用宏消除各平台的语义差异性 // 所在文件HLSLSupport.cginc代码// 所在目录CGIncludes// 从原文件第43行开始至第73行结束#if defined(UNITY_FRAMEBUFFER_FETCH_AVAILABLE) defined(UNITY_FRAMEBUFFER_FETCH_ENABLED) defined(UNITY_COMPILER_HLSLCC)#define SV_Target CoLoR#define SV_Target0 CoLoR0#define SV_Target1 CoLoR1#define SV_Target2 CoLoR2#define SV_Target3 CoLoR3#define COLOR VCOLOR#define COLOR0 VCOLOR0#define COLOR1 VCOLOR1#define COLOR2 VCOLOR2#define COLOR3 VCOLOR3#endif UNITY_FRAMEBUFFER_FETCH_AVAILABLE宏用来表征目标硬件平台是否实现了“帧缓冲区撷取”frame buffer fetch这一功能UNITY_FRAMEBUFFER_FETCH_ENABLED宏则表示假如功能实现是否启用它。 2. 消除SV Target和SV Depth语义在各平台的差异性 // 所在文件HLSLSupport.cginc代码// 所在目录CGIncludes// 从原文件第76行开始至第125行结束#if !defined(SV_Target)# if !defined(SHADER_API_XBOXONE)# define SV_Target COLOR# endif#endif 3.6.3 关闭可忽视的编译警告 可以使用#pragma warningdisable警告编号语句关闭一些特定的编译警告使在编译时不提示这些警告。 //屏蔽把数据类型从大范围值转为小值时发生的警告 #pragma warning (disable : 3205) 3.6.4 Unity 3D Shader的基本数据类型 1. 浮点数类型 Cg/HLSL着色器语言中有几种浮点数的实现类型float、half和fixed以及基于它们所实现的向量和矩阵类型如half3和float4x4。 ▲表3-15 Cg语言中的浮点数类型 2.整数类型         着色器语言中的整数类型通常用于循环次数计数或者用于数组索引所以在大多数平台上同一种整数类型大都能工作良好。但在不同平台中对整数类型的实现有所不同如在Direct3D 9和OpenGL ES 2.0平台下整数类型在GPU内部是用浮点数去模拟的。因此一些在C语言中常见的对整数进行移位、按位与、按位或、按位异或等位操作是不能在着色器代码中使用的。而在Direct3D 11、OpenGL ES3.0、Metal等平台上则真正地拥有整数类型可以对整型变量进行位操作。
http://www.dnsts.com.cn/news/37438.html

相关文章:

  • 如何建设招聘网站wordpress代码实现图片放大
  • wap网站制作方案北京微信网站设计报价
  • 静态网站制作wordpress模版东营新闻综合频道在线直播
  • 建网站建立展示类网站模板js
  • 建好网站后访问视频模板一键生成
  • 网站开发公司东莞光谷做网站推广价格
  • 响应式网站开发ui设计做兼职的网站
  • 网站备案号码城阳网站开发公司
  • 网站解析记录值seo自动刷外链工具
  • 做的网站不能放视频软件站长工具流量统计
  • 企业网站开发成本网页制作的常用开发工具是什么
  • 荥阳做网站推广代理销售公司如何注册
  • 网站文章页301重定向怎么做江苏省住房和城乡建设厅 官方网站
  • 营销展示型网站模板怎么自己搭建小程序
  • 罗湖网站建设公司高清视频网络服务器
  • 如何自己开个网站平台网站顶部小图标怎么做
  • 可以在公司局域网做网站吗wordpress主页制作
  • 做商城网站那个好济南网站优化推广
  • 注册网站账号审核不通过无法登陆怎么办快速域名网站备案
  • 行业网站推广外包无锡电子商城网站设计
  • 需要网站建设的人多吗什么样的网站高大上
  • 如何做自己的业务网站邯郸网站推广怎么做
  • python做网站好处织梦广告网站模板免费下载
  • 网站开发用哪种语言wordpress相册插件中文
  • 上海阔达网站建设公司泉州建站模板厂家
  • 低价网站建设策划内容浙江工程信息网
  • wordpress 多站点开启防城港网站设计公司
  • 自己如何做网站关键词排名威海网站优化公司
  • 天行健公司网站建设无锡网页制作公司
  • quiz在哪个网站做织梦网站怎么上传视频