segunda-feira, 2 de setembro de 2013 0 comentários

Fatec de Ourinhos é Boa?

Bom esses dias falei no Facebook que a Fatec de Ourinhos não era uma boa faculdade, como tantos papagaiam por ai, quase fui crucifixado pelos alunos de lá. É normal e os entendo, já que se esforçaram para entrar nela e dai chega um maluco falando que ela é ruim como é isso? O problema é que mexo na área e fiquei 2,5 anos na faculdade, quando faltava um ano e meio para terminar, não suportei e sai, não foi por ter que matar um leão por dia para estar presente nas aulas ou os professores metido a piadistas e sim a carência de docentes qualificados e aulas que condiz com a realidade do programador.

Vemos professores de jogos ensinado a mexer em RPG Maker, em minha humilde opinião, se a pessoa precisa de faculdade para mexer no RPG Maker algum problema tem, professores que ensinam a bolar historinhas. Meu Deus se a pessoa não sabe bolar uma historia para seu jogo com certeza está na profissão errada, tentam se fazer de professores, mas muitos nem sabe escrever um algorítimo e nunca fizeram um game na vida para querer ensinar os outros como se faz.

Os alunos coitados, não quero generalizar, mas são uma massa facilmente controlada, pois o que o professor fala para eles é 100% verdade. Quando entram em greve falam que seu salario é baixo e que não são valorizados. Os alunos nem se indagam sobre os carrões parados no estacionamento, sem um risco e as roupas de "Burgues" usadas pelos professores, simplesmente se veste de palhaço e vão para as ruas embaixo de sol forte, lutar pelos professores que fazem terrorismo escolar e cobram até pingo no i na hora das provas.

E se está tão ruim assim, porque não pedem demissão? Podemos ver o fracasso da Fatec na semana de tecnologia, onde estão os projetos dos alunos, alias que projetos dos alunos? Cade os sistemas projetados pelos educados? Se não trouxessem pessoas de fora, professores e alunos que são realmente programadores, simplesmente a semana da tecnologia seria um fracasso.

E a Semana dos Jogos ou Semana dos Games? Em vez de mostrarem os jogos produzidos pela instituição, baixam jogos, muitos desses feitos por pessoas que nem sequer diplomados são, digo isso porque muitos alunos afirmam que sem diploma é impossível projetar um game (Ideia passada pelos sábios professores), vemos ai limitações intelectuais dos alunos e seus professores, passam  a semana toda jogando em vez de mostrarem sua evolução diante do grande ensinamento dada pela Fatec.

Vemos professor falando que a Fatec de Ourinhos é uma das faculdade mais conceituadas do Estado de São Paulo. Claro que os professores irão dizer isso, ninguém vai falar mal da onde come e bebe, imagina um professor falando que lá não presta. Inclusive teve professores que já leram o meu blog e falaram em sala de aula: " Parem de falar mal da instituição, falar mal da Fatec é falar mal de vocês mesmos." . Não concordo, quando se fala "mal" da faculdade é um aviso de que algo está errado, que alguma coisa tem e deve ser mudada.

E os mini cursos? Método para tirar mais uma graninha dos "intelectuais" alunos da fatec, ao final de cada curso você ganha um papel de sulfite sem o reconhecimento do MEC e sem o carimbo da instituição, assinado pelo professor anônimo das couves e com os dizeres FATEC no topo (Olha só em negrito hein). Isso com certeza é um grande diferencial na hora de pedir emprego.

E a solução? Abandonar a Fatec? Não, mas fazer pressão, pedir uma mudança no método de ensino, pedir para elaborar apostilas e provas que condiz com o que esta sendo ensinado, falar com alunos auto didata atualizados o que poderia e como estar sendo ensinado, se você ensina que 1 + 1 é 2 não vai elaborar uma prova onde tem 3 * 3, buscar material que incentive o aluno a programar DE VERDADE e que o desafie e não esses Maker meia boca, onde muitos custam mais de 5 mil reais para se poder usar.. Mais um grande problema dos professores é achar que está lidando com alunos recém formados do ensino médio, ali tem homens e mulheres de 30, 40 e 50 anos e acharem que são mais espertos, que podem sair enganando todo mundo.

O que mais queria dos alunos da Fatec é que usassem suas mentes, não só para programar, mas para analisar professores e alunos a sua volta. A instituição é bonita e tem uma ótima biblioteca, com certeza você fez muitos amigos lá. Mas isso não é o aprendizado, você não deve misturar essas coisas, defender a faculdade quando ela está tão carente de educadores que realmente se preocupa com a qualidade e a qualificação profissional futura de seus alunos é tolice.

Pensem nisso e até próxima.
quarta-feira, 29 de maio de 2013 0 comentários

Box2D erro ou error no destroyBody

E hoje estava lá brincando com meu Box2D (uma biblioteca de física para games) gastei o dia todo estudando ele, sabe o que é nem sair para comer? Em fim, trombei com um erro que consegui driblar, mas que não sei se é o jeito correto. Se alguém souber um jeito melhor poste nos comentário.

Código
//Método que verifica uma colisão no jBox2D
public void verificarColisao(){

//Step é o que faz o mundo andar 
mundo.step(0.1f, 6, 2);

//Método que verifica a colisão de 2 corpos 
mundo.setContactListener(new ContactListener(){


//Se houve um contato cai aqui
public void beginContact(Contact contact) {

//Captura os 2 corpos que fizeram contato atribuindo a um Objeto Corpo
Body corpoA = contact.getFixtureA().getBody();
Body corpoB = contact.getFixtureB().getBody();  
 
//Verifica se os corpos são do tipo Bola, poderia ser de tipos distintos como Bala e Garrafa, mas aqui são 2 bolas que irão se explodir ao se tocarem
 if((corpoA.getUserData().equals("Bola") &&
 corpoB.getUserData().equals("Bola")) ||
 (corpoB.getUserData().equals("Bola") && 
 corpoA.getUserData().equals("Bola")) 
 ){
//Aqui que mora o problema, se usarmos mundo.destroyBody(corpoA); irá gerar um erro. O motivo acredito seja porque ainda esteja em meio a testes de colisão. Para consertar isso adicionei os corpos que desejo remover em uma Matriz Array chamada de corposRemove e no final do código mando passar por todos os corpos que desejo remover.

  corposRemove.add(corpoA);
  corposRemove.add(corpoB);
 
}

@Override
public void endContact(Contact contact) {
// TODO Auto-generated method stub
Gdx.app.log("Aviso:", "Fim do contato");
}

@Override
public void preSolve(Contact contact, Manifold oldManifold) {
// TODO Auto-generated method stub

}

@Override
public void postSolve(Contact contact, ContactImpulse impulse) {
// TODO Auto-generated method stub

}

});

              //Podemos colocar um If aqui para ver se há corpos que desejamos retirar a fim de evitar processo desnecessário, passamos pela lista de corpos e se acharmos algumo destruimos .
for(int i =0; i < corposRemove.size; i++){
 mundo.destroyBody(corposRemove.get(i));
 corposRemove.removeIndex(i);
}.
}


Bom, como pudemos ver para se remover um corpo de forma correta devemos destrui-lo após ter saido das verificações de colisão. Um private Iterator corpos; poderia tb dar a ilusão de ter removido um corpo dentro do jogo, mas tudo o que fazemos é remover a fixture dele mantendo o corpo dentro do World ... É necessario sua destruição para bom funcionamento do jogo. Não esqueça também de chamar o dispose da textura usada, para liberar memória. Até a próxima :)
sábado, 2 de fevereiro de 2013 0 comentários

ShaderProgram Utility


ShaderProgram Utility
Este pagina demonstra  passos necessários para se criar o sua própria classe re-utilizável através do utilitário ShaderProgram. Você também pode usar o mais avançado utilitário de ShaderProgram já incluído no LWJGL-básico: ver aqui.

Para nossos propósitos, vamos usar apenas um vértice e um fragmento de shader para criar os nossos programas de sombreamento. Planejamos visar o GL 2.1, que também terá de especificar os locais de atributos manualmente. Se for usar versões mais recentes do OpenGL (ou seja, GLSL 330 +), então podemos especificar os locais de atributos com qualificadores do tipo em seu lugar. Os passos básicos para a criação de um programa de shader como este são:

Compilar o código fonte em um vértice shader shader objeto.

Compilar o código fonte em um fragmento de shader shader objeto.

Criar um programa com ID glCreateProgram.

Anexar os objetos vertex e shader para o nosso programa com glAttachShader.
Se nós estamos usando 2.1, é aqui que ligaria quaisquer atributos manualmente. Por exemplo, poderíamos vincular o atributo posição de índice 0. Para isso, usamos glBindAttribLocation. Se nós estamos usando versões mais recentes do GLSL, podemos pular essa etapa.

Em seguida, ligar o programa com glLinkProgram.

Se o programa conseguiu compilar, agora podemos separar e excluir os objetos de sombreamento da vértice e fragmento como eles não são mais necessários - usando glDetachShader e glDeleteShader, respectivamente. Estes são apenas avisam para o OpenGL, que os objetos serão apagados quando eles não estão mais associados com quaisquer estados de renderização.

Exemplo:
public ShaderProgram(String vertexShader, String fragmentShader, Map<Integer, String> attributes) throws LWJGLException {
 //compile the String source
 vertex = compileShader(vertexShader, GL_VERTEX_SHADER);
 fragment = compileShader(fragmentShader, GL_FRAGMENT_SHADER);
 
 //create the program
 program = glCreateProgram();
 
 //attach the shaders
 glAttachShader(program, vertex);
 glAttachShader(program, fragment);

 //bind the attrib locations for GLSL 120
 if (attributes != null)
  for (Entry<Integer, String> e : attributes.entrySet())
   glBindAttribLocation(program, e.getKey(), e.getValue());

 //link our program
 glLinkProgram(program);

 //grab our info log
 String infoLog = glGetProgramInfoLog(program, glGetProgrami(program, GL_INFO_LOG_LENGTH));
 
 //if some log exists, append it 
 if (infoLog!=null && infoLog.trim().length()!=0)
  log += infoLog;
 
 //if the link failed, throw some sort of exception
 if (glGetProgrami(program, GL_LINK_STATUS) == GL_FALSE)
  throw new LWJGLException(
    "Failure in linking program. Error log:\n" + infoLog);
 
 //detach and delete the shaders which are no longer needed
 glDetachShader(program, vertex);
 glDetachShader(program, fragment);
 glDeleteShader(vertex);
 glDeleteShader(fragment);
}

protected int compileShader(String source, int type) throws LWJGLException {
 //create a shader object
 int shader = glCreateShader(type);
 //pass the source string
 glShaderSource(shader, source);
 //compile the source
 glCompileShader(shader);

 //if info/warnings are found, append it to our shader log
 String infoLog = glGetShaderInfoLog(shader,
   glGetShaderi(shader, GL_INFO_LOG_LENGTH));
 if (infoLog!=null && infoLog.trim().length()!=0)
  log += getName(type) +": "+infoLog + "\n";
 
 //if the compiling was unsuccessful, throw an exception
 if (glGetShaderi(shader, GL_COMPILE_STATUS) == GL_FALSE)
  throw new LWJGLException("Failure in compiling " + getName(type)
    + ". Error log:\n" + infoLog);

 return shader;
}
Usando o programa:
Em OpenGL, só podemos ter um programa único de shader em uso ao mesmo tempo. Chamamos glUseProgram (programa) para especificar o programa ativo. Devemos especificar o glUseProgram (0) para usar o "default" do shader. No entanto, uma vez que estamos tentando trabalhar com o pipeline programável, não devemos mais nos preocupar com o shader padrão, já que não existe tal coisa no GL moderna. Na verdade, ele pode causar erros se tentarmos renderização com o shader padrão no GL 3.1 +  

Assim, nossos métodos para se criar um programa final ficará assim::

/**
 * Make this shader the active program.
 */
public void use() {
 glUseProgram(program);
}

/**
 * Destroy this shader program.
 */
public void destroy() {
 //a flag for GL -- the program will not actually be deleted until it's no longer in use
 glDeleteProgram(program);
}

/**
 * Gets the location of the specified uniform name.
 * @param str the name of the uniform
 * @return the location of the uniform in this program
 */
public int getUniformLocation(String str) {
 return glGetUniformLocation(program, str);
}
Definir valores uniformes:

Tal como discutido anteriormente na série, usamos glUniform para passar dados uniformes para os nossos shaders. Um utilitário ShaderProgram completa pode incluir diversos utilitários para obter e definir uniformes (veja aqui). Nosso exemplo simples irá lidar com o mínimo de: matrizes e uniformes inteiros (para sampler2D).

/**
 * Sets the uniform data at the specified location (the uniform type may be int, bool or sampler2D). 
 * @param loc the location of the int/bool/sampler2D uniform 
 * @param i the value to set
 */
public void setUniformi(int loc, int i) {
 if (loc==-1) return;
 glUniform1i(loc, i);
}

/**
 * Sends a 4x4 matrix to the shader program.
 * @param loc the location of the mat4 uniform
 * @param transposed whether the matrix should be transposed
 * @param mat the matrix to send
 */
public void setUniformMatrix(int loc, boolean transposed, Matrix4f mat) {
 if (loc==-1) return;
 if (buf16Pool == null)
  buf16Pool = BufferUtils.createFloatBuffer(16);
 buf16Pool.clear();
 mat.store(buf16Pool);
 buf16Pool.flip();
 glUniformMatrix4(loc, transposed, buf16Pool);
}
Código fonte completo:

public class ShaderProgram {

 protected static FloatBuffer buf16Pool;
 
 /**
  * Makes the "default shader" (0) the active program. In GL 3.1+ core profile,
  * you may run into glErrors if you try rendering with the default shader. 
  */
 public static void unbind() {
  glUseProgram(0);
 }

 public final int program;
 public final int vertex;
 public final int fragment;
 protected String log;

 public ShaderProgram(String vertexSource, String fragmentSource) throws LWJGLException {
  this(vertexSource, fragmentSource, null);
 }

 /**
  * Creates a new shader from vertex and fragment source, and with the given 
  * map of  attrib locations
  * @param vertexShader the vertex shader source string
  * @param fragmentShader the fragment shader source string
  * @param attributes a map of attrib locations for GLSL 120
  * @throws LWJGLException if the program could not be compiled and linked
  */
 public ShaderProgram(String vertexShader, String fragmentShader, Map<Integer, String> attributes) throws LWJGLException {
  //compile the String source
  vertex = compileShader(vertexShader, GL_VERTEX_SHADER);
  fragment = compileShader(fragmentShader, GL_FRAGMENT_SHADER);
  
  //create the program
  program = glCreateProgram();
  
  //attach the shaders
  glAttachShader(program, vertex);
  glAttachShader(program, fragment);

  //bind the attrib locations for GLSL 120
  if (attributes != null)
   for (Entry<Integer, String> e : attributes.entrySet())
    glBindAttribLocation(program, e.getKey(), e.getValue());

  //link our program
  glLinkProgram(program);

  //grab our info log
  String infoLog = glGetProgramInfoLog(program, glGetProgrami(program, GL_INFO_LOG_LENGTH));
  
  //if some log exists, append it 
  if (infoLog!=null && infoLog.trim().length()!=0)
   log += infoLog;
  
  //if the link failed, throw some sort of exception
  if (glGetProgrami(program, GL_LINK_STATUS) == GL_FALSE)
   throw new LWJGLException(
     "Failure in linking program. Error log:\n" + infoLog);
  
  //detach and delete the shaders which are no longer needed
  glDetachShader(program, vertex);
  glDetachShader(program, fragment);
  glDeleteShader(vertex);
  glDeleteShader(fragment);
 }

 /** Compile the shader source as the given type and return the shader object ID. */
 protected int compileShader(String source, int type) throws LWJGLException {
  //create a shader object
  int shader = glCreateShader(type);
  //pass the source string
  glShaderSource(shader, source);
  //compile the source
  glCompileShader(shader);

  //if info/warnings are found, append it to our shader log
  String infoLog = glGetShaderInfoLog(shader,
    glGetShaderi(shader, GL_INFO_LOG_LENGTH));
  if (infoLog!=null && infoLog.trim().length()!=0)
   log += getName(type) +": "+infoLog + "\n";
  
  //if the compiling was unsuccessful, throw an exception
  if (glGetShaderi(shader, GL_COMPILE_STATUS) == GL_FALSE)
   throw new LWJGLException("Failure in compiling " + getName(type)
     + ". Error log:\n" + infoLog);

  return shader;
 }

 protected String getName(int shaderType) {
  if (shaderType == GL_VERTEX_SHADER)
   return "GL_VERTEX_SHADER";
  if (shaderType == GL_FRAGMENT_SHADER)
   return "GL_FRAGMENT_SHADER";
  else
   return "shader";
 }

 /**
  * Make this shader the active program.
  */
 public void use() {
  glUseProgram(program);
 }

 /**
  * Destroy this shader program.
  */
 public void destroy() {
  glDeleteProgram(program);
 }

 /**
  * Gets the location of the specified uniform name.
  * @param str the name of the uniform
  * @return the location of the uniform in this program
  */
 public int getUniformLocation(String str) {
  return glGetUniformLocation(program, str);
 }
 
 /* ------ UNIFORM SETTERS/GETTERS ------ */
 
 /**
  * Sets the uniform data at the specified location (the uniform type may be int, bool or sampler2D). 
  * @param loc the location of the int/bool/sampler2D uniform 
  * @param i the value to set
  */
 public void setUniformi(int loc, int i) {
  if (loc==-1) return;
  glUniform1i(loc, i);
 }

 /**
  * Sends a 4x4 matrix to the shader program.
  * @param loc the location of the mat4 uniform
  * @param transposed whether the matrix should be transposed
  * @param mat the matrix to send
  */
 public void setUniformMatrix(int loc, boolean transposed, Matrix4f mat) {
  if (loc==-1) return;
  if (buf16Pool == null)
   buf16Pool = BufferUtils.createFloatBuffer(16);
  buf16Pool.clear();
  mat.store(buf16Pool);
  buf16Pool.flip();
  glUniformMatrix4(loc, transposed, buf16Pool);
 }
}
Fonte: https://github.com/mattdesl/lwjgl-basics/wiki/ShaderProgram-Utility
 
;