OSG 绘制Geometry使用

osgearth仿真平台之特效(4) osgearth开发一些特效波束,爆炸等特效 阅读详情

OSG的几何绘制

osg 绘制使用的OpenGL的绘制过程
image

1. OSG绘制简单线

使用简单线绘制,使用OpenGL的绘制的线的能力过程

		// create Geometry object to store all the vertices and lines primitive.
		osg::Geometry* linesGeom = new osg::Geometry();
		//创建定点数据
		osg::Vec3Array* vertices = new osg::Vec3Array(8);
		(*vertices)[0].set(-1.13704, -2.15188e-09, 0.40373);
		(*vertices)[1].set(-0.856897, -2.15188e-09, 0.531441);
		(*vertices)[2].set(-0.889855, -2.15188e-09, 0.444927);
		(*vertices)[3].set(-0.568518, -2.15188e-09, 0.40373);
		(*vertices)[4].set(-1.00933, -2.15188e-09, 0.370773);
		(*vertices)[5].set(-0.716827, -2.15188e-09, 0.292498);
		(*vertices)[6].set(-1.07936, 9.18133e-09, 0.317217);
		(*vertices)[7].set(-0.700348, 9.18133e-09, 0.362533);
		
		
		// 设置到定点数组
		linesGeom->setVertexArray(vertices);

		// set the colors as before, plus using the above
		osg::Vec4Array* colors = new osg::Vec4Array;
		colors->push_back(osg::Vec4(1.0f, 1.0f, 0.0f, 1.0f));
		linesGeom->setColorArray(colors, osg::Array::BIND_OVERALL);

		//设置线宽
		osg::LineWidth* linew = new osg::LineWidth(4);
		linesGeom->getOrCreateStateSet()->setAttributeAndModes(linew);

		// 对应上图绘制线的参数
		linesGeom->addPrimitiveSet(new osg::DrawArrays(osg::PrimitiveSet::LINE_LOOP, 0, 8));

		// add the points geometry to the geode.
		geode->addDrawable(linesGeom);

2. osg 绘制简单面

		osg::Geometry* linesGeom = new osg::Geometry();
		//创建定点数据
		osg::Vec3Array* vertices = new osg::Vec3Array(8);
		(*vertices)[0].set(-1.13704, -2.15188e-09, 0.40373);
		(*vertices)[1].set(-0.856897, -2.15188e-09, 0.531441);
		(*vertices)[2].set(-0.889855, -2.15188e-09, 0.444927);
		(*vertices)[3].set(-0.568518, -2.15188e-09, 0.40373);
		(*vertices)[4].set(-1.00933, -2.15188e-09, 0.370773);
		(*vertices)[5].set(-0.716827, -2.15188e-09, 0.292498);
		(*vertices)[6].set(-1.07936, 9.18133e-09, 0.317217);
		(*vertices)[7].set(-0.700348, 9.18133e-09, 0.362533);


		// 设置到定点数组
		linesGeom->setVertexArray(vertices);

		// set the colors as before, plus using the above
		osg::Vec4Array* colors = new osg::Vec4Array;
		colors->push_back(osg::Vec4(1.0f, 0.0f, 0.5f, 0.5f));
		linesGeom->setColorArray(colors, osg::Array::BIND_OVERALL);


		// This time we simply use primitive, and hardwire the number of coords to use
		// since we know up front,
		linesGeom->addPrimitiveSet(new osg::DrawArrays(osg::PrimitiveSet::POLYGON, 0, 8));

		// add the points geometry to the geode.
		geode->addDrawable(linesGeom);

说明不规则多边形绘会出现一些问题,osg中解决两种解决办法

  1. 自己三角化多边形,网上可以搜索一些算法
  2. 使用osg::Tessellator
  • 关键代码
		osg::ref_ptr<osgUtil::Tessellator> tscx = new osgUtil::Tessellator();
		tscx->setTessellationNormal(osg::Vec3(0.0, -1.0, 0));//面的法线向量
		tscx->setTessellationType(osgUtil::Tessellator::TESS_TYPE_GEOMETRY);
		tscx->setBoundaryOnly(false);
		tscx->setWindingType(osgUtil::Tessellator::TESS_WINDING_ODD); // the commonest tessellation is default, ODD. GE2 allows intersections of constraints to be found.
		tscx->retessellatePolygons(*(linesGeom)); // this should insert extra vertices where constraints overlap

前后对比

使用前使用后
imageimage

3. 使用纹理绘制多边形

主要能解决绘制带符号样式的面,不仅仅是简单颜色填充的面。

用到了OpenGL纹理填充的知识
参照

	osg::Geometry* linesGeom = new osg::Geometry();
		//创建定点数据
		osg::Vec3Array* vertices = new osg::Vec3Array(8);
		(*vertices)[0].set(-1.13704, -2.15188e-09, 0.40373);
		(*vertices)[1].set(-0.856897, -2.15188e-09, 0.531441);
		(*vertices)[2].set(-0.889855, -2.15188e-09, 0.444927);
		(*vertices)[3].set(-0.568518, -2.15188e-09, 0.40373);
		(*vertices)[4].set(-1.00933, -2.15188e-09, 0.370773);
		(*vertices)[5].set(-0.716827, -2.15188e-09, 0.292498);
		(*vertices)[6].set(-1.07936, 9.18133e-09, 0.317217);
		(*vertices)[7].set(-0.700348, 9.18133e-09, 0.362533);

		// 设置到定点数组
		linesGeom->setVertexArray(vertices);

		// set the colors as before, plus using the above
		osg::Vec4Array* colors = new osg::Vec4Array;
		colors->push_back(osg::Vec4(1.0f, 0.0f, 0.5f, 0.5f));
		linesGeom->setColorArray(colors, osg::Array::BIND_OVERALL);
		//
		osg::Vec3Array* normals = new osg::Vec3Array;
		normals->push_back(osg::Vec3(0.0f, -1.0f, 0.0f));
		linesGeom->setNormalArray(normals, osg::Array::BIND_OVERALL);
		//设置线宽

		// This time we simply use primitive, and hardwire the number of coords to use
		// since we know up front,
		linesGeom->addPrimitiveSet(new osg::DrawArrays(osg::PrimitiveSet::POLYGON, 0, 8));
		//贴图纹理
		osg::Texture2D* texture = new osg::Texture2D;
		texture->setWrap(osg::Texture2D::WRAP_S, osg::Texture2D::WrapMode::REPEAT);//贴图填充的方式
		texture->setWrap(osg::Texture2D::WRAP_T, osg::Texture2D::WrapMode::REPEAT);//贴图填充的方式
		texture->setDataVariance(osg::Object::DYNAMIC); // protect from being optimized away as static state.
		texture->setImage(osgDB::readRefImageFile("a-duijiangji_select.png"));

		osg::StateSet* stateset = linesGeom->getOrCreateStateSet();
		stateset->setTextureAttributeAndModes(0, texture, osg::StateAttribute::ON);
		//
		stateset->setMode(GL_BLEND, osg::StateAttribute::ON);//开启透明
		stateset->setMode(GL_DEPTH_TEST, osg::StateAttribute::OFF);//关闭深度测试
		osg::BlendFunc * aphlafunc = new osg::BlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
		stateset->setAttribute(aphlafunc, osg::StateAttribute::ON);
		osg::Program* program = new osg::Program;
		program->setName("microshader");
		//shader

		 const char *microshaderVertSource = {
			"// microshader - colors a fragment based on its position\n"
			"varying vec2 m_tex;\n"
			"void main(void)\n"
			"{\n"
			 "    m_tex = vec2(gl_Vertex.x*20.0,gl_Vertex.z*20.0);\n"//面纹理的主要方法
			"    gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;\n"
			"}\n"
		};

		 const char *microshaderFragSource = {
			"varying vec2 m_tex;\n"
			"uniform sampler2D baseTexture;                                          \n"
			"void main(void)\n"
			"{\n"
			"    gl_FragColor = texture2D( baseTexture, m_tex );\n"
			"}\n"
		};

		program->addShader(new osg::Shader(osg::Shader::VERTEX, microshaderVertSource));
		program->addShader(new osg::Shader(osg::Shader::FRAGMENT, microshaderFragSource));
		stateset->setAttributeAndModes(program, osg::StateAttribute::ON);
		// add the points geometry to the geode.
		geode->addDrawable(linesGeom);
		//
		osg::ref_ptr<osgUtil::Tessellator> tscx = new osgUtil::Tessellator();
		tscx->setTessellationNormal(osg::Vec3(0.0, -1.0, 0));//面的法线向量
		tscx->setTessellationType(osgUtil::Tessellator::TESS_TYPE_GEOMETRY);
		tscx->setBoundaryOnly(false);
		tscx->setWindingType(osgUtil::Tessellator::TESS_WINDING_ODD); // the commonest tessellation is default, ODD. GE2 allows intersections of constraints to be found.
		tscx->retessellatePolygons(*(linesGeom)); // this should insert extra vertices where constraints overlap

绘制效果

image

4. 实际案例分析

现在有一下需求,在椎体上绘制的,并投影到地面的效果,如下图

image

分析需要一下技术点:

  • osg的OverlayNode的类,
  • 椎体的定点和纹理坐标的对应生成
  1. overlayNode的关键代码
 osgSim::OverlayNode* overlayNode = new osgSim::OverlayNode(technique);
        /*每一帧都更新overlay的纹理*/
        overlayNode->setContinuousUpdate(true);
        /*设置将渲染成纹理的节点*/
        overlayNode->setOverlaySubgraph(movingModel);
        /*设置映射的高度,设成比地面低一点即可*/
        overlayNode->setOverlayBaseHeight(baseHeight-0.01);
        overlayNode->addChild(baseModel);//地面节点
  1. 椎体以及纹理关键代码
	
osg::Node* CreateZhuiti(const osg::Vec3& center, float radius, float angle)
{
	float r2 = std::sin(osg::DegreesToRadians(angle))*radius;
	float z = std::cos(osg::DegreesToRadians(angle))*radius;
	int size = 50;
	osg::Vec3Array* vertices = new osg::Vec3Array();
	osg::Vec2Array* coords = new osg::Vec2Array();
	double step = osg::PI * 2 / size;
	for (int i = 0; i < size; i++)
	{
		float x = std::sin(i*step)*r2;
		float y = std::cos(i*step)*r2;
		vertices->push_back(osg::Vec3(x, y, z) + center);
		vertices->push_back(center);
		//纹理坐标
		coords->push_back(osg::Vec2( i*1.0 / size, 1));
		coords->push_back(osg::Vec2( i*1.0 / size, 0));
	}
	vertices->push_back((*vertices)[0]);
	coords->push_back(osg::Vec2(1, 1));
	//
	osg::Geometry* linesGeom = new osg::Geometry();

	// 设置到定点数组
	linesGeom->setVertexArray(vertices);
	linesGeom->setTexCoordArray(0, coords);

	// set the colors as before, plus using the above
	osg::Vec4Array* colors = new osg::Vec4Array;
	colors->push_back(osg::Vec4(1.0f, 1.0f, 1.f, 1.f));
	linesGeom->setColorArray(colors, osg::Array::BIND_OVERALL);
	//
	osg::Texture2D* texture = new osg::Texture2D;
	texture->setDataVariance(osg::Object::DYNAMIC); // protect from being optimized away as static state.
	texture->setImage(osgDB::readRefImageFile("image12.jpg"));

	osg::StateSet* stateset = linesGeom->getOrCreateStateSet();
	stateset->setTextureAttributeAndModes(0, texture, osg::StateAttribute::ON);
	//
	stateset->setMode(GL_BLEND, osg::StateAttribute::ON);//开启透明
														 // since we know up front,
	linesGeom->addPrimitiveSet(new osg::DrawArrays(osg::PrimitiveSet::LINE_STRIP, 0, vertices->size()));

	// add the points geometry to the geode.
	osg::Geode* geode = new osg::Geode;
	geode->addDrawable(linesGeom);
	return geode;
}

最终效果

image

【OSG学习笔记】Day 6: 几何体(Geometry)的创建与自定义 今天学习下几何体的创建,也就是Geometry。学习之前我们先来回想一下右手坐标系:所以如果我们想直观的看到效果需要定义来实现几何体。 阅读详情

相关推荐

OSG读取显示原始三维数据_txt格式

面对最原始的三维数据(x,y,z),怎么是OSG显示出其模型呢? 用osg的Geometry类去实现,通过将一系列的三维数据点压入容器中,让后调用Geometry的setVertexArray方法去实现点云图的绘制: #include #include #include #include #include #include #include #include #inc

zhaohsww的专栏 6513

osggeometry例子

本例子演示了绘制不同的几何图元。 osg::PrimitiveSet::POINTS对应OpenGL中的GL_POINTS绘制单独的点 osg::PrimitiveSet::LINES对应OpenGL中的GL_LINES绘制每两点连接的线 osg::PrimitiveSet::LINE_STRIP对应OpenGL中的GL_LINE_STRIP绘制依次连接各点的线 osg::Primitiv

yungis的专栏 8822

osg中几何体绘制笔记(一)

1、复杂的场景都是由少数的基本图元构成。我们可以通过构建简单的图元来实现复杂场景。 2、osg中定义了纯基类Drawable作为几何图元的基类。从Drawable派生出9个类,其中比较重要的为Geometry和shapeDrawable。Geometry用来绘制几何体,使用比较灵活,而shapeDrawable则是封装了定义好的几何体。 3、指定输入的顶点采用哪一种或者几种基元

dingrong158的博客 1903

osg学习-1《绘制基本单元》

osg中绘制并渲染几何体主要有如下3大步骤:(1)创建各种向量数据,如顶点、纹理坐标、颜色和法线等。需要注意的是,添加顶点数据时主要按照逆时针顺序添加,以确保背面剔除(backface culling)的正确(后面还会有介绍)。(2)实例化一个几何体对象(osg:Geometry),设置顶点坐标数组、纹理坐标数组、颜色数组、法线数组、绑定方式及数据解析。(3)加入叶节点绘制并渲染。...

love code, love life. 2281

OSG Geometry几何体绘制与性能优化指南

3D图形编程中的几何体(Geometry)是构建虚拟场景的基础元素,其本质是通过顶点数据定义物体形状。现代图形管线通过VBO(顶点缓冲对象)等机制将几何数据高效传输至GPU。在OpenSceneGraph(OSG)引擎中,osg::Geometry类封装了从简单图元到复杂模型的绘制功能,支持顶点、法线、纹理坐标等属性的灵活组合。合理使用STRIP/FAN等连续图元能提升30%以上的渲染效率,而实例化渲染技术则可实现大规模场景的流畅展示。本文以OSG开发实践为例,详解几何体创建、纹理映射、LOD优化等核心技术

weixin_31102231的博客 160

osg绘制点

一、代码 #include<map> #include<vector> #include<Windows.h> #include <osgViewer\Viewer> #include <osg\Node> #include <osg\Geode> #include <osg\Group> #include <osg\PositionAttitudeTransform> #include <osgDB\

ljjjjjjjjjjj的博客 2736

【OSG学习笔记】Day 16: Geometry(几何体绘制)

本文详细介绍了OpenSceneGraph(OSG)中几何体绘制的核心类osg::Geometry及其应用。作为OSG三维渲染的基础,Geometry类负责存储顶点、颜色、纹理等几何数据,并通过PrimitiveSet指定绘制方式。文章解析了其核心特性、方法和继承关系,并通过四边形渲染示例展示了Geometry与osg::Geode、osg::PrimitiveSet的协作机制。这三者形成分层结构:Geode作为场景叶节点承载可渲染对象,Geometry管理渲染数据,PrimitiveSet定义绘制指令。完

u012739527的博客 968

OSG编程指南<十>:OSG几何体的绘制

OSG场景基本绘图类讲解、几何体的绘制、OSG预定义几何体及多边形分格化。

欧特GO 2898

OSG/Geometry 索引绑定几何体绘制实例

#include <osgViewer/Viewer> #include <osg/Node> #include <osg/Geode> #include <osg/Group> #include <osgDB/ReadFile> #include <osgDB/WriteFile> #include <osgUtil/Optimizer> #include <osgViewer/ViewerEventHand

欧特GO 1223

OSG三维渲染引擎编程学习之三十八:“第四章:OSG几何体绘制” 之 “4.3 基本几何体绘制”

OSG三维渲染引擎编程学习;第四章:OSG几何体绘制;4.3 基本几何体绘制。

LuckyHanMo的博客 889

单片机技术入门与实战:从零基础到项目开发

单片机(MCU)作为嵌入式系统的核心组件,集成了CPU、内存和各种接口电路,广泛应用于智能家居、工业控制和汽车电子等领域。其工作原理基于实时控制和低功耗设计,通过定时器、中断系统和通信接口等功能模块实现各种控制任务。在物联网和智能硬件快速发展的背景下,掌握单片机开发技术成为电子工程师的重要技能。本文以STM32和PIC系列为例,详细解析单片机的基本概念、功能模块和选型指南,并分享从入门到项目实战的系统学习方法,帮助开发者在3-6个月内快速掌握这一关键技术。

weixin_35753291的博客 652

给osg::Geometry(自己绘制的几何体)添加纹理(二)

osg给osg::Geometry(自己绘制的)添加纹理

danshiming的博客 3107

ORACLE 12C RAC 启动报错,错误代码 ORA-27300,ORA-27301,ORA-27302

非一体机,12.2 无任何补丁,2套X86服务器,1节点集群异常(数据库正常,还有会话),2节点正常工作,负载不高,硬件、空间均未检查到异常,多路径存在掉线的情况,但通过Mulitpath -ll 看又是正常的,2根私有网络,其中一根不同,sysctl中配置的稀疏模式。5、再次加成crs alert ohas等集群日志,以及根据现象和错误再次到后台sr中查找可用信息,发现有一个类似问题,12.2 RAC 无任何补丁,报同样错误,解决方案为重启两套服务器。查询MOS文档以及后台文档,排除上面指出的问题。

weixin_42344665的博客 1464

osg基本绘制-线

osg绘制图形需要定义最基本的顶点坐标数组。 绘制几何图形需要osg::Geometry这个类,他就是负责几何体的绘制。 void create4Geo() { osg::ref_ptr&lt;osg::Group&gt; root = new osg::Group; osg::ref_ptr&lt;osg::Geode&gt; geode = new osg::Geode; root-&...

wb175208的专栏 8642

使用 MATLAB/Simulink 构建一个 核电站汽轮机与发电机协调控制系统 的仿真模型

在核电机组中,汽轮机-发电机系统是将核能最终转化为电能的关键环节。与火电机组不同,核反应堆的热惯性大、功率调节慢,因此汽轮机的控制策略需与反应堆特性相匹配,实现安全、稳定、高效的能量转换。维持发电机输出功率/频率稳定(响应电网调度)调节汽轮机进汽压力(匹配一回路蒸汽供应)实现“堆-机协调控制”保障机组在启停、变负荷、甩负荷等工况下的安全性本教程将带你使用构建一个核电站汽轮机与发电机协调控制系统汽轮机调速系统(调门控制)建模发电机与电网接口建模(同步机)

xiaoheshang_123的博客 188

【零基础入门unity游戏开发——unity通用篇14】unity特性相关的知识(基于unity6开发介绍)

unity特性相关的知识(基于unity6开发介绍)

向宇的博客,专注php/web全栈 unity游戏开发,欢迎大家评论纠错 1204

OSG 渲染剖析 之 Geometry 的 VBO生成

对于一个渲染引擎的渲染过程,我们一般关心的是渲染引擎如何组织、绘制场景对象。OSG 通过状态树与渲染树对渲染节点进行分组、排序与渲染。我们先抛开OSG 事件更新与处理等宏观渲染过程,这里我们从更细的角度研究OSG 是如何将场景对象数据与状态转换成OpenGL 具体实现。 如果让你设计一个渲染引擎渲染场景对象,你通常会怎么做?我们一般都会这样做:首先设计场景对象的组织与数据封装类,将数据从文件或程...

fatcat123的博客 2037

B07:AI 时代怎么考核团队?我把 KPI 改了 5 版才找到答案

最后说一句掏心窝的话。绩效考核不是"管人"的工具,是"引导团队行为"的工具。你定什么指标,团队就会做什么行为。你定"AI 占比",团队就凑占比你定"效率提升",团队就挑软柿子你定"代码行数",团队就刷行数你定"工具使用率",团队就刷使用只有定"业务价值 + 工程质量 + 能力成长"三个维度的指标,团队才会真正关注长期价值。这套 KPI,我在我带的团队里跑了 6 个月,没有任何一个指标被"刷"出来。考核的是结果,不是过程。永远考核"创造了多少价值",永远不考核"用了多少 AI"。

刘一说的IT专栏 502

快速学习OSG(1)——小礼物OSG相册

快速学习OSG

weixin_56464957的博客 1024

实战干货|.NET9 C#上位机:多PLC并发通信+数据防丢+指令精准下发(10台设备实测+踩坑实录)

摘要:本文介绍了一个基于.NET9重构汽车零部件产线10台西门子S7-1200 PLC并发通信的工业级解决方案。针对原有系统存在的同步轮询阻塞、数据丢失、指令重复等问题,采用连接池复用、异步并发控制、超时隔离等技术,实现800ms内完成10台PLC并发采集、零丢包率、100%指令精准下发。方案通过.NET9的ThreadPool调度优化和ValueTask内存管理,将CPU占用控制在15%以内,解决了多PLC通信中的并发冲突、超时扩散等核心痛点,并提供了可直接复用的工业级代码实现。

这里只有干货:从 Modbus 通信到 MES 对接,从 YOLO 训练到工控机部署,带你搞定工业软件开发全流程。 453

【LAMMPS学习】五、LAMMPS命令(8) Pair_style 势

所有LAMMPS pair_style命令如下表所示。有些样式有加速版本。这由括号中的附加字母表示:g = GPU, i = INTEL, k = KOKKOS, o = OPENMP, t = OPT。

荷塘阅色 3016

OSG学习笔记-基本几何体的绘制(3-2)

OSG学习笔记-基本几何体的绘制

liangfei868的博客 1652

温度PID控制PLC程序

温度PID稳定控制程序,适用于欧姆龙PLC,对其他PLC也具有很大参考价值

OSG使用Geometry绘制自定义图形、更新修改绘制数据、绘制带边线图形(多 PrimitiveSet 绘制)

OSG使用Geometry绘制自定义图形、更新修改绘制数据、绘制带边线图形(多 PrimitiveSet 绘制)

qq_45523399的博客 1356

华为的C语言编程规范.pdf

华为技术有限公司内部技术规范。本规范制定了编写C语言程序的基本原则、规则和建议。从代码的清晰、简洁、可测试、安全、程序效率、可移植各个方面对C语言编程作出了具体指导。

OV9734 DATASHEET,完整规格书

OV9734完整规格书,包括电气参数,尺寸规格,寄存器配置表等

美国海军研究生学校(NPS)OSG教程学习笔记——第一课

相比OSG自带的例子程序和OSGQS中列举的示例程序,NPS的OSG教程内容更丰富一些,而且配有详细的文字说明,适合初学者作为入门教程学习。NPS教程的第一课题目是《OpenSceneGraph 几何体的绘制》,本课通过绘制一个金字塔形状的死棱锥,介绍了OSG中几个重要的类osg::Node, osg::Group, osg::Geode, osg::Geometry, osg::Drawab

OSG学习 2266

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

【OSG】Examples

1. Examples osgbillboard 这个项目很简单,就几个函数,而且很有意思。 osg::Billboard类是一个控制器,不管你怎么旋转漫游场景,它始终都会朝向摄像机。 看里面代码时,就会接触到osg的核心类了,比如 - osg::Geometry - osg::Vec3Array - osg::StateSet - osg::Group - osgViewer::Viewer - 等等 这里面的类又会引用到其他类,慢慢展开,但是大体上都是属于 OSG Core/osg 项目中的内容,也就

撬动未来的支点的专栏 4336
上一篇: OSG 使用Qt的QOpenGLWidget
下一篇: QML 开发问题记录
jdq0603
博客等级 码龄17年 19粉丝 11原创
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值