• Announcements

    • khawk

      Download the Game Design and Indie Game Marketing Freebook   07/19/17

      GameDev.net and CRC Press have teamed up to bring a free ebook of content curated from top titles published by CRC Press. The freebook, Practices of Game Design & Indie Game Marketing, includes chapters from The Art of Game Design: A Book of Lenses, A Practical Guide to Indie Game Marketing, and An Architectural Approach to Level Design. The GameDev.net FreeBook is relevant to game designers, developers, and those interested in learning more about the challenges in game development. We know game development can be a tough discipline and business, so we picked several chapters from CRC Press titles that we thought would be of interest to you, the GameDev.net audience, in your journey to design, develop, and market your next game. The free ebook is available through CRC Press by clicking here. The Curated Books The Art of Game Design: A Book of Lenses, Second Edition, by Jesse Schell Presents 100+ sets of questions, or different lenses, for viewing a game’s design, encompassing diverse fields such as psychology, architecture, music, film, software engineering, theme park design, mathematics, anthropology, and more. Written by one of the world's top game designers, this book describes the deepest and most fundamental principles of game design, demonstrating how tactics used in board, card, and athletic games also work in video games. It provides practical instruction on creating world-class games that will be played again and again. View it here. A Practical Guide to Indie Game Marketing, by Joel Dreskin Marketing is an essential but too frequently overlooked or minimized component of the release plan for indie games. A Practical Guide to Indie Game Marketing provides you with the tools needed to build visibility and sell your indie games. With special focus on those developers with small budgets and limited staff and resources, this book is packed with tangible recommendations and techniques that you can put to use immediately. As a seasoned professional of the indie game arena, author Joel Dreskin gives you insight into practical, real-world experiences of marketing numerous successful games and also provides stories of the failures. View it here. An Architectural Approach to Level Design This is one of the first books to integrate architectural and spatial design theory with the field of level design. The book presents architectural techniques and theories for level designers to use in their own work. It connects architecture and level design in different ways that address the practical elements of how designers construct space and the experiential elements of how and why humans interact with this space. Throughout the text, readers learn skills for spatial layout, evoking emotion through gamespaces, and creating better levels through architectural theory. View it here. Learn more and download the ebook by clicking here. Did you know? GameDev.net and CRC Press also recently teamed up to bring GDNet+ Members up to a 20% discount on all CRC Press books. Learn more about this and other benefits here.

Steve_Segreto

Members
  • Content count

    681
  • Joined

  • Last visited

Community Reputation

2080 Excellent

About Steve_Segreto

  • Rank
    Advanced Member

Personal Information

  • Location
    Redmond, Washington
  1. Ask your programmers to add asserts that fast_fail in their code and then run your test code with asserts enabled, capture the crash dump plus heap and link it to the bug for the programmer to investigate the failed assert at their leisure. If possible link a keystroke or other input to an assert that always crashes the program. Use this only if you are experiencing a show-stopping glitch that doesn't actually trip an assert or crash in any other way.
  2. I was able to create indexed triangle vertex arrays with 16-bit index format in Bullet by calling the 0-argument constructor and specifying the stride manually. typedef unsigned short IndexFormat; pMesh->m_pTriMesh = new btTriangleIndexVertexArray(); btIndexedMesh iMesh; iMesh.m_numTriangles = pMesh->m_numFaces; iMesh.m_triangleIndexBase = (const unsigned char *)pMesh->m_pIndices; iMesh.m_triangleIndexStride = 3 * sizeof(IndexFormat); iMesh.m_numVertices = pMesh->m_numVertices; iMesh.m_vertexBase = (const unsigned char *)pMesh->m_pVertices; iMesh.m_vertexStride = sizeof(D3DXVECTOR3); pMesh->m_pTriMesh->addIndexedMesh( iMesh, PHY_SHORT );
  3. struct line_vertex {     float x, y, z;     D3DXCOLOR color; }; const DWORD line_fvf = D3DFVF_XYZ | D3DFVF_DIFFUSE;   Your color should be a DWORD ARGB since you used D3DFVF_DIFFUSE
  4. Do you call SetTrackAnimationSet first to put a different animation set on track 1?   Also have you tried UnkeyAllTrackEvents to sort of empty the anim mixer out first?
  5. Your debug configuration may have iterator debugging turned on which is ridiculously slow compared to how useful it is (in addition to the fact that all memory allocations use the debug heap which is also slow, but at least useful).   Follow this mess and turn all of the iterator debugging off and see if Debug configuration is acceptably fast again.   https://msdn.microsoft.com/en-us/library/aa985982.aspx
  6. You're using D3DXCompileShader and hence D3DX, which is an optional addition to DirectX and thus requires the redist (https://www.microsoft.com/en-us/download/details.aspx?id=8109)   Basically your users need the suite of D3DX9_**.dll's (but probably d3dx9_43.dll and d3dx9_31.dll would be good enough, depending if you passed the legacy 9_31 flag to the D3DXCompileShader call). Also as mentioned you should log both the HR of the call and the LPD3DXBUFFER for the error message.   d3dx9_24.dll d3dx9_25.dll d3dx9_26.dll d3dx9_27.dll d3dx9_28.dll d3dx9_29.dll d3dx9_30.dll d3dx9_31.dll d3dx9_32.dll d3dx9_33.dll d3dx9_34.dll d3dx9_35.dll d3dx9_36.dll D3DX9_37.dll D3DX9_38.dll D3DX9_39.dll D3DX9_40.dll D3DX9_41.dll D3DX9_42.dll D3DX9_43.dll
  7. Your "Marien_text" looks like it's nearly in the same position, are you sure you're taking into account the scale and rotation specified in the original world transform for the car?
  8. Hi this is a great list of questions!   In my experience constants buffer are the best way in dx9, 10 and 11 to send the updated bone transforms to the shader for the vertex skinning. A buffer of about 50 or less 4x4 matrices should be able to handle most (> 90%) of the low to mid class game engine skinned actors in one draw call (I can confirm this for Dark Age of Camelot, Unreal Tournament, Mortal Kombat Armageddon, Zelda Twilight Princess and TitanQuest skinned actors).   As for the 4 bone weights per vertex limit, this does seem to be an arbitrary legacy based limit from shader model 2 and the fixed function before it when the blend indices were packed into 4 dwords. I think I saw some research paper that concluded for bipedal meshes 4 blend indices is sufficient for a certain fidelity of realistic motion, but I can't find the paper at hand to link to it.   As for the last question of whether you should always blend in 4 bone weights, I actually use another number to tell me how many of the 4 blend indices are needed. Here is some example shader model 2 code for skinning:   CRenderableMesh 0F7B78E8: ================================================================================= Vertex Declaration: 0B98C860 =================================================================================  8 Vertex Elements { Stream = 0, Offset = 0, Type = D3DDECLTYPE_FLOAT3, Method = D3DDECLMETHOD_DEFAULT, Usage = D3DDECLUSAGE_POSITION, UsageIndex = 0 }, { Stream = 0, Offset = 12, Type = D3DDECLTYPE_FLOAT3, Method = D3DDECLMETHOD_DEFAULT, Usage = D3DDECLUSAGE_NORMAL, UsageIndex = 0 }, { Stream = 0, Offset = 24, Type = D3DDECLTYPE_FLOAT3, Method = D3DDECLMETHOD_DEFAULT, Usage = D3DDECLUSAGE_BLENDWEIGHT, UsageIndex = 0 }, { Stream = 0, Offset = 36, Type = D3DDECLTYPE_D3DCOLOR, Method = D3DDECLMETHOD_DEFAULT, Usage = D3DDECLUSAGE_BLENDINDICES, UsageIndex = 0 }, { Stream = 0, Offset = 40, Type = D3DDECLTYPE_FLOAT4, Method = D3DDECLMETHOD_DEFAULT, Usage = D3DDECLUSAGE_TEXCOORD, UsageIndex = 0 }, { Stream = 0, Offset = 56, Type = D3DDECLTYPE_FLOAT4, Method = D3DDECLMETHOD_DEFAULT, Usage = D3DDECLUSAGE_TEXCOORD, UsageIndex = 1 }, { Stream = 0, Offset = 72, Type = D3DDECLTYPE_FLOAT4, Method = D3DDECLMETHOD_DEFAULT, Usage = D3DDECLUSAGE_TEXCOORD, UsageIndex = 2 }, { Stream = 0, Offset = 88, Type = D3DDECLTYPE_FLOAT4, Method = D3DDECLMETHOD_DEFAULT, Usage = D3DDECLUSAGE_TEXCOORD, UsageIndex = 3 } Vertex Shader 0FA01450: ================================================================================= //-------------------------------------------------------------------------------------- // Automatically generated Vertex Shader. // // Copyright (c) Steve Segreto. All rights reserved. // Shader Flags = 887f9 // Shader Type = Linear-Based Quaternion Skinning // Shader Quality = PHONG_LIGHTING //--------------------------------------------------------------------------------------   struct DirLight {     float4 ambient;     float4 diffuse;     float4 spec;     float3 dirW;     float4 fogColor;     float3 lightPosW; };   struct Mtrl {     float4 ambient;     float4 diffuse;     float4 spec;     float  specPower;     float4 emissive; };   //-------------------------------------------------------------------------------------- // Macro defines //-------------------------------------------------------------------------------------- #define MATRIX_PALETTE_SIZE (13)   //-------------------------------------------------------------------------------------- // Global variables //-------------------------------------------------------------------------------------- uniform extern DirLight gLight; uniform extern Mtrl gMtrl; uniform extern float4x4 gWorld; uniform extern float4x4 gWVP; uniform extern float4x4 gInvWorld; uniform extern float4x4 gView; uniform extern float3 gEyePosW; uniform extern float gFarClipDist; uniform extern float gAlphaRef = 0.29f; uniform extern float gFogRange = 250.0f; uniform extern float gFogStart = 1.0f; uniform extern matrix amPalette[ MATRIX_PALETTE_SIZE ]; uniform extern float gNumBones;   //---------------------------------------------------------------------------- // Shader body - VS_Skin //----------------------------------------------------------------------------   // // Define the inputs -- caller must fill this, usually right from the VB. // struct VS_SKIN_INPUT {     float4 vPos;     float3 vNor;     float3 vBlendWeights;     float4 vBlendIndices; };   // // Return skinned position and normal // struct VS_SKIN_OUTPUT {     float4 vPos;     float3 vNor; };   // // Call this function to skin VB position and normal. // VS_SKIN_OUTPUT VS_Skin( const VS_SKIN_INPUT vInput, int iNumBones ) {     VS_SKIN_OUTPUT vOutput = (VS_SKIN_OUTPUT) 0;       float fLastWeight = 1.0;     float afBlendWeights[ 3 ] = (float[ 3 ]) vInput.vBlendWeights;     int aiIndices[ 4 ]        = (int[ 4 ])   D3DCOLORtoUBYTE4( vInput.vBlendIndices );       for( int iBone = 0; (iBone < 3) && (iBone < iNumBones - 1); ++ iBone )     {         float fWeight = afBlendWeights[ iBone ];         fLastWeight -= fWeight;         vOutput.vPos.xyz += mul( vInput.vPos, amPalette[ aiIndices[ iBone  ] ] ) * fWeight;         vOutput.vNor     += mul( float4(vInput.vNor, 0.0f), amPalette[ aiIndices[ iBone  ] ] ) * fWeight;     }       vOutput.vPos.xyz += mul( vInput.vPos, amPalette[ aiIndices[ iNumBones - 1 ] ] ) * fLastWeight;     vOutput.vNor     += mul( float4(vInput.vNor, 0.0f), amPalette[ aiIndices[ iNumBones - 1 ] ] ) * fLastWeight;       return vOutput; } struct VS_in {     float3 posL         : POSITION0;     float3 normalL      : NORMAL0;     float3 BlendWeights : BLENDWEIGHT;     float4 BlendIndices : BLENDINDICES;     float4 tex0_tex1    : TEXCOORD0;     float4 tex2_tex3    : TEXCOORD1;     float4 tex4_tex5    : TEXCOORD2;     float4 tex6_tex7    : TEXCOORD3; };   struct VS_out {     float4 posH         : POSITION0;     float4 tex0_tex1    : TEXCOORD0;     float4 tex2_tex3    : TEXCOORD1;     float4 tex4_tex5    : TEXCOORD2;     float4 tex6_tex7    : TEXCOORD3;     float3 normalW      : TEXCOORD4;     float4 posVS        : TEXCOORD5;     float4 color        : COLOR0;     float  fogLerpParam : COLOR1; };   VS_out VS_Scene( VS_in i ) {     //     // Zero out our output.     //     VS_out o = (VS_out)0;       //     // Skin VB inputs     //     VS_SKIN_INPUT  vsi = { float4( i.posL, 1.0f ), i.normalL, i.BlendWeights, i.BlendIndices };     VS_SKIN_OUTPUT vso = VS_Skin( vsi, gNumBones );     i.posL = vso.vPos.xyz;     i.normalL = vso.vNor;       //     // Transform normal to world space and pass along     // to be interpolated by rasterizer.     //     o.normalW = mul( gInvWorld, float4(i.normalL, 0) ).xyz;       //     // Pass along per-vertex color to be interpolated by rasterizer.     //     o.color = gMtrl.diffuse;       //     // Transform position to homogeneous clip space.     //     float4 vPositionVS = mul(float4(i.posL, 1.0f), mul(gWorld, gView));     o.posH = mul(float4(i.posL, 1.0f), gWVP);       //     // This position will be used to output view space depth.     //     o.posVS = vPositionVS;     o.posVS.z = max(o.posVS.z, 0.0f);       //     // Pass on texture coordinates to be interpolated in rasterization.     //     o.tex0_tex1.xy = i.tex0_tex1.xy;     o.tex0_tex1.zw = i.tex0_tex1.zw;     o.tex2_tex3.xy = i.tex2_tex3.xy;     o.tex2_tex3.zw = i.tex2_tex3.zw;     o.tex4_tex5.xy = i.tex4_tex5.xy;     o.tex4_tex5.zw = i.tex4_tex5.zw;     o.tex6_tex7.xy = i.tex6_tex7.xy;     o.tex6_tex7.zw = i.tex6_tex7.zw;       //     // Compute vertex distance from camera in world     // space for fog calculation.     //     float dist = distance(mul(float4(i.posL, 1.0f), gWorld).xyz, gEyePosW);     o.fogLerpParam = saturate((dist - gFogStart) / gFogRange);       //     // Done--return the output.     //     return o; } Pixel Shader 0FA11C80: ================================================================================= //-------------------------------------------------------------------------------------- // Automatically generated Pixel Shader. // // Copyright (c) Steve Segreto. All rights reserved. // Shader Flags = 827e8 // Shader Type = Linear-Based Quaternion Skinning // Shader Quality = PHONG_LIGHTING //--------------------------------------------------------------------------------------   struct DirLight {     float4 ambient;     float4 diffuse;     float4 spec;     float3 dirW;     float4 fogColor;     float3 lightPosW; };   struct Mtrl {     float4 ambient;     float4 diffuse;     float4 spec;     float  specPower;     float4 emissive; };   //-------------------------------------------------------------------------------------- // Macro defines //--------------------------------------------------------------------------------------   //-------------------------------------------------------------------------------------- // Global variables //-------------------------------------------------------------------------------------- uniform extern DirLight gLight; uniform extern Mtrl gMtrl; uniform extern float4x4 gInvWorld; uniform extern float4x4 gView; uniform extern float3 gEyePosW; uniform extern float gFarClipDist; uniform extern float gAlphaRef = 0.29f; uniform extern float3 gFogColor; uniform extern texture gTex0;   struct PS_in {     float4 tex0_tex1    : TEXCOORD0;     float4 tex2_tex3    : TEXCOORD1;     float4 tex4_tex5    : TEXCOORD2;     float4 tex6_tex7    : TEXCOORD3;     float3 normalW      : TEXCOORD4;     float4 posVS        : TEXCOORD5;     float4 color        : COLOR0;     float  fogLerpParam : COLOR1; };   struct PS_out {     float4 vMaterial    : COLOR0;     float4 vWorldNrm    : COLOR1;     float4 vEmittance   : COLOR2;     float4 vDepth       : COLOR3; };   sampler TexS0 = sampler_state {     Texture   = <gTex0>;     MinFilter = Linear;     MagFilter = Linear;     MipFilter = Point;     AddressU  = Wrap;     AddressV  = Wrap; };   PS_out PS_Scene( PS_in i ) {     //     // Zero out our output.     //     PS_out o = (PS_out)0;       //     // Interpolated normals can become unnormal.     //     i.normalW   = normalize(i.normalW);       //     // VERT_MODE_SRC_IGNORE     //     float3 matAmbient  = gMtrl.ambient.rgb;     float4 matDiffuse  = gMtrl.diffuse;     float3 matEmissive = gMtrl.emissive.rgb;       //     // Incoming colors.     //     float3 color_stage0 = saturate((matAmbient * gLight.ambient) + matDiffuse + matEmissive);     o.vEmittance.y = gMtrl.spec.r;     o.vEmittance.z = gMtrl.specPower;     float  alpha_stage0 = matDiffuse.a;       //     // Sample textures.     //     float4 color0 = tex2D(TexS0, i.tex0_tex1.xy);       //     // Apply texturing stages     //       //     // Diffuse map.     //     float3 color_stage1  = color_stage0 * color0.rgb;       //     // Final (pre-fog) color.     //     float4 texColor = float4( color_stage1.rgb, alpha_stage0 );       //     // Add fog     //     o.vMaterial = texColor;     o.vEmittance.w = i.fogLerpParam;     // convert normal to texture space [-1;+1] -> [0;1]     o.vWorldNrm.xyz = i.normalW * 0.5 + 0.5;       // post-perspective z/w depth     o.vDepth = i.posVS.z / gFarClipDist;       //     // Done--return the output.     //     return o; }
  9. That's the funny thing about chasing heap leaks, when you examine the code everything looks like its being cleaned up correctly. You need to enlist the help of tools like the CRT debug heap or gflags debug heap to help you understand which allocations are being made without being freed, because this can provoke new thought and cause you to see what you are missing. I just caught a heap leak in my own source code last night that resulted from some scene graph nodes not being parented as I would have expected so even though the de-allocation code was rock solid and correct, there was still a heap leak because for a certain class of model a certain group of scene graph nodes were created as orphans without parents and thus a top-down de-allocation algorithm couldn't find them.
  10. Hi! If you have memory leaks that you are concerned about (e.g. that actually leak memory in response to application activities besides simply exiting the application), then you will need to clear away the application exit memory leaks as well so that you can more clearly see the other memory leaks to remove them.   At the basic level, you have allocated memory and have not freed it before your application exits. This can also stem from incrementing a ref count to a COM object (often unknowingly through an API call) and thus preventing the program from freeing the memory for the COM object. You could also be re-allocating memory to a pointer without first freeing it (this would be a dangerous heap leak).   A first suggestion is to enable debug heap at the beginning of your program and then run the application in Visual Studio in debug mode and scrub through the unfreed allocations.   if the below doesn't work, try gflags from application verifier and enable their debug heap, but I have run out of memory on moderately sized and larger programs doing that (debug heaps are expensive on memory budgets!) Good luck, please post more information for us to help you!!!     // Enable run-time memory check for debug builds. #if defined(DEBUG) | defined(_DEBUG)     _CrtSetDbgFlag( _CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF ); #endif
  11. Here's a graph based approach that usually forces the player to explore most of your randomly created dungeon, which is the equivalent of "fun" right? :)   http://www.roguebasin.com/index.php?title=Creating_Measurably_%22Fun%22_Maps
  12. Thanks for teaching me about the existence of OpenTissue it looks fun!   You may have to setup the CMAKE environment required by OpenTissue and modify it to perform a 64-bit build. I don't have any pre-built 64-bit versions of it sorry. Maybe you could post the operator overload compiler errors and we could help you with that?
  13. Can you provide some of your failing code for example please?   Be careful when passing a float for your pointsize that you properly cast your  float to the DWORD the API expects:   m_pDevice9->SetRenderState(D3DRS_POINTSIZE, *((DWORD*)&pointSize));   https://msdn.microsoft.com/en-us/library/windows/desktop/bb172599%28v=vs.85%29.aspx
  14. Maybe you need to set collision flags or set activation state to disable de-activation? Here is my helper routine ...    btRigidBody* CPhysicsEngine::CreateRigidBody( float mass, const btTransform& startTransform, btCollisionShape* shape, COLLISION_DATA *pCD ) {     btAssert((!shape || shape->getShapeType() != INVALID_SHAPE_PROXYTYPE));       //     // Rigidbody is dynamic if and only if mass is non zero, otherwise static.     //     bool isDynamic = (mass != 0.f);       btVector3 localInertia(0,0,0);     if (isDynamic)         shape->calculateLocalInertia(mass,localInertia);       //     // Using motionstate is recommended, it provides interpolation capabilities,     // and only synchronizes 'active' objects.     // #if 1     btDefaultMotionState* myMotionState = new btDefaultMotionState(startTransform);     btRigidBody::btRigidBodyConstructionInfo cInfo(mass,myMotionState,shape,localInertia);     btRigidBody* body = new btRigidBody(cInfo); #else     btRigidBody* body = new btRigidBody(mass,0,shape,localInertia);     body->setWorldTransform(startTransform); #endif       pCD->m_pRigidBody = body;     body->setUserPointer( (void *)pCD );     if (isDynamic)     {         body->setContactProcessingThreshold(0.0f);     }     body->setGravity( btVector3( 0.0f, -30.0f, 0.0f ) );     body->setCollisionFlags( btCollisionObject::CF_KINEMATIC_OBJECT );     body->setActivationState(DISABLE_DEACTIVATION);       m_dynamicsWorld->addRigidBody(body);       return body; }
  15. A background loading thread can be a good idea, it has worked well for me in the past with DX9.   You should block entry into the game until all objects within the player's immediate field of vision (basically a circle of a certain radius around the players (x,y,z) position) have been loaded. After that, simply load the other objects in the background thread as the player's position moves. If you do it right they won't notice objects "popping" into view when they run forward or rotate their view. This is all assuming your game is a first/third-person open world exploration, other cameras require other approaches.   Brush up on Windows synchronization primitives so that your 2nd thread doesn't data conflict with the main thread and vice versa, also you can only render from the thread you created the graphics device on.