算法上使用分形插值算法。渲染上,效率和扩展性中最理想的是用shader,但为了方便也可以用封装好的pixmap或shapeRenderer。这里用pixmap来绘制3d山。值得一提,1.6.1API:Color.toIntBits(int r,int g,int b,int a)是错的,参数位置前后倒了,导致山体一片红,所以顺着对的修改完毕。可以重置,修改blend模式以及精细程度。
以下是代码和效果图。
(可以看到n值为2倍后内存消耗增加不止1倍,渲染算法上是需要改进的)
package indi.dawn.ff.work;
import java.util.StringTokenizer;
import com.badlogic.gdx.Application.ApplicationType;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.Input;
import com.badlogic.gdx.graphics.Color;
import com.badlogic.gdx.graphics.GL20;
import com.badlogic.gdx.graphics.Pixmap;
import com.badlogic.gdx.graphics.Pixmap.Blending;
import com.badlogic.gdx.graphics.Texture;
import com.badlogic.gdx.graphics.Pixmap.Format;
import com.badlogic.gdx.graphics.g2d.Batch;
import com.badlogic.gdx.graphics.glutils.ShapeRenderer;
import com.badlogic.gdx.scenes.scene2d.Actor;
import com.badlogic.gdx.scenes.scene2d.InputEvent;
import com.badlogic.gdx.scenes.scene2d.InputListener;
import com.badlogic.gdx.utils.Disposable;
class MountainC extends Actor implements Disposable{
ShapeRenderer jj;
int n = 32, n1, h,w,h2,w2, mx0,my0, xPol[],yPol[], iCol[][][];
double rnd, fiX = .2, fiY = .3, dfi = .01, scale = .8, m20,m21,m22;
double vert[][][], vert1[][][], Norm[][][][], Norm1z[][][], M[];
Color col[][];
boolean painted;
Texture buffImage;Pixmap buffGraphics;
InputListener ip;
public MountainC(){
ip=new InputListener(){
@Override
public boolean touchDown(InputEvent event, float x, float y,
int pointer, int button) {
// TODO Auto-generated method stub
mx0 = (int) x; my0 = (int) y;
if ( Gdx.input.isKeyPressed(Input.Keys.CONTROL_LEFT) ){
setup();
// repaint();
}
if ( Gdx.input.isKeyPressed(Input.Keys.ALT_LEFT) ){
if (Gdx.input.isKeyPressed(Input.Keys.SHIFT_LEFT) ){ n /= 2; if (n < 1) n = 1;}
else n *= 2;
setup();
// repaint();
}
if(Gdx.app.getType()==ApplicationType.Android){
if (pointer==1){
n *= 2;
setup();
// repaint();
}
if (pointer==2 )
{ n /= 2; if (n < 1) n = 1;}
}
return true;
}
@Override
public void touchDragged(InputEvent event, float x, float y,
int pointer) {
// TODO Auto-generated method stub
int x1 = (int) x; int y1 = (int) y;
if ( Gdx.input.isKeyPressed(Input.Keys.SHIFT_LEFT) ) scale *= Math.exp(-(y1 - my0)/(double)w);
else fiX += dfi*(y1 - my0);
fiY += dfi*(x1 - mx0); mx0 = x1; my0 = y1;
rotate();
// repaint();
}
};
init();
/*for(int i=0;i<4;i++){
for(Color c:col[i]){
System.out.println(c.toIntBits());