Coding a radar, and a bunch of other stuff perhaps.

All topics about ZGameEditor goes here.

Moderator: Moderators

Post Reply
jinxtengu
Posts: 80
Joined: Wed Oct 14, 2009 2:05 pm
Contact:

Coding a radar, and a bunch of other stuff perhaps.

Post by jinxtengu » Thu Sep 26, 2019 8:31 am

Hey all,
I am interested in coding a radar showing the positions of enemies in relation to the player, similar to the old game Battlezone

here's a screenshot of battlezone, you see the radar in the top right hand of the screen.
Image

Does anyone know the formula to achieve this?
I'm thinking it requires some kind of atan biz, syncing objects that have their position divided by the size of the radar screen in relation to the full screen.

Also another question, and I believe I have asked this before but I don't have a fully working code to do this. Anyhow can someone supply me with a code to make an object face the camera (and centered in the view of the camera) at all times,
the primary use of this would be for a Gui or a cross hair.
:)
Btw I plan to release some cool games made with z game editor real soon. Hoping I can get more support to allow me to build better stuff.
The past support from Kjell and Ville has been invaluable :D :D

User avatar
Kjell
Posts: 1715
Joined: Sat Feb 23, 2008 11:15 pm

Re: Coding a radar, and a bunch of other stuff perhaps.

Post by Kjell » Thu Sep 26, 2019 2:03 pm

Hi jinxtengu,
jinxtengu wrote:
Thu Sep 26, 2019 8:31 am
I am interested in coding a radar showing the positions of enemies in relation to the player, similar to the old game Battlezone
Personally i wouldn't call what Battlezone 2000 on ATARI Lynx does a "radar" .. it's more like a mini-map. A radar only updates the location of objects it detects once per revolution, while in Battlezone 2000 objects are updated continuously. Anyway, semantics aside .. here's a example ( use arrow keys to navigate ).

Code: Select all

<?xml version="1.0" encoding="iso-8859-1" ?>
<ZApplication Name="App" Caption="Radar" ScreenMode="0" CameraPosition="0 0.25 0" LightPosition="0 1 0.25" ViewportRatio="3" FileVersion="2">
  <OnLoaded>
    <ZExternalLibrary ModuleName="opengl32">
      <Source>
<![CDATA[//

void glViewport(int x, int y, int width, int height){}

//

void glBegin(int mode){}
void glEnd(){}

void glColor3f(float red, float green, float blue){}
void glTexCoord2f(float s, float t){}
void glVertex2f(float x, float y){}]]>
      </Source>
    </ZExternalLibrary>
    <ZExpression>
      <Expression>
<![CDATA[//

for(int i=0; i<8; i++)
{
  Enemy.Position.X = floor(rnd()*16)-7.5;
  Enemy.Position.Z = floor(rnd()*16)-7.5;

  Enemy.Rotation.Y = floor(rnd()*4)*0.25;

  createModel(Enemy);
}]]>
      </Expression>
    </ZExpression>
  </OnLoaded>
  <OnUpdate>
    <Repeat Name="AxisRepeat" Count="2" WhileExp="//">
      <OnIteration>
        <ZExpression>
          <Expression>
<![CDATA[//

int i = AxisRepeat.Iteration;

//

Axis[i] = 0;

//

AxisPositive.CharCode = AxisMap[i,0];
AxisNegative.CharCode = AxisMap[i,1];]]>
          </Expression>
        </ZExpression>
        <KeyPress Name="AxisPositive" CharCode="38">
          <OnPressed>
            <ZExpression>
              <Expression>
<![CDATA[//

Axis[AxisRepeat.Iteration]++;]]>
              </Expression>
            </ZExpression>
          </OnPressed>
        </KeyPress>
        <KeyPress Name="AxisNegative" CharCode="40">
          <OnPressed>
            <ZExpression>
              <Expression>
<![CDATA[//

Axis[AxisRepeat.Iteration]--;]]>
              </Expression>
            </ZExpression>
          </OnPressed>
        </KeyPress>
      </OnIteration>
    </Repeat>
    <ZExpression>
      <Expression>
<![CDATA[// Declare local variables

float t, a, sinA, cosA, x, z, dx, dz, sx, sy;

// Cache variables for performance & convenience

t = App.DeltaTime;

// Camera controls

App.CameraRotation.Y += Axis[0]*0.125*t;

a = App.CameraRotation.Y*PI*2;

sinA = sin(a);
cosA = cos(a);

App.CameraPosition.X += Axis[1]*sinA*t;
App.CameraPosition.Z -= Axis[1]*cosA*t;

// More caching ;-)

x = App.CameraPosition.X;
z = App.CameraPosition.Z;

// Calculate radar dots

model[] enemies;
getModels(enemies, 0);

Dot.SizeDim1 = 0;

for(int i=0; i<enemies.SizeDim1; i++)
{
  dx = enemies[i].Position.X-x; // Calculate distance from enemy to camera
  dz = enemies[i].Position.Z-z;

  sx = (dx*cosA+dz*sinA)*0.125; // Calculate screen-space coordinate of dot
  sy = (dx*sinA-dz*cosA)*0.125;

  if(sqrt(sx*sx+sy*sy) < 0.95)  // If dot is within radius add to Dot array
  {
    int d = Dot.SizeDim1++;

    Dot[d,0] = sx;
    Dot[d,1] = sy;
  }
}]]>
      </Expression>
    </ZExpression>
  </OnUpdate>
  <OnRender>
    <Group Comment="Floor">
      <Children>
        <UseMaterial Material="FloorMaterial"/>
        <RenderMesh Mesh="FloorMesh"/>
      </Children>
    </Group>
    <Group Comment="Radar">
      <Children>
        <ZExpression>
          <Expression>
<![CDATA[// Reset matrices

mat4 m;

for(int i=0; i<4; i++)
{
  m[i,i] = 1;
}

setMatrix(0, m);
setMatrix(1, m);

// Set viewport to top-right corner ( size based on vertical resolution )

int s = App.ViewportHeight/4;

glViewport(App.ViewportX+App.ViewportWidth-s, App.ViewportY+App.ViewportHeight-s, s, s);]]>
          </Expression>
        </ZExpression>
        <UseMaterial Material="CircleMaterial"/>
        <RenderMesh Mesh="CircleMesh"/>
        <UseMaterial Material="DotMaterial"/>
        <Repeat Name="DotRepeat">
          <OnIteration>
            <ZExpression>
              <Expression>
<![CDATA[//

int i = DotRepeat.Iteration;

//

DotTransform.Translate.X = Dot[i,0];
DotTransform.Translate.Y = Dot[i,1];]]>
              </Expression>
            </ZExpression>
            <RenderTransformGroup Name="DotTransform" Translate="0.4579 0.4321 0">
              <Children>
                <RenderMesh Mesh="DotMesh"/>
              </Children>
            </RenderTransformGroup>
          </OnIteration>
          <WhileExp>
<![CDATA[//

return Iteration < Dot.SizeDim1;]]>
          </WhileExp>
        </Repeat>
        <ZExpression>
          <Expression>
<![CDATA[// Reset viewport

glViewport(App.ViewportX, App.ViewportY, App.ViewportWidth, App.ViewportHeight);]]>
          </Expression>
        </ZExpression>
      </Children>
    </Group>
  </OnRender>
  <Content>
    <Group Comment="Axis">
      <Children>
        <Array Name="Axis" SizeDim1="2"/>
        <Array Name="AxisMap" Type="4" Dimensions="1" SizeDim1="2" SizeDim2="2" Persistent="255">
          <Values>
<![CDATA[78DA535755D300000183009B]]>
          </Values>
        </Array>
      </Children>
    </Group>
    <Group Comment="Floor">
      <Children>
        <Mesh Name="FloorMesh">
          <Producers>
            <MeshBox Scale="8 8 1" Grid2DOnly="255"/>
            <MeshExpression AutoNormals="0" HasTexCoords="255">
              <Expression>
<![CDATA[//

TexCoord.X = V.X*0.5;
TexCoord.Y = V.Y*0.5;

//

V.Z = -V.Y;
V.Y =      0;
V.X =  V.X;]]>
              </Expression>
            </MeshExpression>
          </Producers>
        </Mesh>
        <Bitmap Name="FloorBitmap" Width="2" Height="2" Filter="1">
          <Producers>
            <BitmapExpression>
              <Expression>
<![CDATA[//

if(X+Y != 1)
{
  Pixel.R = 1;
  Pixel.G = 1;
  Pixel.B = 1;
}
else
{
  Pixel.R = 0;
  Pixel.G = 0;
  Pixel.B = 1;
}]]>
              </Expression>
            </BitmapExpression>
          </Producers>
        </Bitmap>
        <Material Name="FloorMaterial" Shading="1" Light="0">
          <Textures>
            <MaterialTexture Texture="FloorBitmap" TextureWrapMode="1" TexCoords="1"/>
          </Textures>
        </Material>
      </Children>
    </Group>
    <Group Comment="Enemy">
      <Children>
        <Model Name="Enemy" Position="1.5 0 7.5" Rotation="0 0.25 0">
          <OnRender>
            <UseMaterial Material="EnemyMaterial"/>
            <RenderMesh Mesh="EnemyMesh"/>
          </OnRender>
        </Model>
        <Mesh Name="EnemyMesh">
          <Producers>
            <MeshImport HasVertexColors="1">
              <MeshData>
<![CDATA[78DAE590BD4A034114858F31092AFE4410C14EC156B00F9880AD4F60B59585557C03CB6DC45E84B54865E503046D2C17B6B50B2858098A26B8A8C9F1FECC689EC0C65DE6CCDDC3CC77EEDD36804DE8737C6D1B5E746F01173B40A78564F7F6E48199E9E9C67DB740C774FBF270F549FDFD2B20DF2359A883844C53D29C8CEC35D5E935D551BA2A6FD274EB0E6DD5409E7062A272B416BE67159E38C1376648B11E3CDD133D2BF49345FDE94766393AD7595CBB45986E1D38780C34278873B6C6BEA9277A7A5F4FFA1F709A137CA240F6FE93E8081F91206ACC5FBED01873454327D3A8C83BE6980D34B022F5BBD46FFCE288339843C90FCE62090B781677C8AADC989245714BD6F0C945D4C4A962C0D2EE8C5891EF79BC72C03A968DA909AAF53FAAF33CFFD7EB1BDD01E882]]>
              </MeshData>
            </MeshImport>
          </Producers>
        </Mesh>
        <Material Name="EnemyMaterial" Shading="1" DrawBackFace="255"/>
      </Children>
    </Group>
    <Group Comment="Radar">
      <Children>
        <Group Comment="Dot">
          <Children>
            <Array Name="Dot" Dimensions="1" SizeDim1="5" SizeDim2="2"/>
            <Mesh Name="DotMesh">
              <Producers>
                <MeshBox Scale="0.05 0.05 1" Grid2DOnly="255"/>
              </Producers>
            </Mesh>
            <Bitmap Name="DotBitmap" Filter="2">
              <Producers>
                <BitmapExpression>
                  <Expression>
<![CDATA[//

float u, v;

u = 0.5-X;
v = 0.5-Y;

Pixel.R = 1;
Pixel.A = 16-sqrt(u*u+v*v)*32;]]>
                  </Expression>
                </BitmapExpression>
              </Producers>
            </Bitmap>
            <Material Name="DotMaterial" Shading="1" Light="0" Blend="1" ZBuffer="0">
              <Textures>
                <MaterialTexture Texture="DotBitmap" TexCoords="1"/>
              </Textures>
            </Material>
          </Children>
        </Group>
        <Group Comment="Circle">
          <Children>
            <Mesh Name="CircleMesh">
              <Producers>
                <MeshBox Grid2DOnly="255"/>
              </Producers>
            </Mesh>
            <Bitmap Name="CircleBitmap" Width="128" Height="128" Filter="2">
              <Producers>
                <BitmapExpression>
                  <Expression>
<![CDATA[//

float u, v, s;

u = 0.5-X;
v = 0.5-Y;

s = sqrt(u*u+v*v);

Pixel.R = 1;
Pixel.G = 1;
Pixel.B = 1;
Pixel.A = clamp(32-s*64, 0, 0.5) - clamp(1-s*64, 0, 1);]]>
                  </Expression>
                </BitmapExpression>
              </Producers>
            </Bitmap>
            <Material Name="CircleMaterial" Light="0" Blend="1" ZBuffer="0">
              <Textures>
                <MaterialTexture Texture="CircleBitmap" TexCoords="1"/>
              </Textures>
            </Material>
          </Children>
        </Group>
      </Children>
    </Group>
  </Content>
</ZApplication>
jinxtengu wrote:
Thu Sep 26, 2019 8:31 am
Also another question, and I believe I have asked this before but I don't have a fully working code to do this. Anyhow can someone supply me with a code to make an object face the camera (and centered in the view of the camera) at all times, the primary use of this would be for a Gui or a cross hair.
You did ask this before yes .. here is the thread :wink:

K

User avatar
VilleK
Site Admin
Posts: 2025
Joined: Mon Jan 15, 2007 4:50 pm
Location: Stockholm, Sweden
Contact:

Re: Coding a radar, and a bunch of other stuff perhaps.

Post by VilleK » Fri Sep 27, 2019 7:50 am

Every time someone asks Kjell for help he ends up writing an example that is already half the game :). Looks real nice. Great work as usual Kjell!

Post Reply