Click here to Skip to main content
15,867,686 members
Articles / Mobile Apps / iPhone
Article

2d Textures in cocos2d-x V3

Rate me:
Please Sign up or sign in to vote.
4.76/5 (5 votes)
16 Feb 2014CPOL 17.4K   1  
Well it wasn’t as easy as I thought it was going to be, but I managed to get a version of my scrolling texture program working under cocos2d-x V3 Beta 2. I set up cocos2d-x v3 as in my previous … Continue reading →

Well it wasn’t as easy as I thought it was going to be, but I managed to get a version of my scrolling texture program working under cocos2d-x V3 Beta 2.

I set up cocos2d-x v3 as in my previous post. Then I edited the HelloWorldScene.cpp, pretty much re-writing it, to replicate what I did previously in cocos2d after using the great PRKit.

The idea is exactly the same – an array of points is created, representing the triangle strip to be drawn to create the surface and sub-terrain of our landscape. so,first point is the surface, second the same X coordinate but at the bottom of the screen (y = 0). Third point is the next surface point to the right, fourth is the same X coordinate but at the bottom of the screen. And so on.

Every time the cocos layer is drawn, we decrease all the x coordinates – so the effect of our ‘landscape’ scrolling to the left is achieved.

Scrolling textures with cocos2d-x 3

Scrolling textures with cocos2d-x 3

It’s not that big, so I will paste the whole code from HelloWorldScene.cpp here

C++
#import <CoreGraphics/CoreGraphics.h>
#include "HelloWorldScene.h"

USING_NS_CC;

Texture2D* _texture;
// The points used to draw the openGl triangle strip
cocos2d::Point* _areaTrianglePoints;
// The points used by openGl to apply the testure to the triabgle strip
cocos2d::Point* _texturePoints;
// The points on the surface. Not actually used in this demo, but would be used to set the surface sprites for example
std::vector<cocos2d::Point> _points;
// An offset, used to allow our textrue to scrol with the triangle list
cocos2d::Point _textureOffset;
// The number of points in our triangle array (so 2* the number of surface points)
int _numberOfPoints;
// The dy and dx that we use to scroll
cocos2d::Point _scrollSpeed;

// The openGl program object used
GLProgram* _glProgram;

Scene* HelloWorld::createScene()
{
    auto scene = Scene::create();
    auto layer = HelloWorld::create();
    scene->addChild(layer);
    return scene;
}

bool HelloWorld::init()
{
    if ( !Layer::init() )
    {
        return false;
    }

	_textureOffset = cocos2d::Point(0,0);
	_numberOfPoints = 200;
	_texture = Director::getInstance()->getTextureCache()->addImage("somerock.png");

	_areaTrianglePoints = (cocos2d::Point*) malloc(sizeof(cocos2d::Point) * _numberOfPoints);
	_texturePoints = (cocos2d::Point*) malloc(sizeof(cocos2d::Point) * _numberOfPoints);

	float x=0;
	float y=400;
	float maxy=800;
	float maxDx = 50;
	float maxDy = 240;
	for (int i=0;i<_numberOfPoints;i+=2)
	{
		cocos2d::Point p = cocos2d::Point(x,y);

		_points.push_back(p);
		// Add a point
		_areaTrianglePoints[i] = p;
		// Add another point, vertically below the previous point
		_areaTrianglePoints[i+1] = cocos2d::Point(x, 0);

		x+= rand() % (int)maxDx;
		float dy = (rand() % (int)(maxDy * 2)) – maxDy;
		y+=dy;

		if (y>maxy) y=maxy;
		if (y<0) y=20;
	}

	_glProgram = cocos2d::ShaderCache::getInstance()->getProgram(GLProgram::SHADER_NAME_POSITION_TEXTURE)  ;
    return true;
}

void HelloWorld::draw()
{
	_scrollSpeed = cocos2d::Point(-0.5,0);
	_textureOffset -= _scrollSpeed;

	for (int i = 0; i < _numberOfPoints; i++)
	{
		_areaTrianglePoints[i] += _scrollSpeed;
	}

	HelloWorld::calculateTexturePoints();

	// Tell OpenGL this is the texture we're using
	GL::bindTexture2D(_texture->getName());
	// wrap in both the S and T directions (that's X and Y for the rest of us!)
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
	glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
	// Enable the arrays
	GL::enableVertexAttribs(GL::VERTEX_ATTRIB_FLAG_POSITION | GL::VERTEX_ATTRIB_FLAG_TEX_COORDS);

	_glProgram->use();
	// Tell Cocos2D to pass the CCNode's position/scale/rotation matrix to the shader (well, that's what Ray says!)
	_glProgram->setUniformsForBuiltins();
	// Give OpenGl our array of points that we want to fill
	glVertexAttribPointer(GLProgram::VERTEX_ATTRIB_POSITION, 2, GL_FLOAT, GL_FALSE, sizeof(cocos2d::Point), _areaTrianglePoints);
	// Give OpenGl the array of points in the texture we want to use to fill the above array of points
	glVertexAttribPointer(GLProgram::VERTEX_ATTRIB_TEX_COORDS, 2, GL_FLOAT, GL_FALSE, sizeof(cocos2d::Point), _texturePoints);
	// Tell OpenGl to draw the arrays we gave it
	glDrawArrays(GL_TRIANGLE_STRIP, 0, _numberOfPoints);
}

void HelloWorld::calculateTexturePoints()
{
	for (int i = 0; i < _numberOfPoints; i++)
	{
		// Calculate a point based on the areaTriangle point plus the current offset
		cocos2d::Point p = cocos2d::Point(_areaTrianglePoints[i].x + _textureOffset.x, _areaTrianglePoints[i].y + _textureOffset.y);
		// mod it to be within the bounds of the texture
		_texturePoints[i] = p * (1.0f / _texture->getPixelsWide());
		// reverse the y coordinate
		_texturePoints[i].y = 1 – _texturePoints[i].y;
	}
}

I’m off now to build this into PooperPig for cocos2d-x!

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Software Developer (Senior) Devo
Australia Australia
Software developer par excellence,sometime artist, teacher, musician, husband, father and half-life 2 player (in no particular order either of preference or ability)
Started programming aged about 16 on a Commodore Pet.
Self-taught 6500 assembler - wrote Missile Command on the Pet (impressive, if I say so myself, on a text-only screen!)
Progressed to BBC Micro - wrote a number of prize-winning programs - including the best graphics application in one line of basic (it drew 6 multicoloured spheres viewed in perspective)
Trained with the MET Police as a COBOL programmer
Wrote platform game PooperPig which was top of the Ceefax Charts for a while in the UK
Did a number of software dev roles in COBOL
Progressed to Atari ST - learned 68000 assembler & write masked sprite engine.
Worked at Atari ST User magazine as Technical Editor - and was editor of Atari ST World for a while.
Moved on to IBM Mid range for work - working as team leader then project manager
Emigrated to Aus.
Learned RPG programming on the job (by having frequent coffee breaks with the wife!!)
Moved around a few RPG sites
Wrote for PC User magazine - was Shareware Magazine editor for a while.
Organised the first large-scale usage of the Internet in Australia through PC User magazine.
Moved from RPG to Delphi 1
Developed large applications in Delphi before moving on to VB .Net and C#
Became I.T. Manager - realised how boring paper pushing can be
And now I pretty much do .Net development in the daytime, while redeveloping PooperPig for the mobile market at night.

Comments and Discussions

 
-- There are no messages in this forum --