void calculateValues() { MAT tm; tm.CreateRotationMatrix(rotation); // A bit optimized version, use base vectors directly normal.x = tm.Get(8); normal.y = tm.Get(9); normal.z = tm.Get(10); VC3 biasNormal = normal; biasNormal *= .07f; VC3 right(tm.Get(0), tm.Get(1), tm.Get(2)); VC3 up(tm.Get(4), tm.Get(5), tm.Get(6)); right *= .5f * size.x; up *= .5f * size.y; assert(fabsf(up.GetDotWith(right)) < 0.0001f); vertices[0] = position; vertices[0] -= right; vertices[0] -= up; vertices[0] += biasNormal; vertices[1] = position; vertices[1] -= right; vertices[1] += up; vertices[1] += biasNormal; vertices[2] = position; vertices[2] += right; vertices[2] -= up; vertices[2] += biasNormal; vertices[3] = position; vertices[3] += right; vertices[3] += up; vertices[3] += biasNormal; COL finalColor = light; finalColor.Clamp(); vertexColor = finalColor.GetAsD3DCompatibleARGB() & 0x00FFFFFF; vertexColor |= alpha << 24; if(entity) entity->setRadius(getRadius()); }
//------------------------------------------------------------------ // Storm3D_Scene_PicList_Font::Render //------------------------------------------------------------------ void Storm3D_Scene_PicList_Font::Render() { // Calculate complete letter amount and letters per texture int letters_per_texture=font->tex_letter_rows*font->tex_letter_columns; int letter_amt=font->texture_amount*letters_per_texture; // Create 3d-vector VC3 pos(position.x,position.y,0); // Create color (color+alpha) COL color = font->GetColor(); color *= colorFactor; color.Clamp(); //DWORD col=font->GetColor().GetAsD3DCompatibleARGB(); //DWORD col=color.GetAsD3DCompatibleARGB(); DWORD col = D3DCOLOR_ARGB((int)((alpha)*255.0f),(int)(color.r*255.0f),(int)(color.g*255.0f),(int)(color.b*255.0f)); Storm3D2->GetD3DDevice()->SetRenderState(D3DRS_ALPHABLENDENABLE,TRUE); if(font->font && font->sprite) { #pragma message("** **") #pragma message("** Size to screen boundary and enable clipping **") #pragma message("** **") //VC2 _position,VC2 _size RECT rc = { int(position.x), int(position.y), int(position.x + size.x + 100), int(position.y + size.y + 1000) }; //if(uniText) // font->font->DrawTextW(0, uniText, wcslen(uniText), &rc, DT_SINGLELINE | DT_LEFT | DT_NOCLIP, col); //else if(text) // font->font->DrawText(0, text, strlen(text), &rc, DT_SINGLELINE | DT_LEFT | DT_NOCLIP, col); DWORD flags = D3DXSPRITE_SORT_TEXTURE | D3DXSPRITE_ALPHABLEND; font->sprite->Begin(flags); if(uniText) font->font->DrawTextW(font->sprite, uniText, wcslen(uniText), &rc, DT_LEFT | DT_NOCLIP, col); else if(text) font->font->DrawText(font->sprite, text, strlen(text), &rc, DT_LEFT | DT_NOCLIP, col); font->sprite->End(); } else if(text) { for(int l=0;l<int(strlen(text));l++) { // Search for letter int let=-1; for (int i=0;i<letter_amt;i++) { if (font->letter_characters[i]==text[l]) { let=i; // doh, why not break now when we found it and save time! break; } else { // if we find the null terminator, just stop there, because // otherwise we'll go past the character array size if it // does not contain character definitions for total of letter_amt // characters. In my opininion requiring such a thing is not nice. if (font->letter_characters[i] == '\0') break; } } // Is this letter in font if (let>=0) { // Apply the correct texture font->textures[let/letters_per_texture]->Apply(0); // Calculate x/y int x=let%font->tex_letter_columns; int y=(let%letters_per_texture)/font->tex_letter_columns; // Calculate texture coordinates float tx1=1/(float)font->tex_letter_columns; float ty1=1/(float)font->tex_letter_rows; float fx=(float)x*tx1; float fy=(float)y*ty1; // Create a quad VXFORMAT_2D vx[4]; vx[0]=VXFORMAT_2D(pos+VC3(0,size.y,0),1, col,VC2(fx,fy+ty1)); vx[1]=VXFORMAT_2D(pos,1, col,VC2(fx,fy)); vx[2]=VXFORMAT_2D(pos+VC3(size.x,size.y,0),1, col,VC2(fx+tx1,fy+ty1)); vx[3]=VXFORMAT_2D(pos+VC3(size.x,0,0),1, col,VC2(fx+tx1,fy)); // Clip if (Clip2DRectangle(Storm3D2,vx[1],vx[2])) { // Copy clipping vx[0].position.x=vx[1].position.x; vx[0].texcoords.x=vx[1].texcoords.x; vx[3].position.y=vx[1].position.y; vx[3].texcoords.y=vx[1].texcoords.y; vx[0].position.y=vx[2].position.y; vx[0].texcoords.y=vx[2].texcoords.y; vx[3].position.x=vx[2].position.x; vx[3].texcoords.x=vx[2].texcoords.x; for(int i = 0; i < 4; ++i) { vx[i].position.x -= .5f; vx[i].position.y -= .5f; } // Render it Storm3D2->GetD3DDevice()->SetVertexShader(0); Storm3D2->GetD3DDevice()->SetFVF(FVF_VXFORMAT_2D); frozenbyte::storm::validateDevice(*Storm3D2->GetD3DDevice(), Storm3D2->getLogger()); Storm3D2->GetD3DDevice()->DrawPrimitiveUP(D3DPT_TRIANGLESTRIP,2,vx,sizeof(VXFORMAT_2D)); scene->AddPolyCounter(2); } } // Add x-koordinate if (let>=0) pos.x+=((float)font->letter_width[let]/64.0f)*size.x; else pos.x+=size.x/2.0f; } } }
void render(Storm3D_Scene &scene) { gfx::Renderer& renderer = storm.renderer; gfx::Device& device = renderer.device; gfx::ProgramManager& programManager = renderer.programManager; baseDecalVertex = 0; findDecals(scene); if (decals.empty()) return; Vertex_P3NDUV *buffer = 0; renderer.lockDynVtx<Vertex_P3NDUV>(decals.size() * 4, &buffer, &baseDecalVertex); for (unsigned int i = 0; i < decals.size(); ++i) { Decal& decal = *decals[i]; COL decalColor = decal.light * (decal.type == Outside ? outFactor : inFactor); decalColor.Clamp(); uint32_t vertexColor = decalColor.as_u32_D3D_ARGB(decal.alpha); decal.insert(buffer, vertexColor); buffer += 4; } renderer.unlockDynVtx(); // Render if (!decals.empty()) { device.SetRenderState(D3DRS_ZWRITEENABLE, FALSE); device.SetRenderState(D3DRS_ALPHABLENDENABLE, TRUE); device.SetRenderState(D3DRS_ALPHATESTENABLE, FALSE); device.SetRenderState(D3DRS_SRCBLEND, D3DBLEND_SRCALPHA); device.SetRenderState(D3DRS_DESTBLEND, D3DBLEND_INVSRCALPHA); D3DXMATRIX tm; D3DXMatrixIdentity(&tm); programManager.setWorldMatrix(tm); programManager.setProgram(gfx::ProgramManager::DECAL_LIGHTING); renderer.setDynVtxBuffer<Vertex_P3NDUV>(); renderer.setFVF(FVF_P3NDUV); int materialIndex = 0; int startIndex = 0; int endIndex = 0; for (;;) { materialIndex = decals[startIndex]->materialIndex; if(materials[materialIndex].baseTexture) materials[materialIndex].baseTexture->Apply(0); programManager.setDiffuse(materials[materialIndex].diffuseColor); programManager.applyState(device); int decalAmount = decals.size(); for (int i = startIndex + 1; i < decalAmount; ++i) { if (decals[i]->materialIndex != materialIndex) break; endIndex = i; } int renderAmount = endIndex - startIndex + 1; renderer.drawQuads(baseDecalVertex + startIndex * 4, renderAmount); startIndex = ++endIndex; if (startIndex >= decalAmount) break; } device.SetRenderState(D3DRS_ALPHABLENDENABLE, FALSE); } }