begin process at 2012 02 11 17:27:25
  Trouver un code source :
 
dans
 
Accueil > 

Code

 > 

Maths & Algorithmes

 > MOTEUR 3D

MOTEUR 3D


 Information sur la source

Note :
8 / 10 - par 10 personnes
8,00 / 10

  • 1

  • 2

  • 3

  • 4

  • 5

  • 6

  • 7

  • 8

  • 9

  • 10
Catégorie :Maths & Algorithmes Classé sous :moteur, 3d, couleurs, gd, matrices Niveau :Expert Date de création :23/07/2005 Date de mise à jour :19/12/2005 16:50:36 Vu / téléchargé :8 335 / 521

Auteur : CyberP

Ecrire un message privé
Site perso
Commentaire sur cette source (16)
Ajouter un commentaire et/ou une note

 Description

Cliquez pour voir la capture en taille normale
C'est un... moteur 3D !
Il fait un seul rendu bien évidemment et utilise les mêmes techniques de rendu software que les vrais moteurs. Pour l'instant, il affiche les arêtes d'un cube (mais on peut modifier et mettre autre chose qu'un cube) selon la position de la caméra que l'on peut définir en modifiant la source

J'ai fait cela pour prouver qu'il n'était pas si compliqué de faire un moteur 3D, même en php
Il utilise GD. J'ai fait ça pour me faciliter la vie... après on peut aussi faire un .bmp avec et ne pas utiliser GD

Le backbuffer ne fonctionne pas correctement, j'ai mis la partie qui utiliser le backbuffer en commentaire

Source

  • $width = 320;
  • $height = 240;
  • $clipping = 500;
  • $wireframe = false; // mode fil de fer
  • header("Content-type: image/jpeg");
  • function drawtriangle($im, $backbuffer, $pt1, $pt2, $pt3, $width, $height, $wireframe) {
  • if ($pt1[1] > $pt2[1]) { $tmp = $pt2; $pt2 = $pt1; $pt1 = $tmp; }
  • if ($pt1[1] > $pt3[1]) { $tmp = $pt3; $pt3 = $pt1; $pt1 = $tmp; }
  • if ($pt2[1] > $pt3[1]) { $tmp = $pt3; $pt3 = $pt2; $pt2 = $tmp; }
  • if ($pt1[1] > $pt2[1]) { $tmp = $pt2; $pt2 = $pt1; $pt1 = $tmp; }
  • if ($pt1[1] > $pt3[1]) { $tmp = $pt3; $pt3 = $pt1; $pt1 = $tmp; }
  • if ($pt2[1] > $pt3[1]) { $tmp = $pt3; $pt3 = $pt2; $pt2 = $tmp; }
  • for ($i = 0; $i <= ($pt3[1] - $pt1[1]); ++$i) {
  • if ($i + $pt1[1] > $height || $i + $pt1[1] < 0)
  • continue;
  • $num1 = $pt1[0] + $i * ($pt3[0] - $pt1[0]) / ($pt3[1] - $pt1[1]);
  • $num1z = $pt1[2] + $i * ($pt3[2] - $pt1[2]) / ($pt3[1] - $pt1[1]);
  • $num1r = $pt1[3] + $i * ($pt3[3] - $pt1[3]) / ($pt3[1] - $pt1[1]);
  • $num1g = $pt1[4] + $i * ($pt3[4] - $pt1[4]) / ($pt3[1] - $pt1[1]);
  • $num1b = $pt1[5] + $i * ($pt3[5] - $pt1[5]) / ($pt3[1] - $pt1[1]);
  • if ($i > ($pt2[1] - $pt1[1])) {
  • $num2 = $pt2[0] + ($pt3[0] - $pt2[0]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
  • $num2z = $pt2[2] + ($pt3[2] - $pt2[2]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
  • $num2r = $pt2[3] + ($pt3[3] - $pt2[3]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
  • $num2g = $pt2[4] + ($pt3[4] - $pt2[4]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
  • $num2b = $pt2[5] + ($pt3[5] - $pt2[5]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
  • } else {
  • $num2 = $pt1[0] + ($pt2[0] - $pt1[0]) * $i / ($pt2[1] - $pt1[1]);
  • $num2z = $pt1[2] + ($pt2[2] - $pt1[2]) * $i / ($pt2[1] - $pt1[1]);
  • $num2r = $pt1[3] + ($pt2[3] - $pt1[3]) * $i / ($pt2[1] - $pt1[1]);
  • $num2g = $pt1[4] + ($pt2[4] - $pt1[4]) * $i / ($pt2[1] - $pt1[1]);
  • $num2b = $pt1[5] + ($pt2[5] - $pt1[5]) * $i / ($pt2[1] - $pt1[1]);
  • }
  • if ($num1 > $num2) {
  • $tmp = $num2;
  • $num2 = $num1;
  • $num1 = $tmp;
  • $tmp = $num2z;
  • $num2z = $num1z;
  • $num1z = $tmp;
  • $tmp = $num2r;
  • $num2r = $num1r;
  • $num1r = $tmp;
  • $tmp = $num2g;
  • $num2g = $num1g;
  • $num1g = $tmp;
  • $tmp = $num2b;
  • $num2b = $num1b;
  • $num1b = $tmp;
  • }
  • if ($num1 == $num2) $num2 = $num1 + 1;
  • for ($j = $num1; $j <= $num2; $j += $wireframe?($num2 - $num1):1) {
  • if ($j > $width || $j < 0) continue;
  • $zcoord = $num1z + ($num2z - $num1z) * (($j - $num1) / ($num2 - $num1));
  • /*if ($zcoord > ($backbuffer[$j + ($i + $pt1[1]) * $width]))
  • continue;
  • $backbuffer[$j + ($i + $pt1[1]) * $width] = $zcoord;*/
  • $red = $num1r + ($num2r - $num1r) * (($j - $num1) / ($num2 - $num1));
  • $green = $num1g + ($num2g - $num1g) * (($j - $num1) / ($num2 - $num1));
  • $blue = $num1b + ($num2b - $num1b) * (($j - $num1) / ($num2 - $num1));
  • imagesetpixel($im, $j, $i + $pt1[1], imagecolorallocate($im, $red, $green, $blue));
  • }
  • }
  • return $backbuffer;
  • }
  • class mesh {
  • var $points;
  • var $triangle1;
  • var $triangle2;
  • var $triangle3;
  • var $scale;
  • var $translation;
  • function render($matrix, $width, $height, $im, $backbuffer, $wireframe) {
  • $matrix2 = multiply(multiply($matrix, $this->translation), $this->scale);
  • for ($i = 0; $i < sizeof($this->triangle1); ++$i) {
  • if (!isset($this->triangle1[$i])) continue;
  • if (!isset($this->triangle2[$i])) continue;
  • if (!isset($this->triangle3[$i])) continue;
  • $pt1 = $this->points[$this->triangle1[$i]];
  • $pt2 = $this->points[$this->triangle2[$i]];
  • $pt3 = $this->points[$this->triangle3[$i]];
  • $tmp1 = $pt1->calculate($matrix2);
  • $tmp2 = $pt2->calculate($matrix2);
  • $tmp3 = $pt3->calculate($matrix2);
  • $tmp1[0] = ($tmp1[0] + 1) * $width / 2;
  • $tmp1[1] = ($tmp1[1] + 1) * $height / 2;
  • $tmp2[0] = ($tmp2[0] + 1) * $width / 2;
  • $tmp2[1] = ($tmp2[1] + 1) * $height / 2;
  • $tmp3[0] = ($tmp3[0] + 1) * $width / 2;
  • $tmp3[1] = ($tmp3[1] + 1) * $height / 2;
  • $backbuffer = drawtriangle($im, $backbuffer, $tmp1, $tmp2, $tmp3, $width, $height, $wireframe);
  • }
  • }
  • function mesh() {
  • $this->points = array();
  • $this->triangle1 = array();
  • $this->triangle2 = array();
  • $this->triangle3 = array();
  • $this->scale = new matrix();
  • $this->scale->loadIdentity();
  • $this->translation = new matrix();
  • $this->translation->loadIdentity();
  • }
  • };
  • class point {
  • var $x;
  • var $y;
  • var $z;
  • var $cr;
  • var $cg;
  • var $cb;
  • function point($x = 0, $y = 0, $z = 0, $r = 255, $g = 255, $b = 255) {
  • $this->x = $x;
  • $this->y = $y;
  • $this->z = $z;
  • $this->cr = $r;
  • $this->cg = $g;
  • $this->cb = $b;
  • }
  • function calculate($matrix) {
  • $retour = array(0, 0, 0, 255, 255, 255);
  • $retour[0] = $this->x * $matrix->values[0] + $this->y * $matrix->values[1] + $this->z * $matrix->values[2] + $matrix->values[3];
  • $retour[1] = $this->x * $matrix->values[4] + $this->y * $matrix->values[5] + $this->z * $matrix->values[6] + $matrix->values[7];
  • $retour[2] = $this->x * $matrix->values[8] + $this->y * $matrix->values[9] + $this->z * $matrix->values[10] + $matrix->values[11];
  • $retour[3] = $this->cr;
  • $retour[4] = $this->cg;
  • $retour[5] = $this->cb;
  • return $retour;
  • }
  • };
  • class matrix {
  • var $values;
  • function get($x, $y) {
  • return $y + $x * 4;
  • }
  • function loadIdentity() {
  • $this->values = array(1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1);
  • }
  • function projection($angle, $ratio, $zNear, $zFar) {
  • $angle = $angle;
  • $yScale = atan($angle / 2);
  • $this->loadIdentity();
  • $this->values[0] = $ratio / $yScale;
  • $this->values[5] = $yScale;
  • $this->values[10] = $zFar / ($zFar - $zNear);
  • $this->values[11] = -$zNear * $zFar / ($zFar - $zNear);
  • $this->values[14] = 1;
  • $this->values[15] = 0;
  • }
  • function lookat($eye, $at, $up) {
  • $zaxis = new point();
  • $zaxis->x = $eye->x - $at->x; $zaxis->y = $eye->y - $at->y; $zaxis->z = $eye->z - $at->z;
  • $dist = sqrt($zaxis->x * $zaxis->x + $zaxis->y * $zaxis->y + $zaxis->z * $zaxis->z);
  • $zaxis->x /= $dist; $zaxis->y /= $dist; $zaxis->z /= $dist;
  • $xaxis = new point();
  • $xaxis->x = $up->y * $zaxis->z - $up->z * $zaxis->y;
  • $xaxis->y = $up->z * $zaxis->x - $up->x * $zaxis->z;
  • $xaxis->z = $up->x * $zaxis->y - $up->y * $zaxis->x;
  • $dist = sqrt($xaxis->x * $xaxis->x + $xaxis->y * $xaxis->y + $xaxis->z * $xaxis->z);
  • $xaxis->x /= $dist; $xaxis->y /= $dist; $xaxis->z /= $dist;
  • $yaxis = new point();
  • $yaxis->x = $zaxis->y * $xaxis->z - $zaxis->z * $xaxis->y;
  • $yaxis->y = $zaxis->z * $xaxis->x - $zaxis->x * $xaxis->z;
  • $yaxis->z = $zaxis->x * $xaxis->y - $zaxis->y * $xaxis->x;
  • $dot1 = $xaxis->x * $eye->x + $xaxis->y * $eye->y + $xaxis->z * $eye->z;
  • $dot2 = $yaxis->x * $eye->x + $yaxis->y * $eye->y + $yaxis->z * $eye->z;
  • $dot3 = $zaxis->x * $eye->x + $zaxis->y * $eye->y + $zaxis->z * $eye->z;
  • $this->loadIdentity();
  • $this->values[0] = $xaxis->x;
  • $this->values[1] = $xaxis->y;
  • $this->values[2] = $xaxis->z;
  • $this->values[3] = -$dot1;
  • $this->values[4] = $yaxis->x;
  • $this->values[5] = $yaxis->y;
  • $this->values[6] = $yaxis->z;
  • $this->values[7] = -$dot2;
  • $this->values[8] = $zaxis->x;
  • $this->values[9] = $zaxis->y;
  • $this->values[10] = $zaxis->z;
  • $this->values[11] = -$dot3;
  • $this->values[15] = 1;
  • }
  • function translate($x, $y, $z) {
  • $this->loadIdentity();
  • $this->values[3] = $x;
  • $this->values[7] = $y;
  • $this->values[11] = $z;
  • }
  • function scale($x, $y, $z) {
  • $this->loadIdentity();
  • $this->values[0] = $x;
  • $this->values[5] = $y;
  • $this->values[10] = $z;
  • }
  • function matrix() {
  • $this->values = array(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
  • }
  • };
  • function multiply($matrix1, $matrix2) {
  • $retour = new matrix();
  • for ($i = 0; $i < 4; ++$i)
  • for ($j = 0; $j < 4; ++$j)
  • for ($k = 0; $k < 4; ++$k)
  • $retour->values[$retour->get($i, $j)] += $matrix1->values[$matrix1->get($i, $k)] * $matrix2->values[$matrix2->get($k, $j)];
  • return $retour;
  • }
  • $im = imagecreatetruecolor($width, $height);
  • $fond = imagecolorallocate($im, 0, 0, 0);
  • $blanc = imagecolorallocate($im, 255, 255, 255);
  • $backbuffer = array($width * $height);
  • for ($i = 0; $i < $width * $height; ++$i)
  • $backbuffer[$i] = $clipping;
  • $projection = new matrix();
  • $projection->projection(45, $width / $height, 1, $clipping);
  • $view = new matrix();
  • $view->lookat(new point(2.5, 0.7, 1.3), new point(0, 0, 0), new point(0, 1, 0));
  • $matrice = multiply($projection, $view);
  • $cube = new mesh();
  • $taille = 0.5;
  • $cube->points[0] = new point($taille, $taille, $taille, 255, 0, 0);
  • $cube->points[1] = new point(-$taille, $taille, $taille, 255, 128, 128);
  • $cube->points[2] = new point(-$taille, -$taille, $taille, 200, 200, 0);
  • $cube->points[3] = new point($taille, -$taille, $taille, 255, 255, 60);
  • $cube->points[4] = new point($taille, -$taille, -$taille, 128, 128, 0);
  • $cube->points[5] = new point($taille, $taille, -$taille, 200, 0, 0);
  • $cube->points[6] = new point(-$taille, $taille, -$taille, 255, 45, 45);
  • $cube->points[7] = new point(-$taille, -$taille, -$taille, 255, 255, 128);
  • $cube->triangle1[0] = 0; $cube->triangle2[0] = 1; $cube->triangle3[0] = 2;
  • $cube->triangle1[1] = 0; $cube->triangle2[1] = 2; $cube->triangle3[1] = 3;
  • $cube->triangle1[2] = 4; $cube->triangle2[2] = 5; $cube->triangle3[2] = 7;
  • $cube->triangle1[3] = 5; $cube->triangle2[3] = 6; $cube->triangle3[3] = 7;
  • $cube->triangle1[4] = 0; $cube->triangle2[4] = 3; $cube->triangle3[4] = 4;
  • $cube->triangle1[5] = 0; $cube->triangle2[5] = 4; $cube->triangle3[5] = 5;
  • $cube->triangle1[6] = 1; $cube->triangle2[6] = 2; $cube->triangle3[6] = 7;
  • $cube->triangle1[7] = 1; $cube->triangle2[7] = 6; $cube->triangle3[7] = 7;
  • $cube->triangle1[8] = 0; $cube->triangle2[8] = 1; $cube->triangle3[8] = 6;
  • $cube->triangle1[9] = 0; $cube->triangle2[9] = 5; $cube->triangle3[9] = 6;
  • $cube->triangle1[10] = 2; $cube->triangle2[10] = 3; $cube->triangle3[10] = 7;
  • $cube->triangle1[11] = 3; $cube->triangle2[11] = 4; $cube->triangle3[11] = 7;
  • $cube->scale->scale(0.5, 0.5, 0.5);
  • $cube->translation->translate(0.2, 0.5, 0.3);
  • $cube->render($matrice, $width, $height, $im, $backbuffer, $wireframe);
  • imagejpeg($im);
$width = 320;
$height = 240;

$clipping = 500;

$wireframe = false; // mode fil de fer

header("Content-type: image/jpeg");

function drawtriangle($im, $backbuffer, $pt1, $pt2, $pt3, $width, $height, $wireframe) {
	if ($pt1[1] > $pt2[1]) { $tmp = $pt2; $pt2 = $pt1; $pt1 = $tmp; }
	if ($pt1[1] > $pt3[1]) { $tmp = $pt3; $pt3 = $pt1; $pt1 = $tmp; }
	if ($pt2[1] > $pt3[1]) { $tmp = $pt3; $pt3 = $pt2; $pt2 = $tmp; }
	if ($pt1[1] > $pt2[1]) { $tmp = $pt2; $pt2 = $pt1; $pt1 = $tmp; }
	if ($pt1[1] > $pt3[1]) { $tmp = $pt3; $pt3 = $pt1; $pt1 = $tmp; }
	if ($pt2[1] > $pt3[1]) { $tmp = $pt3; $pt3 = $pt2; $pt2 = $tmp; }
	
	for ($i = 0; $i <= ($pt3[1] - $pt1[1]); ++$i) {
		if ($i + $pt1[1] > $height || $i + $pt1[1] < 0)
			continue;
	
		$num1 = $pt1[0] + $i * ($pt3[0] - $pt1[0]) / ($pt3[1] - $pt1[1]);
		$num1z = $pt1[2] + $i * ($pt3[2] - $pt1[2]) / ($pt3[1] - $pt1[1]);
		$num1r = $pt1[3] + $i * ($pt3[3] - $pt1[3]) / ($pt3[1] - $pt1[1]);
		$num1g = $pt1[4] + $i * ($pt3[4] - $pt1[4]) / ($pt3[1] - $pt1[1]);
		$num1b = $pt1[5] + $i * ($pt3[5] - $pt1[5]) / ($pt3[1] - $pt1[1]);
		
		if ($i > ($pt2[1] - $pt1[1])) {
			$num2 = $pt2[0] + ($pt3[0] - $pt2[0]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
			$num2z = $pt2[2] + ($pt3[2] - $pt2[2]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
			$num2r = $pt2[3] + ($pt3[3] - $pt2[3]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
			$num2g = $pt2[4] + ($pt3[4] - $pt2[4]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
			$num2b = $pt2[5] + ($pt3[5] - $pt2[5]) * ($i - ($pt2[1] - $pt1[1])) / ($pt3[1] - $pt2[1]);
		} else {
			$num2 = $pt1[0] + ($pt2[0] - $pt1[0]) * $i / ($pt2[1] - $pt1[1]);
			$num2z = $pt1[2] + ($pt2[2] - $pt1[2]) * $i / ($pt2[1] - $pt1[1]);
			$num2r = $pt1[3] + ($pt2[3] - $pt1[3]) * $i / ($pt2[1] - $pt1[1]);
			$num2g = $pt1[4] + ($pt2[4] - $pt1[4]) * $i / ($pt2[1] - $pt1[1]);
			$num2b = $pt1[5] + ($pt2[5] - $pt1[5]) * $i / ($pt2[1] - $pt1[1]);
		}
			
		if ($num1 > $num2) {
			$tmp = $num2;
			$num2 = $num1;
			$num1 = $tmp;
			
			$tmp = $num2z;
			$num2z = $num1z;
			$num1z = $tmp;
			
			$tmp = $num2r;
			$num2r = $num1r;
			$num1r = $tmp;
			
			$tmp = $num2g;
			$num2g = $num1g;
			$num1g = $tmp;
			
			$tmp = $num2b;
			$num2b = $num1b;
			$num1b = $tmp;
		}
		
		if ($num1 == $num2) $num2 = $num1 + 1;
		for ($j = $num1; $j <= $num2; $j += $wireframe?($num2 - $num1):1) {
			if ($j > $width || $j < 0) continue;
		
			$zcoord = $num1z + ($num2z - $num1z) * (($j - $num1) / ($num2 - $num1));
			/*if ($zcoord > ($backbuffer[$j + ($i + $pt1[1]) * $width]))
				continue;
			$backbuffer[$j + ($i + $pt1[1]) * $width] = $zcoord;*/
			
			$red = $num1r + ($num2r - $num1r) * (($j - $num1) / ($num2 - $num1));
			$green = $num1g + ($num2g - $num1g) * (($j - $num1) / ($num2 - $num1));
			$blue = $num1b + ($num2b - $num1b) * (($j - $num1) / ($num2 - $num1));
			
			imagesetpixel($im, $j, $i + $pt1[1], imagecolorallocate($im, $red, $green, $blue));
		}
	}
	
	return $backbuffer;
}

class mesh {
	var $points;
	var $triangle1;
	var $triangle2;
	var $triangle3;
	
	var $scale;
	var $translation;
	
	function render($matrix, $width, $height, $im, $backbuffer, $wireframe) {
		$matrix2 = multiply(multiply($matrix, $this->translation), $this->scale);
	
		for ($i = 0; $i < sizeof($this->triangle1); ++$i) {
			if (!isset($this->triangle1[$i])) continue;
			if (!isset($this->triangle2[$i])) continue;
			if (!isset($this->triangle3[$i])) continue;
			
			$pt1 = $this->points[$this->triangle1[$i]];
			$pt2 = $this->points[$this->triangle2[$i]];
			$pt3 = $this->points[$this->triangle3[$i]];
			
			$tmp1 = $pt1->calculate($matrix2);
			$tmp2 = $pt2->calculate($matrix2);
			$tmp3 = $pt3->calculate($matrix2);
			
			$tmp1[0] = ($tmp1[0] + 1) * $width / 2;
			$tmp1[1] = ($tmp1[1] + 1) * $height / 2;
			$tmp2[0] = ($tmp2[0] + 1) * $width / 2;
			$tmp2[1] = ($tmp2[1] + 1) * $height / 2;
			$tmp3[0] = ($tmp3[0] + 1) * $width / 2;
			$tmp3[1] = ($tmp3[1] + 1) * $height / 2;
			
			$backbuffer = drawtriangle($im, $backbuffer, $tmp1, $tmp2, $tmp3, $width, $height, $wireframe);
		}
	}
	
	function mesh() {
		$this->points = array();
		$this->triangle1 = array();
		$this->triangle2 = array();
		$this->triangle3 = array();
		
		$this->scale = new matrix();
		$this->scale->loadIdentity();
		$this->translation = new matrix();
		$this->translation->loadIdentity();
	}
};

class point {
	var $x;
	var $y;
	var $z;
	
	var $cr;
	var $cg;
	var $cb;
	
	function point($x = 0, $y = 0, $z = 0, $r = 255, $g = 255, $b = 255) {
		$this->x = $x;
		$this->y = $y;
		$this->z = $z;
		$this->cr = $r;
		$this->cg = $g;
		$this->cb = $b;
	}
	
	function calculate($matrix) {
		$retour = array(0, 0, 0, 255, 255, 255);
		$retour[0] = $this->x * $matrix->values[0] + $this->y * $matrix->values[1] + $this->z * $matrix->values[2] + $matrix->values[3];
		$retour[1] = $this->x * $matrix->values[4] + $this->y * $matrix->values[5] + $this->z * $matrix->values[6] + $matrix->values[7];
		$retour[2] = $this->x * $matrix->values[8] + $this->y * $matrix->values[9] + $this->z * $matrix->values[10] + $matrix->values[11];
		$retour[3] = $this->cr;
		$retour[4] = $this->cg;
		$retour[5] = $this->cb;
		return $retour;
	}
};

class matrix {
	var $values;
	
	function get($x, $y) {
		return $y + $x * 4;
	}
	
	function loadIdentity() {
		$this->values = array(1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1);
	}
	
	function projection($angle, $ratio, $zNear, $zFar) {
		$angle = $angle;
		$yScale = atan($angle / 2);
		
		$this->loadIdentity();
		$this->values[0] = $ratio / $yScale;
		$this->values[5] = $yScale;
		$this->values[10] = $zFar / ($zFar - $zNear);
		$this->values[11] = -$zNear * $zFar / ($zFar - $zNear);
		$this->values[14] = 1;
		$this->values[15] = 0;
	}
	
	function lookat($eye, $at, $up) {
		$zaxis = new point();
		$zaxis->x = $eye->x - $at->x; $zaxis->y = $eye->y - $at->y; $zaxis->z = $eye->z - $at->z;
		$dist = sqrt($zaxis->x * $zaxis->x + $zaxis->y * $zaxis->y + $zaxis->z * $zaxis->z);
		$zaxis->x /= $dist; $zaxis->y /= $dist; $zaxis->z /= $dist;
		
		$xaxis = new point();
		$xaxis->x = $up->y * $zaxis->z - $up->z * $zaxis->y;
		$xaxis->y = $up->z * $zaxis->x - $up->x * $zaxis->z;
		$xaxis->z = $up->x * $zaxis->y - $up->y * $zaxis->x;
		$dist = sqrt($xaxis->x * $xaxis->x + $xaxis->y * $xaxis->y + $xaxis->z * $xaxis->z);
		$xaxis->x /= $dist; $xaxis->y /= $dist; $xaxis->z /= $dist;
		
		$yaxis = new point();
		$yaxis->x = $zaxis->y * $xaxis->z - $zaxis->z * $xaxis->y;
		$yaxis->y = $zaxis->z * $xaxis->x - $zaxis->x * $xaxis->z;
		$yaxis->z = $zaxis->x * $xaxis->y - $zaxis->y * $xaxis->x;
		
		$dot1 = $xaxis->x * $eye->x + $xaxis->y * $eye->y + $xaxis->z * $eye->z;
		$dot2 = $yaxis->x * $eye->x + $yaxis->y * $eye->y + $yaxis->z * $eye->z;
		$dot3 = $zaxis->x * $eye->x + $zaxis->y * $eye->y + $zaxis->z * $eye->z;

		$this->loadIdentity();
		$this->values[0] = $xaxis->x;
		$this->values[1] = $xaxis->y;
		$this->values[2] = $xaxis->z;
		$this->values[3] = -$dot1;
		$this->values[4] = $yaxis->x;
		$this->values[5] = $yaxis->y;
		$this->values[6] = $yaxis->z;
		$this->values[7] = -$dot2;
		$this->values[8] = $zaxis->x;
		$this->values[9] = $zaxis->y;
		$this->values[10] = $zaxis->z;
		$this->values[11] = -$dot3;
		$this->values[15] = 1;
	}
	
	function translate($x, $y, $z) {
		$this->loadIdentity();
		$this->values[3] = $x;
		$this->values[7] = $y;
		$this->values[11] = $z;
	}
	
	function scale($x, $y, $z) {
		$this->loadIdentity();
		$this->values[0] = $x;
		$this->values[5] = $y;
		$this->values[10] = $z;
	}
	
	function matrix() {
		$this->values = array(0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
	}
};

function multiply($matrix1, $matrix2) {
	$retour = new matrix();
		
	for ($i = 0; $i < 4; ++$i)
		for ($j = 0; $j < 4; ++$j)
			for ($k = 0; $k < 4; ++$k)
				$retour->values[$retour->get($i, $j)] += $matrix1->values[$matrix1->get($i, $k)] * $matrix2->values[$matrix2->get($k, $j)];
	return $retour;
}

$im = imagecreatetruecolor($width, $height);

$fond = imagecolorallocate($im, 0, 0, 0);
$blanc = imagecolorallocate($im, 255, 255, 255);

$backbuffer = array($width * $height);
for ($i = 0; $i < $width * $height; ++$i)
	$backbuffer[$i] = $clipping;

$projection = new matrix();
$projection->projection(45, $width / $height, 1, $clipping);

$view = new matrix();
$view->lookat(new point(2.5, 0.7, 1.3), new point(0, 0, 0), new point(0, 1, 0));

$matrice = multiply($projection, $view);

$cube = new mesh();

$taille = 0.5;
$cube->points[0] = new point($taille, $taille, $taille, 255, 0, 0);
$cube->points[1] = new point(-$taille, $taille, $taille, 255, 128, 128);
$cube->points[2] = new point(-$taille, -$taille, $taille, 200, 200, 0);
$cube->points[3] = new point($taille, -$taille, $taille, 255, 255, 60);
$cube->points[4] = new point($taille, -$taille, -$taille, 128, 128, 0);
$cube->points[5] = new point($taille, $taille, -$taille, 200, 0, 0);
$cube->points[6] = new point(-$taille, $taille, -$taille, 255, 45, 45);
$cube->points[7] = new point(-$taille, -$taille, -$taille, 255, 255, 128);

$cube->triangle1[0] = 0; $cube->triangle2[0] = 1; $cube->triangle3[0] = 2;
$cube->triangle1[1] = 0; $cube->triangle2[1] = 2; $cube->triangle3[1] = 3;
$cube->triangle1[2] = 4; $cube->triangle2[2] = 5; $cube->triangle3[2] = 7;
$cube->triangle1[3] = 5; $cube->triangle2[3] = 6; $cube->triangle3[3] = 7;
$cube->triangle1[4] = 0; $cube->triangle2[4] = 3; $cube->triangle3[4] = 4;
$cube->triangle1[5] = 0; $cube->triangle2[5] = 4; $cube->triangle3[5] = 5;
$cube->triangle1[6] = 1; $cube->triangle2[6] = 2; $cube->triangle3[6] = 7;
$cube->triangle1[7] = 1; $cube->triangle2[7] = 6; $cube->triangle3[7] = 7;
$cube->triangle1[8] = 0; $cube->triangle2[8] = 1; $cube->triangle3[8] = 6;
$cube->triangle1[9] = 0; $cube->triangle2[9] = 5; $cube->triangle3[9] = 6;
$cube->triangle1[10] = 2; $cube->triangle2[10] = 3; $cube->triangle3[10] = 7;
$cube->triangle1[11] = 3; $cube->triangle2[11] = 4; $cube->triangle3[11] = 7;

$cube->scale->scale(0.5, 0.5, 0.5);
$cube->translation->translate(0.2, 0.5, 0.3);

$cube->render($matrice, $width, $height, $im, $backbuffer, $wireframe);

imagejpeg($im);

 Conclusion

J'utilise les mêmes matrices que DirectX

Voici le site qui contient les explications :
http://aaprog.free.fr/?page=php/examples/3dengin e1
http://aaprog.free.fr/?page=php/examples/3dengi ne2

Si un jour je supprime le site je mettrai ces explications dans une page html dans le zip
Le zip, qui d'ailleurs contient plusieurs fichiers .php
Le dernier est celui qui a le plus grand numéro (ils s'appelent tous moteur3d#.php où # est un nombre)
J'ai mis les anciennes versions tout simplement pour que vous arriviez à comprendre au fur et à mesure

 Fichier Zip

Les Membres Club peuvent télécharger directement un fichier contenu dans le zip sans télécharger le zip en entier !

Télécharger le zip


 Historique

29 juillet 2005 11:02:18 :
Ajout de l'affichage des faces (colorées)
01 août 2005 14:25:02 :
Les translations fonctionnent (j'avais mis les coordonnées sur la dernière colonne de la matrice au lieu de les mettre sur la dernière ligne) et j'ai rajouté des liens vers l'aide pour comprendre la source
01 août 2005 14:38:34 :
Rajout du mode fil de fer (il suffit de mettre $wireframe à true tout au début)
09 octobre 2005 08:22:08 :
Modification des URLs pour les explications
19 décembre 2005 16:50:36 :
Ajout des mots clés

 Sources du même auteur

Source avec Zip ENVOI D'UN MESSAGE SUR UN HUB (PROTOCOLE DE DC++)

 Sources de la même categorie

EXEMPLE D'APPLICATION DE L'ALGORITHME DE DIJKSTRA EN PHP par philtr8
CLEF POUR EAN 13 ET 14 par RaftY
FONCTION DE CALCUL DU NOMBRE DE DUEL UNIQUE POUR UN NOMBRE N... par mtrix000
Source avec Zip Source avec une capture TRIANGLE DE PASCAL ET SON ÉQUATION par vendeeHdLR89
Source avec Zip CONVERTISSEUR LAMBERT2 ÉTENDU EN COORDONNÉE GÉOGRAPHIQUE (LO... par varfendell

 Sources en rapport avec celle ci

Source avec Zip Source avec une capture MOTEUR DE RECHERCHE SUR BASE MYSQL FULLTEXT ET BOOLEAN AVEC ... par cod57
Source avec Zip MYGGL GOOGLE API CLASS FOR BEGINERZ par lezj
Source avec Zip Source avec une capture MOTEUR DE RENDU DE FICHIER 3D (WAVEFRONT OBJ POUR LE MOMENT)... par ciberrique
Source avec Zip Source avec une capture METTEZ VOS IMAGES OU VOS PHOTOS EN 3D ; EN PERSPECTIVE par zulrigh
Source avec Zip Source avec une capture UN GRAPHIQUE CAMEMBERT EN 3D par pgpp

Commentaires et avis

Commentaire de vilhjalms le 23/07/2005 10:15:51

Saell og blesud

Belle source ... ;-) De mémoire mon grand frère en avait fait un également mais basé sur la librairie ImageMagik ... Il m'a toujours dit qu'elle était plus évolué et surtout plus souple ? ...

Vilhjálms Sigurðsdóttir aka Frëyjá

Commentaire de malalam le 23/07/2005 11:47:34 administrateur CS

Hello,

je n'ai pas teste. Je viens d'essayer de noter, si ca n'a pas marche je noterai lundi.
Je testerai aussi lundi, mais je passais juste pour dire que je suis impressionne! ne serait-ce que pour l'idee. Et je te fais confiance sur le fait que cela marche.
Je ne pense pas que ce soit tres utile en php, ceci dit...;-)
Mais...jolie source, oui, tres. je mets (mettrai) 10.

Commentaire de LocalStone le 23/07/2005 13:38:13

Vilhjalms, est-ce que tu pourrais poster la source de ton grand frère pour comparer ?
++ !
L.S.

Commentaire de CyberP le 23/07/2005 20:02:26

Merci :)
Sinon je connais pas ImageMagik...

Sinon quand je vais modifier la source je laisserai une ancienne "version" (affichage des arêtes par exemple) dans le zip pour que ceux qui veulent comprendre puissent le faire au fur et à mesure

Commentaire de Taka_s_tiger le 27/07/2005 16:40:23

moi aussi j'ai commencé a faire un moteur 3d...

http://takastiger.free.fr/3d.php

j'ai aussi la version C++ en construction...

Commentaire de malalam le 28/07/2005 10:59:45 administrateur CS

Taka => tres joli! :-)Et plutot rapide, pour du php.

Commentaire de CyberP le 28/07/2005 14:46:28

ah tu as mis les faces dans une seule couleur
personnelement j'essaye de mettre un dégradé (comme en opengl/directx) mais je n'y arrive pas

par contre ton code a l'air compliqué

Commentaire de Taka_s_tiger le 29/07/2005 01:40:32

en php...c'est dur
j'utilise imagefilledpolygone() alors je controle pas le remplissage au dela de sa couleur

le code est pas compliqué quand on l'a fait :) mais j'imagine que le nom des variable et la disposition aide pas....

les modèles sont stocké dans les fichiers cube.mdl, pyra.mdl et sheep.mdl
et la C'est encore moins lisible...mais c'est fait (j'ai pas fait de test avancé sur la technique...) pour réduire le travail a fournir par le code PHP

l'affichage se fait soit par ligne (fil de fer) ou par polygone..pour les polygone il faut calculé la distance entre "la camera" et le polygone pour commencé a dessiné ceux en arrière plan et finir par ceux en avant plan

Commentaire de CyberP le 29/07/2005 09:39:53

pour l'affichage, un zbuffer c'est plus simple d'après moi (le problème est que ça calcule la coordonnée z des points 2d de la même façon que ça calcule la couleur, et comme les couleurs ne marchent pas....

Commentaire de MATHIS49 le 31/07/2005 22:57:17

ca manque cruellement de commentaires, dommage :'

Commentaire de CyberP le 01/08/2005 07:07:05

oui je voulais expliquer toute la source mais j'ai pas vraiment le temps et l'envie, donc je ferai ça un jour

Commentaire de CyberP le 01/08/2005 14:47:19

Voilà j'ai mis à jour...
Notez que le premier lien que j'ai mis pour les explications n'est pas tout à fait terminé au moment où j'ai fait la mise à jour mais ça ne devrait pas tarder. Le deuxième n'est pas encore fait et je le ferai quand le backbuffer marchera (histoire d'avoir un beau cube)

Commentaire de MATHIS49 le 01/08/2005 18:30:21

Super ton site, bravo ;)
Par contre j'ai juste un probleme avec ton script pour le BMP , sou s firefox jai des caracteres et sous IE l'image ne s'affiche pas
: http://angersbouge.com/Projet%20BMP/

Commentaire de CyberP le 02/08/2005 09:29:40

en effet c'est un problème avec les bmp 8 (je viens de le remarquer)
je vais essayer de dépanner
merci

Commentaire de spyro666 le 05/05/2006 09:39:31

J'ai un tout autre problème avec ce script : il ne s'exécute tout simplement pas :(... quand j'affiche la page tel quel il m'affiche le code et quand je donne la page comme source d'image ça ne fonctionne pas non plus. Tu pourrais me donner un exemple d'implémentation qui fonctionne ?Merci

Commentaire de CyberP le 05/05/2006 17:11:28

ben il faut mettre les balises php autour
<?php tout devant et ?> à la fin

 Ajouter un commentaire


Discussions en rapport avec ce code source dans le forum

Bug EasyPHP d'urgence !!! [ par Clem ] Je pose ce message car il y a plus de chances ici que sur le forum easyphp.J'ai un bug avec easyphp. Vous avez certainemant remarqué qu'il y a un bout Bug EasyPHP d'urgence !!! [ par Clem ] Je pose ce message car il y a plus de chances ici que sur le forum easyphp.J'ai un bug avec easyphp. Vous avez certainemant remarqué qu'il y a un bout excuser moi vous avez une idee ?. [ par flashx ] flashxsalut ya t'il quelqu'un qui a une idee pour faire un robot de moteur de recherche car je sais pas comment ca marche de trop la je vais cree un m moteur de recherche alphabétique [ par princeg ] Quelqu'un peut-il m'aider, please? je voudrais créer un moteur de recherche alphabétique comme celui présent sur le site www.zouklist.fr.st et en plu générer des miniatures avec gd 1.6 [ par vegetaline ] muhaha alors là c'est rigolo, un super défi pour les programmeurs fous!ok j'ai le code pour générer des miniatures grâce au php, mais ça marche qu'ave moteur de recherche [ par fatNugly ] Bonjour, j'ai des petites questionsle quel des languages suivant php, c, est il le plus adequat pour faire un moteur de recherche dans une page?? la c moteur de recherche [ par fatNugly ] Bonjour, j'ai des petites questionsle quel des languages suivant php, c, est il le plus adequat pour faire un moteur de recherche dans une page??la cr Installation GD 2.0--> Help !! [ par SuperDede ] comment on fait pour installer GD 2.0 sur apache je suis sous Windows et avec Easy PhPmerci ! Creation d'un moteur de recherche [ par Coundelitch ] bonjour !Je dois créer un moteur de recherche en PHP. Ce moteur cherchera dans un dossier des fichiers au format HTML.C'est peut-etre simple mais le p moteur de recherche à partir d'un formulaire [ par cindy648 ] Je dois faire un moteur de recherche en php et je n'y connais rien du tout, pouvez-vous m'aider??? 8)Ce moteur de recherche devra répondre aux requète


Nos sponsors


Sondage...

CalendriCode

Février 2012
LMMJVSD
  12345
6789101112
13141516171819
20212223242526
272829    

Consulter la suite du CalendriCode

Photothèque

 
Développement réalisé par Nicolas SOREL (Nix) avec l'aide de : Cyril DURAND et Emmanuel (EBArtSoft), Merci à Vincent pour ses précieux conseils.
CodeS-SourceS.com© Toute reproduction même partielle est interdite sauf accord écrit du Webmaster
CodeS-SourceS.com© est une marque déposée tous droits réservés

Google Coop CodeS-SourceS Google Coop CodeS-SourceS
Temps d'éxécution de la page : 4,883 sec (3)

Nous contacter | Annoncer sur CodeS-SourceS | Mentions légales