Графика DirectX в Delphi
Шрифт:
Diffuse.R := 1.0; // Цвет источника
Diffuse.G := 1.0;
Diffuse.В := 1.0;
Specular := Diffuse; // Дополнительные параметры
Ambient := Diffuse;
Position := DSDVector(0.0, 0.0, 0.0); // Позиция в пространстве
AttenuationO := 1.0; // Коэффициенты закона ослабления
Attenuationl := 1.0;
Attenuation2 := 1.0;
Range := 2.5; // Расстояние, задающее область освещенности
end;
FD3DDevice.SetLight(0, Light);
FDSDDevice.LightEnable(0, True);
end;
Первое
procedure TfrmD3D.DrawScene;
var
matTranslate, matScale : TDSDMatrix;
begin
// Вычисляем текущее положение источника
Light.Position := DSDVector(0.0, cos (Angle) * 2, 0.0);
with FDSDDevice do begin
// Возвращаем мировую систему координат
SetTransform(D3DTS_WORLD, IdentityMatrix);
// Устанавливаем источник света в новом положении
SetLight(0, Light);
DrawPrimitive(D3DPT_TRIANGLELIST, 0, 864); // Вывод тора
end;
// Источник света будет внутри сферы
Light.Position := D3DVector(0.О, 0.0, 0.0);
// Матрица трансформаций для сферы
SetTranslateMatrix(matTranslate, 0.0, cos (Angle) * 2, 0.0);
SetScaleMatrix(matScale, 0.1, 0.1, 0.1);
with FDBDDevice do begin
SetTransform(D3DTS_WORLD, MatrixMul(matScale, matTranslate));
SetLight(0, Light);
DrawPrimitive(D3DPT_TRIANGLELIST, 864 * 3, 1200);
end;
end;
Позже мы подробнее поговорим о полях структуры, связанной с источником света, а сейчас попробуем построить модель комнаты, чтобы убедиться, что использование точечного источника света значительно повышает реализм изображений. В проекте каталога Ех02 рисуется комната, в ее центре находится конус, вокруг которого вращается сфера (рис. 10.2).
Матрицы трансформаций полностью заполняются один раз, в начале
procedure TfrmD3D.FormCreate(Sender: TObject);
var
hRet : HRESULT;
matView, matProj : TD3DMatrix;
matRotate, matTranslate, matScale : TD3DMatrix;
begin
hRet := InitDSD;
if Failed (hRet) then ErrorOut ('InitDBD', hRet);
hRet := InitVB;
if Failed (hRet) then ErrorOut ( ' InitVertex' , hRet);
// Голубоватый материал конуса
MaterialConus := InitMaterial(0, 0.5, 1, 0) ;
// Белый материал стен комнаты
MaterialWhite := InitMaterial(1, 1, I, 0);
// Светло-коричневый материал сферы
MaterialSphere := InitMaterial(1, 0.5, 0, 0) ;
// Точка зрения задается один раз
SetViewMatrix(matview, D3DVector(0, 0, 2.577), D3DVector(0, 0, -5),
D3DVector(0, 1, 0));
FD3DDevice.SetTransform(D3DTS_VIEW, matView);
// Матрица проекций
SetProjectionMatrix (matProj, 1, 1, 1, 10);
FD3DDevice.SetTransform(D3DTS_PROJECTION, matProj);
// Инициализация источников света
SetupLights;
// Поворот конуса вокруг оси X
SetRotateXMatrix(matRotate, -Pi / 2);
// Переносим конус, его вершина в центре сцены
SetTranslateMatrixfmatTranslate, 0.0, -1.0, 0.0);
// Масштабируем конус
SetScaleMatrixfmatScale, 0.25, 1.0, 0.2);
// Матрица трансформаций конуса вычисляется один раз
matCone := MatrixMul(matScale, MatrixMul(matTranslate, matRotate));
// Инициализация матрицы трансформаций сферы
matSphere := IdentityMatrix;
// Переносим сферу по оси Y
matSphere._42 := -0.5;
end;
Я ввел в сцену четыре источника света. Три точечных источника предназначены для освещения стен комнаты, конус и сфера освещаются направленным источником света:
procedure TfrmDSD.SetupLights,
var
LightO : TD3DLight8;
Lightl : TD3DLight8;
Light2 : TD3DLight8;
Light3 : TD3DLight8;
begin
ZeroMemory(@LightO, SizeOf(LightO));
with LightO do begin
Type := D3DLIGHT POINT;
Diffuse.r := 0.4; // Поскольку присутствует три источника,
Diffuse.g := 0.4; // их яркость задается небольшой
Diffuse.b := 0.4;
Specular := Diffuse;
Ambient := Diffuse;
Position := D3DVector(0.5, 0.75, 1.5);
AttenuationO := 1.0;
Attenuationl := 1.0;
Attenuation2 := 0.0;
Range := 2.56; end;
ZeroMemory(@Light1, SizeOf(Light1));
with Lightl do begin
_Type := D3DLIGHT_POINT;
Diffuse.r := 0.4;