OpenClonk
C4Draw.cpp
Go to the documentation of this file.
1 /*
2  * OpenClonk, http://www.openclonk.org
3  *
4  * Copyright (c) 1998-2000, Matthes Bender
5  * Copyright (c) 2001-2009, RedWolf Design GmbH, http://www.clonk.de/
6  * Copyright (c) 2009-2016, The OpenClonk Team and contributors
7  *
8  * Distributed under the terms of the ISC license; see accompanying file
9  * "COPYING" for details.
10  *
11  * "Clonk" is a registered trademark of Matthes Bender, used with permission.
12  * See accompanying file "TRADEMARK" for details.
13  *
14  * To redistribute this file separately, substitute the full license texts
15  * for the above references.
16  */
17 
18 /* NewGfx interfaces */
19 #include "C4Include.h"
21 #include "graphics/C4Draw.h"
22 
23 #include "graphics/C4DrawGL.h"
24 #include "graphics/C4DrawT.h"
25 #include "graphics/C4FontLoader.h"
26 #include "graphics/CSurface8.h"
27 #include "lib/C4Markup.h"
28 #include "lib/C4Rect.h"
29 #include "lib/StdColors.h"
30 #include "lib/StdMesh.h"
31 #include "platform/C4App.h"
32 #include "platform/C4Window.h"
33 
34 // Instruct Optimus laptops to use nVidia GPU instead of integrated GPU
35 #if defined(_WIN32) && !defined(USE_CONSOLE)
36 extern "C" {
37  __declspec(dllexport) DWORD NvOptimusEnablement = 0x00000001;
38 }
39 #endif
40 
41 // Global access pointer
42 C4Draw *pDraw=nullptr;
43 
44 void C4BltTransform::SetRotate(float iAngle, float fOffX, float fOffY) // set by angle and rotation offset
45 {
46  // iAngle is in degrees (cycling from 0 to 360)
47  // determine sine and cos of reversed angle in radians
48  // fAngle = -iAngle * pi/180 = iAngle * -pi/180
49  float fAngle = iAngle * -0.0174532925f;
50  float fsin = sinf(fAngle); float fcos = cosf(fAngle);
51  // set matrix values
52  mat[0] = +fcos; mat[1] = +fsin; mat[2] = (1-fcos)*fOffX - fsin*fOffY;
53  mat[3] = -fsin; mat[4] = +fcos; mat[5] = (1-fcos)*fOffY + fsin*fOffX;
54  mat[6] = 0; mat[7] = 0; mat[8] = 1;
55  /* calculation of rotation matrix:
56  x2 = fcos*(x1-fOffX) + fsin*(y1-fOffY) + fOffX
57  = fcos*x1 - fcos*fOffX + fsin*y1 - fsin*fOffY + fOffX
58  = x1*fcos + y1*fsin + (1-fcos)*fOffX - fsin*fOffY
59 
60  y2 = -fsin*(x1-fOffX) + fcos*(y1-fOffY) + fOffY
61  = x1*-fsin + fsin*fOffX + y1*fcos - fcos*fOffY + fOffY
62  = x1*-fsin + y1*fcos + fsin*fOffX + (1-fcos)*fOffY */
63 }
64 
66 {
67  // calc inverse of matrix
68  float det = r.mat[0]*r.mat[4]*r.mat[8] + r.mat[1]*r.mat[5]*r.mat[6]
69  + r.mat[2]*r.mat[3]*r.mat[7] - r.mat[2]*r.mat[4]*r.mat[6]
70  - r.mat[0]*r.mat[5]*r.mat[7] - r.mat[1]*r.mat[3]*r.mat[8];
71  if (!det) { Set(1,0,0,0,1,0,0,0,1); return false; }
72  mat[0] = (r.mat[4] * r.mat[8] - r.mat[5] * r.mat[7]) / det;
73  mat[1] = (r.mat[2] * r.mat[7] - r.mat[1] * r.mat[8]) / det;
74  mat[2] = (r.mat[1] * r.mat[5] - r.mat[2] * r.mat[4]) / det;
75  mat[3] = (r.mat[5] * r.mat[6] - r.mat[3] * r.mat[8]) / det;
76  mat[4] = (r.mat[0] * r.mat[8] - r.mat[2] * r.mat[6]) / det;
77  mat[5] = (r.mat[2] * r.mat[3] - r.mat[0] * r.mat[5]) / det;
78  mat[6] = (r.mat[3] * r.mat[7] - r.mat[4] * r.mat[6]) / det;
79  mat[7] = (r.mat[1] * r.mat[6] - r.mat[0] * r.mat[7]) / det;
80  mat[8] = (r.mat[0] * r.mat[4] - r.mat[1] * r.mat[3]) / det;
81  return true;
82 }
83 
84 void C4BltTransform::TransformPoint(float &rX, float &rY) const
85 {
86  // apply matrix
87  float fW = mat[6] * rX + mat[7] * rY + mat[8];
88  // store in temp, so original rX is used for calculation of rY
89  float fX = (mat[0] * rX + mat[1] * rY + mat[2]) / fW;
90  rY = (mat[3] * rX + mat[4] * rY + mat[5]) / fW;
91  rX = fX; // apply temp
92 }
93 
95 {
96  sfcPattern32 = nPattern.sfcPattern32;
97  if (sfcPattern32) sfcPattern32->Lock();
98  delete [] CachedPattern;
99  if (nPattern.CachedPattern)
100  {
101  CachedPattern = new uint32_t[sfcPattern32->Wdt * sfcPattern32->Hgt];
102  memcpy(CachedPattern, nPattern.CachedPattern, sfcPattern32->Wdt * sfcPattern32->Hgt * 4);
103  }
104  else
105  {
106  CachedPattern = nullptr;
107  }
108  Wdt = nPattern.Wdt;
109  Hgt = nPattern.Hgt;
110  Zoom = nPattern.Zoom;
111  return *this;
112 }
113 
114 bool C4Pattern::Set(C4Surface * sfcSource, int iZoom)
115 {
116  // Safety
117  if (!sfcSource) return false;
118  // Clear existing pattern
119  Clear();
120  // new style: simply store pattern for modulation or shifting, which will be decided upon use
121  sfcPattern32=sfcSource;
122  sfcPattern32->Lock();
123  Wdt = sfcPattern32->Wdt;
124  Hgt = sfcPattern32->Hgt;
125  // set zoom
126  Zoom=iZoom;
127  // set flags
128  CachedPattern = new uint32_t[Wdt * Hgt];
129  if (!CachedPattern) return false;
130  for (int y = 0; y < Hgt; ++y)
131  for (int x = 0; x < Wdt; ++x)
132  {
133  CachedPattern[y * Wdt + x] = sfcPattern32->GetPixDw(x, y, false);
134  }
135  return true;
136 }
137 
139 {
140  // disable
141  sfcPattern32=nullptr;
142  CachedPattern = nullptr;
143  Zoom=0;
144 }
145 
147 {
148  // pattern assigned
149  if (sfcPattern32)
150  {
151  // unlock it
152  sfcPattern32->Unlock();
153  // clear field
154  sfcPattern32=nullptr;
155  }
156  delete[] CachedPattern; CachedPattern = nullptr;
157 }
158 
159 DWORD C4Pattern::PatternClr(unsigned int iX, unsigned int iY) const
160 {
161  if (!CachedPattern) return 0;
162  // wrap position
163  iX %= Wdt; iY %= Hgt;
164  return CachedPattern[iY * Wdt + iX];
165 }
166 
167 //--------------------------------------------------------------------
168 
170 {
171  RenderTarget=nullptr;
172  ClipAll=false;
173  Active=false;
174  BlitModulated=false;
175  dwBlitMode = 0;
176  ResetGamma();
177  pFoW = nullptr;
178  ZoomX = 0; ZoomY = 0; Zoom = 1;
179  MeshTransform = nullptr;
180  fUsePerspective = false;
182 }
183 
185 {
186  ResetGamma();
187  Active=BlitModulated=false;
188  dwBlitMode = 0;
189 }
190 
191 bool C4Draw::GetSurfaceSize(C4Surface * sfcSurface, int &iWdt, int &iHgt)
192 {
193  return sfcSurface->GetSurfaceSize(iWdt, iHgt);
194 }
195 
196 bool C4Draw::SubPrimaryClipper(int iX1, int iY1, int iX2, int iY2)
197 {
198  // Set sub primary clipper
199  SetPrimaryClipper(std::max(iX1,iClipX1),std::max(iY1,iClipY1),std::min(iX2,iClipX2),std::min(iY2,iClipY2));
200  return true;
201 }
202 
204 {
205  // Store current primary clipper
207  return true;
208 }
209 
211 {
212  // Restore primary clipper
214  return true;
215 }
216 
217 bool C4Draw::SetPrimaryClipper(int iX1, int iY1, int iX2, int iY2)
218 {
219  // set clipper
220  fClipX1=iX1; fClipY1=iY1; fClipX2=iX2; fClipY2=iY2;
221  iClipX1=iX1; iClipY1=iY1; iClipX2=iX2; iClipY2=iY2;
222  UpdateClipper();
223  // Done
224  return true;
225 }
226 
228 {
229  return true;
230 }
231 
233 {
234  return true;
235 }
236 
238 {
239  // apply maximum clipper
240  SetPrimaryClipper(0,0,439832,439832);
241  // Done
242  return true;
243 }
244 
245 void C4Draw::BlitLandscape(C4Surface * sfcSource, float fx, float fy,
246  C4Surface * sfcTarget, float tx, float ty, float wdt, float hgt)
247 {
248  Blit(sfcSource, fx, fy, wdt, hgt, sfcTarget, tx, ty, wdt, hgt, false);
249 }
250 
251 void C4Draw::Blit8Fast(CSurface8 * sfcSource, int fx, int fy,
252  C4Surface * sfcTarget, int tx, int ty, int wdt, int hgt)
253 {
254  // blit 8bit-sfc
255  // lock surfaces
256  assert(sfcTarget->fPrimary);
257  bool fRender = sfcTarget->IsRenderTarget();
258  if (!fRender) if (!sfcTarget->Lock())
259  { return; }
260 
261  float tfx = tx, tfy = ty, twdt = wdt, thgt = hgt;
262  if (Zoom != 1.0)
263  {
264  ApplyZoom(tfx, tfy);
265  twdt *= Zoom;
266  thgt *= Zoom;
267  }
268 
269  // blit 8 bit pix in batches of 1024 pixels
270  static const int BUF_SIZE = 1024;
271  C4BltVertex* vertices = new C4BltVertex[BUF_SIZE];
272  int bufcnt = 0;
273 
274  for (int ycnt=0; ycnt<thgt; ++ycnt)
275  {
276  for (int xcnt=0; xcnt<twdt; ++xcnt)
277  {
278  BYTE byPix = sfcSource->GetPix(fx+wdt*xcnt/twdt, fy+hgt*ycnt/thgt);
279  DWORD dwClr = byPix ? sfcSource->pPal->GetClr(byPix) : 0x00000000;
280 
281  vertices[bufcnt].ftx = (float)(tx + xcnt / Zoom);
282  vertices[bufcnt].fty = (float)(ty + ycnt / Zoom);
283  DwTo4UB(dwClr, vertices[bufcnt].color);
284  ++bufcnt;
285 
286  if(bufcnt == BUF_SIZE)
287  {
288  PerformMultiPix(sfcTarget, vertices, BUF_SIZE, nullptr);
289  bufcnt = 0;
290  }
291  }
292 
293  }
294  if(bufcnt > 0)
295  PerformMultiPix(sfcTarget, vertices, bufcnt, nullptr);
296  delete[] vertices;
297  // unlock
298  if (!fRender) sfcTarget->Unlock();
299 }
300 
301 bool C4Draw::Blit(C4Surface * sfcSource, float fx, float fy, float fwdt, float fhgt,
302  C4Surface * sfcTarget, float tx, float ty, float twdt, float thgt,
303  bool fSrcColKey, const C4BltTransform *pTransform)
304 {
305  return BlitUnscaled(sfcSource, fx * sfcSource->Scale, fy * sfcSource->Scale, fwdt * sfcSource->Scale, fhgt * sfcSource->Scale,
306  sfcTarget, tx, ty, twdt, thgt, fSrcColKey, pTransform);
307 }
308 
309 bool C4Draw::BlitUnscaled(C4Surface * sfcSource, float fx, float fy, float fwdt, float fhgt,
310  C4Surface * sfcTarget, float tx, float ty, float twdt, float thgt,
311  bool fSrcColKey, const C4BltTransform *pTransform)
312 {
313  // safety
314  if (!sfcSource || !sfcTarget || !twdt || !thgt || !fwdt || !fhgt) return false;
315  // emulated blit?
316  if (!sfcTarget->IsRenderTarget())
317  {
318  C4BltTransform t;
319  if(pTransform && Zoom != 1.0)
320  {
321  t.Set(pTransform->mat[0]*Zoom, pTransform->mat[1]*Zoom, pTransform->mat[2]*Zoom + ZoomX*(1-Zoom),
322  pTransform->mat[3]*Zoom, pTransform->mat[4]*Zoom, pTransform->mat[5]*Zoom + ZoomY*(1-Zoom),
323  pTransform->mat[6], pTransform->mat[7], pTransform->mat[8]);
324  pTransform = &t;
325  }
326  else if(Zoom != 1.0)
327  {
328  ApplyZoom(tx, ty);
329  twdt *= Zoom;
330  thgt *= Zoom;
331  }
332 
333  return Blit8(sfcSource, int(fx), int(fy), int(fwdt), int(fhgt), sfcTarget, int(tx), int(ty), int(twdt), int(thgt), fSrcColKey, pTransform);
334  }
335 
336  // bound
337  if (ClipAll) return true;
338  // inside screen?
339  if (twdt<=0 || thgt<=0) return false;
340  // prepare rendering to surface
341  if (!PrepareRendering(sfcTarget)) return false;
342  // texture present?
343  if (!sfcSource->texture)
344  {
345  // primary surface?
346  if (sfcSource->fPrimary)
347  {
348  // blit emulated
349  return Blit8(sfcSource, int(fx), int(fy), int(fwdt), int(fhgt), sfcTarget, int(tx), int(ty), int(twdt), int(thgt), fSrcColKey);
350  }
351  return false;
352  }
353  // blit with basesfc?
354  bool fBaseSfc=false;
355  if (sfcSource->pMainSfc) if (sfcSource->pMainSfc->texture) fBaseSfc = true;
356 
357  C4TexRef *pTex = sfcSource->texture.get();
358  // set up blit data
359  C4BltVertex vertices[6];
360  vertices[0].ftx = tx; vertices[0].fty = ty;
361  vertices[1].ftx = tx + twdt; vertices[1].fty = ty;
362  vertices[2].ftx = tx + twdt; vertices[2].fty = ty + thgt;
363  vertices[3].ftx = tx; vertices[3].fty = ty + thgt;
364  vertices[0].tx = fx / pTex->iSizeX; vertices[0].ty = fy / pTex->iSizeY;
365  vertices[1].tx = (fx + fwdt) / pTex->iSizeX; vertices[1].ty = fy / pTex->iSizeY;
366  vertices[2].tx = (fx + fwdt) / pTex->iSizeX; vertices[2].ty = (fy + fhgt) / pTex->iSizeY;
367  vertices[3].tx = fx / pTex->iSizeX; vertices[3].ty = (fy + fhgt) / pTex->iSizeY;
368  DwTo4UB(0xffffffff, vertices[0].color);
369  DwTo4UB(0xffffffff, vertices[1].color);
370  DwTo4UB(0xffffffff, vertices[2].color);
371  DwTo4UB(0xffffffff, vertices[3].color);
372 
373  // duplicate vertices
374  vertices[4] = vertices[0]; vertices[5] = vertices[2];
375 
376  C4TexRef * pBaseTex = pTex;
377  // is there a base-surface to be blitted first?
378  if (fBaseSfc)
379  {
380  // then get this surface as same offset as from other surface
381  // assuming this is only valid as long as there's no texture management,
382  // organizing partially used textures together!
383  pBaseTex = sfcSource->pMainSfc->texture.get();
384  }
385 
386  C4TexRef* pNormalTex = nullptr;
387  if (sfcSource->pNormalSfc)
388  pNormalTex = sfcSource->pNormalSfc->texture.get();
389 
390  // ClrByOwner is always fully opaque
391  const DWORD dwOverlayClrMod = 0xff000000 | sfcSource->ClrByOwnerClr;
392  PerformMultiTris(sfcTarget, vertices, 6, pTransform, pBaseTex, fBaseSfc ? pTex : nullptr, pNormalTex, dwOverlayClrMod, nullptr);
393  // success
394  return true;
395 }
396 
397 bool C4Draw::RenderMesh(StdMeshInstance &instance, C4Surface * sfcTarget, float tx, float ty, float twdt, float thgt, DWORD dwPlayerColor, C4BltTransform* pTransform)
398 {
399  // TODO: Emulate rendering
400  if (!sfcTarget->IsRenderTarget()) return false;
401 
402  // TODO: Clip
403 
404  // prepare rendering to surface
405  if (!PrepareRendering(sfcTarget)) return false;
406  // Update bone matrices and vertex data (note this also updates attach transforms and child transforms)
407  instance.UpdateBoneTransforms();
408  // Order faces according to MeshTransformation (note pTransform does not affect Z coordinate, so does not need to be taken into account for correct ordering)
410  if(MeshTransform) mat = *MeshTransform * mat;
411  instance.ReorderFaces(&mat);
412  // Render mesh
413  PerformMesh(instance, tx, ty, twdt, thgt, dwPlayerColor, pTransform);
414  // success
415  return true;
416 }
417 
418 bool C4Draw::Blit8(C4Surface * sfcSource, int fx, int fy, int fwdt, int fhgt,
419  C4Surface * sfcTarget, int tx, int ty, int twdt, int thgt,
420  bool fSrcColKey, const C4BltTransform *pTransform)
421 {
422  if (!pTransform) return BlitSimple(sfcSource, fx, fy, fwdt, fhgt, sfcTarget, tx, ty, twdt, thgt, fSrcColKey!=false);
423  // safety
424  if (!fwdt || !fhgt) return true;
425  // Lock the surfaces
426  if (!sfcSource->Lock())
427  return false;
428  if (!sfcTarget->Lock())
429  { sfcSource->Unlock(); return false; }
430  // transformed, emulated blit
431  // Calculate transform target rect
432  C4BltTransform Transform;
433  Transform.SetMoveScale(tx-(float)fx*twdt/fwdt, ty-(float)fy*thgt/fhgt, (float) twdt/fwdt, (float) thgt/fhgt);
434  Transform *=* pTransform;
435  C4BltTransform TransformBack;
436  TransformBack.SetAsInv(Transform);
437  auto ttx0=(float)tx, tty0=(float)ty, ttx1=(float)(tx+twdt), tty1=(float)(ty+thgt);
438  auto ttx2=(float)ttx0, tty2=(float)tty1, ttx3=(float)ttx1, tty3=(float)tty0;
439  pTransform->TransformPoint(ttx0, tty0);
440  pTransform->TransformPoint(ttx1, tty1);
441  pTransform->TransformPoint(ttx2, tty2);
442  pTransform->TransformPoint(ttx3, tty3);
443  int ttxMin = std::max<int>((int)floor(std::min(std::min(ttx0, ttx1), std::min(ttx2, ttx3))), 0);
444  int ttxMax = std::min<int>((int)ceil(std::max(std::max(ttx0, ttx1), std::max(ttx2, ttx3))), sfcTarget->Wdt);
445  int ttyMin = std::max<int>((int)floor(std::min(std::min(tty0, tty1), std::min(tty2, tty3))), 0);
446  int ttyMax = std::min<int>((int)ceil(std::max(std::max(tty0, tty1), std::max(tty2, tty3))), sfcTarget->Hgt);
447  // blit within target rect
448  for (int y = ttyMin; y < ttyMax; ++y)
449  for (int x = ttxMin; x < ttxMax; ++x)
450  {
451  float ffx=(float)x, ffy=(float)y;
452  TransformBack.TransformPoint(ffx, ffy);
453  int ifx=static_cast<int>(ffx), ify=static_cast<int>(ffy);
454  if (ifx<fx || ify<fy || ifx>=fx+fwdt || ify>=fy+fhgt) continue;
455  sfcTarget->BltPix(x,y, sfcSource, ifx,ify, !!fSrcColKey);
456  }
457  // Unlock the surfaces
458  sfcSource->Unlock();
459  sfcTarget->Unlock();
460  return true;
461 }
462 
463 bool C4Draw::BlitSimple(C4Surface * sfcSource, int fx, int fy, int fwdt, int fhgt,
464  C4Surface * sfcTarget, int tx, int ty, int twdt, int thgt,
465  bool fTransparency)
466 {
467  // rendertarget?
468  if (sfcTarget->IsRenderTarget())
469  {
470  return Blit(sfcSource, float(fx), float(fy), float(fwdt), float(fhgt), sfcTarget, float(tx), float(ty), float(twdt), float(thgt), true);
471  }
472  // Object is first stretched to dest rect
473  int xcnt,ycnt,tcx,tcy,cpcx,cpcy;
474  if (!fwdt || !fhgt || !twdt || !thgt) return false;
475  // Lock the surfaces
476  if (!sfcSource->Lock())
477  return false;
478  if (!sfcTarget->Lock())
479  { sfcSource->Unlock(); return false; }
480  // Rectangle centers
481  tcx=twdt/2; tcy=thgt/2;
482  for (ycnt=0; ycnt<thgt; ycnt++)
483  if (Inside(cpcy=ty+tcy-thgt/2+ycnt,0,sfcTarget->Hgt-1))
484  for (xcnt=0; xcnt<twdt; xcnt++)
485  if (Inside(cpcx=tx+tcx-twdt/2+xcnt,0,sfcTarget->Wdt-1))
486  sfcTarget->BltPix(cpcx, cpcy, sfcSource, xcnt*fwdt/twdt+fx, ycnt*fhgt/thgt+fy, fTransparency);
487  // Unlock the surfaces
488  sfcSource->Unlock();
489  sfcTarget->Unlock();
490  return true;
491 }
492 
493 
494 bool C4Draw::Error(const char *szMsg)
495 {
496  if (pApp) pApp->Error(szMsg);
497  Log(szMsg); return false;
498 }
499 
500 
501 bool C4Draw::CreatePrimaryClipper(unsigned int iXRes, unsigned int iYRes)
502 {
503  // simply setup primary viewport
504  // assume no zoom has been set yet
505  assert(Zoom==1.0f);
506  SetPrimaryClipper(0, 0, iXRes - 1, iYRes - 1);
508  return true;
509 }
510 
511 bool C4Draw::BlitSurface(C4Surface * sfcSurface, C4Surface * sfcTarget, int tx, int ty, bool fBlitBase)
512 {
513  if (fBlitBase)
514  {
515  Blit(sfcSurface, 0.0f, 0.0f, (float)sfcSurface->Wdt, (float)sfcSurface->Hgt, sfcTarget, float(tx), float(ty), float(sfcSurface->Wdt), float(sfcSurface->Hgt), false);
516  return true;
517  }
518  else
519  {
520  if (!sfcSurface) return false;
521  C4Surface *pSfcBase = sfcSurface->pMainSfc;
522  sfcSurface->pMainSfc = nullptr;
523  Blit(sfcSurface, 0.0f, 0.0f, (float)sfcSurface->Wdt, (float)sfcSurface->Hgt, sfcTarget, float(tx), float(ty), float(sfcSurface->Wdt), float(sfcSurface->Hgt), false);
524  sfcSurface->pMainSfc = pSfcBase;
525  return true;
526  }
527 }
528 
529 bool C4Draw::BlitSurfaceTile(C4Surface * sfcSurface, C4Surface * sfcTarget, float iToX, float iToY, float iToWdt, float iToHgt, float iOffsetX, float iOffsetY, C4ShaderCall* shader_call)
530 {
531  // Only direct rendering from single, tileable, texture
532  if (!sfcTarget->IsRenderTarget()) return false;
533  if ((sfcSurface->texture->iFlags & C4SF_Tileable) == 0) return false;
534 
535  // source surface dimensions
536  const float sourceWdt = sfcSurface->Wdt;
537  const float sourceHgt = sfcSurface->Hgt;
538 
539  // vertex positions
540  C4BltVertex vertices[6];
541  vertices[0].ftx = iToX; vertices[0].fty = iToY; vertices[0].ftz = 0.0f;
542  vertices[0].tx = (0.0f + iOffsetX) / sourceWdt; vertices[0].ty = (0.0f + iOffsetY) / sourceHgt;
543  DwTo4UB(0xffffffff, vertices[0].color);
544  vertices[1].ftx = iToX + iToWdt; vertices[1].fty = iToY; vertices[1].ftz = 0.0f;
545  vertices[1].tx = (iToWdt + iOffsetX) / sourceWdt; vertices[1].ty = (0.0f + iOffsetY) / sourceHgt;
546  DwTo4UB(0xffffffff, vertices[1].color);
547  vertices[2].ftx = iToX + iToWdt; vertices[2].fty = iToY + iToHgt; vertices[2].ftz = 0.0f;
548  vertices[2].tx = (iToWdt + iOffsetX) / sourceWdt; vertices[2].ty = (iToHgt + iOffsetY) / sourceHgt;
549  DwTo4UB(0xffffffff, vertices[2].color);
550  vertices[3].ftx = iToX; vertices[3].fty = iToY + iToHgt; vertices[3].ftz = 0.0f;
551  vertices[3].tx = (0.0f + iOffsetX) / sourceWdt; vertices[3].ty = (iToHgt + iOffsetY) / sourceHgt;
552  DwTo4UB(0xffffffff, vertices[3].color);
553  // duplicate vertices
554  vertices[4] = vertices[0]; vertices[5] = vertices[2];
555 
556  // Draw
557  PerformMultiTris(sfcTarget, vertices, 6, nullptr, sfcSurface->texture.get(), nullptr, nullptr, 0, shader_call);
558  return true;
559 }
560 
561 bool C4Draw::TextOut(const char *szText, CStdFont &rFont, float fZoom, C4Surface * sfcDest, float iTx, float iTy, DWORD dwFCol, BYTE byForm, bool fDoMarkup)
562 {
563  C4Markup Markup(true);
564  static char szLinebuf[2500+1];
565  for (int cnt=0; SCopySegmentEx(szText,cnt,szLinebuf,fDoMarkup ? '|' : '\n','\n',2500); cnt++,iTy+=int(fZoom*rFont.GetLineHeight()))
566  if (!StringOut(szLinebuf,sfcDest,iTx,iTy,dwFCol,byForm,fDoMarkup,Markup,&rFont,fZoom)) return false;
567  return true;
568 }
569 
570 bool C4Draw::StringOut(const char *szText, CStdFont &rFont, float fZoom, C4Surface * sfcDest, float iTx, float iTy, DWORD dwFCol, BYTE byForm, bool fDoMarkup)
571 {
572  // init markup
573  C4Markup Markup(true);
574  // output string
575  return StringOut(szText, sfcDest, iTx, iTy, dwFCol, byForm, fDoMarkup, Markup, &rFont, fZoom);
576 }
577 
578 bool C4Draw::StringOut(const char *szText, C4Surface * sfcDest, float iTx, float iTy, DWORD dwFCol, BYTE byForm, bool fDoMarkup, C4Markup &Markup, CStdFont *pFont, float fZoom)
579 {
580  // clip
581  if (ClipAll) return true;
582  // safety
583  if (!PrepareRendering(sfcDest)) return false;
584  // convert align
585  int iFlags=0;
586  switch (byForm)
587  {
588  case ACenter: iFlags |= STDFONT_CENTERED; break;
589  case ARight: iFlags |= STDFONT_RIGHTALGN; break;
590  }
591  if (!fDoMarkup) iFlags|=STDFONT_NOMARKUP;
592  // draw text
593  pFont->DrawText(sfcDest, iTx , iTy , dwFCol, szText, iFlags, Markup, fZoom);
594  // done, success
595  return true;
596 }
597 
598 void C4Draw::DrawPix(C4Surface * sfcDest, float tx, float ty, DWORD dwClr)
599 {
600  // Draw
601  C4BltVertex vtx;
602  vtx.ftx = tx;
603  vtx.fty = ty;
604  DwTo4UB(dwClr, vtx.color);
605  PerformMultiPix(sfcDest, &vtx, 1, nullptr);
606 }
607 
608 void C4Draw::DrawLineDw(C4Surface * sfcTarget, float x1, float y1, float x2, float y2, DWORD dwClr, float width)
609 {
610  C4BltVertex vertices[2];
611  vertices[0].ftx = x1; vertices[0].fty = y1;
612  vertices[1].ftx = x2; vertices[1].fty = y2;
613  DwTo4UB(dwClr, vertices[0].color);
614  DwTo4UB(dwClr, vertices[1].color);
615  PerformMultiLines(sfcTarget, vertices, 2, width, nullptr);
616 }
617 
618 void C4Draw::DrawCircleDw(C4Surface * sfcTarget, float cx, float cy, float r, DWORD dwClr, float width)
619 {
620  // Draw as line segments
621  int32_t num_lines = 12 + int32_t(r / 10);
622  std::unique_ptr<C4BltVertex[]> vertices(new C4BltVertex[num_lines * 2]);
623  for (int32_t i = 0; i < num_lines; ++i)
624  {
625  float ang = float(i) * 2 * M_PI / num_lines;
626  int32_t iv = i * 2 + 1;
627  vertices[iv].ftx = cx + sin(ang) * r;
628  vertices[iv].fty = cy + cos(ang) * r;
629  DwTo4UB(dwClr, vertices[iv].color);
630  vertices[(iv + 1) % (num_lines * 2)] = vertices[iv];
631  }
632  PerformMultiLines(sfcTarget, vertices.get(), num_lines * 2, width, nullptr);
633 }
634 
635 void C4Draw::DrawFrameDw(C4Surface * sfcDest, int x1, int y1, int x2, int y2, DWORD dwClr, float width) // make these parameters float...?
636 {
637  C4BltVertex vertices[8];
638  vertices[0].ftx = x1; vertices[0].fty = y1;
639  vertices[1].ftx = x2; vertices[1].fty = y1;
640  vertices[2] = vertices[1];
641  vertices[3].ftx = x2; vertices[3].fty = y2;
642  vertices[4] = vertices[3];
643  vertices[5].ftx = x1; vertices[5].fty = y2;
644  vertices[6] = vertices[5];
645  vertices[7] = vertices[0];
646 
647  for(auto & vertex : vertices)
648  DwTo4UB(dwClr, vertex.color);
649 
650  PerformMultiLines(sfcDest, vertices, 8, width, nullptr);
651 }
652 
653 void C4Draw::DrawQuadDw(C4Surface * sfcTarget, float *ipVtx, DWORD dwClr1, DWORD dwClr2, DWORD dwClr3, DWORD dwClr4, C4ShaderCall* shader_call)
654 {
655  C4BltVertex vertices[6];
656  vertices[0].ftx = ipVtx[0]; vertices[0].fty = ipVtx[1];
657  vertices[1].ftx = ipVtx[2]; vertices[1].fty = ipVtx[3];
658  vertices[2].ftx = ipVtx[4]; vertices[2].fty = ipVtx[5];
659  vertices[3].ftx = ipVtx[6]; vertices[3].fty = ipVtx[7];
660  DwTo4UB(dwClr1, vertices[0].color);
661  DwTo4UB(dwClr2, vertices[1].color);
662  DwTo4UB(dwClr3, vertices[2].color);
663  DwTo4UB(dwClr4, vertices[3].color);
664  vertices[4] = vertices[0];
665  vertices[5] = vertices[2];
666  PerformMultiTris(sfcTarget, vertices, 6, nullptr, nullptr, nullptr, nullptr, 0, shader_call);
667 }
668 
669 void C4Draw::DrawPatternedCircle(C4Surface * sfcDest, int x, int y, int r, BYTE col, C4Pattern & Pattern, CStdPalette &rPal)
670 {
671  bool fRenderTarget = sfcDest->IsRenderTarget();
672  if (!fRenderTarget) if (!sfcDest->Lock()) return;
673  for (int ycnt = -r; ycnt < r; ycnt++)
674  {
675  int lwdt = (int)sqrt(float(r * r - ycnt * ycnt));
676  // Set line
677  if (fRenderTarget)
678  {
679  for (int xcnt = x - lwdt; xcnt < x + lwdt; ++xcnt)
680  {
681  DrawPix(sfcDest, xcnt, y + ycnt, Pattern.PatternClr(xcnt, y + ycnt));
682  }
683  }
684  else
685  {
686  for (int xcnt = x - lwdt; xcnt < x + lwdt; ++xcnt)
687  {
688  sfcDest->SetPixDw(xcnt, y + ycnt, Pattern.PatternClr(xcnt, y + ycnt));
689  }
690  }
691  }
692  if (!fRenderTarget) sfcDest->Unlock();
693 }
694 
695 void C4Draw::Grayscale(C4Surface * sfcSfc, int32_t iOffset)
696 {
697  // safety
698  if (!sfcSfc) return;
699  // change colors
700  int xcnt,ycnt,wdt=sfcSfc->Wdt,hgt=sfcSfc->Hgt;
701  // Lock surface
702  if (!sfcSfc->Lock()) return;
703  for (ycnt=0; ycnt<hgt; ycnt++)
704  {
705  for (xcnt=0; xcnt<wdt; xcnt++)
706  {
707  DWORD dwColor = sfcSfc->GetPixDw(xcnt,ycnt,false);
708  uint32_t r = GetRedValue(dwColor), g = GetGreenValue(dwColor), b = GetBlueValue(dwColor), a = dwColor >> 24;
709  int32_t gray = Clamp<int32_t>((r + g + b) / 3 + iOffset, 0, 255);
710  sfcSfc->SetPixDw(xcnt, ycnt, RGBA(gray, gray, gray, a));
711  }
712  }
713  sfcSfc->Unlock();
714 }
715 
716 bool C4Draw::GetPrimaryClipper(int &rX1, int &rY1, int &rX2, int &rY2)
717 {
718  // Store drawing clip values
719  rX1=fClipX1; rY1=fClipY1; rX2=fClipX2; rY2=fClipY2;
720  // Done
721  return true;
722 }
723 
725 {
726  int iWdt=std::min(iClipX2, RenderTarget->Wdt-1)-iClipX1+1;
727  int iHgt=std::min(iClipY2, RenderTarget->Hgt-1)-iClipY1+1;
728  int iX=iClipX1; if (iX<0) { iWdt+=iX; iX=0; }
729  int iY=iClipY1; if (iY<0) { iHgt+=iY; iY=0; }
730  return C4Rect(iX, iY, iWdt, iHgt);
731 }
732 
734 {
735  return C4Rect(0, 0, RenderTarget->Wdt, RenderTarget->Hgt);
736 }
737 
738 void C4Draw::SetGamma(float r, float g, float b, int32_t iRampIndex)
739 {
740  // Set
741  gamma[iRampIndex][0] = r;
742  gamma[iRampIndex][1] = g;
743  gamma[iRampIndex][2] = b;
744  // Recalculate resulting gamma. Note that we flip gamma direction here,
745  // because higher gammaOut means darker.
746  gammaOut[0] = gammaOut[1] = gammaOut[2] = 1.0f;
747  for (auto & i : gamma) {
748  gammaOut[0] /= i[0];
749  gammaOut[1] /= i[1];
750  gammaOut[2] /= i[2];
751  }
752 }
753 
755 {
756  for (auto & i : gamma) {
757  i[0] = 1.0f;
758  i[1] = 1.0f;
759  i[2] = 1.0f;
760  }
761  gammaOut[0] = 1.0f;
762  gammaOut[1] = 1.0f;
763  gammaOut[2] = 1.0f;
764 }
765 
767 {
768  return C4RGB(int(pow(float(GetRedValue(dwClr)) / 255.0f, gammaOut[0]) * 255.0),
769  int(pow(float(GetGreenValue(dwClr)) / 255.0f, gammaOut[1]) * 255.0),
770  int(pow(float(GetBlueValue(dwClr)) / 255.0f, gammaOut[2]) * 255.0));
771 }
772 
773 void C4Draw::SetZoom(float X, float Y, float Zoom)
774 {
775  this->ZoomX = X; this->ZoomY = Y; this->Zoom = Zoom;
776 }
777 
778 void C4Draw::ApplyZoom(float & X, float & Y)
779 {
780  X = (X - ZoomX) * Zoom + ZoomX;
781  Y = (Y - ZoomY) * Zoom + ZoomY;
782 }
783 
784 void C4Draw::RemoveZoom(float & X, float & Y)
785 {
786  X = (X - ZoomX) / Zoom + ZoomX;
787  Y = (Y - ZoomY) / Zoom + ZoomY;
788 }
789 
790 bool DDrawInit(C4AbstractApp * pApp, unsigned int iXRes, unsigned int iYRes, unsigned int iMonitor)
791 {
792  // create engine
793  #ifndef USE_CONSOLE
794  pDraw = new CStdGL();
795  #else
796  pDraw = new CStdNoGfx();
797  #endif
798  if (!pDraw) return false;
799  // init it
800  if (!pDraw->Init(pApp, iXRes, iYRes, iMonitor))
801  {
802  delete pDraw;
803  return false;
804  }
805  // done, success
806  return true;
807 }
808 
809 bool C4Draw::Init(C4AbstractApp * pApp, unsigned int iXRes, unsigned int iYRes, unsigned int iMonitor)
810 {
811  this->pApp = pApp;
812 
814 
815  if (!RestoreDeviceObjects())
816  return false;
817 
818  if (!CreatePrimaryClipper(iXRes, iYRes))
819  return Error(" Clipper failure.");
820 
821  return true;
822 }
823 
824 void C4Draw::DrawBoxFade(C4Surface * sfcDest, float iX, float iY, float iWdt, float iHgt, DWORD dwClr1, DWORD dwClr2, DWORD dwClr3, DWORD dwClr4, C4ShaderCall* shader_call)
825 {
826  // set vertex buffer data
827  // vertex order:
828  // 0=upper left dwClr1
829  // 1=lower left dwClr3
830  // 2=lower right dwClr4
831  // 3=upper right dwClr2
832  float vtx[8];
833  vtx[0] = iX ; vtx[1] = iY;
834  vtx[2] = iX ; vtx[3] = iY+iHgt;
835  vtx[4] = iX+iWdt; vtx[5] = iY+iHgt;
836  vtx[6] = iX+iWdt; vtx[7] = iY;
837  DrawQuadDw(sfcDest, vtx, dwClr1, dwClr3, dwClr4, dwClr2, shader_call);
838 }
839 
840 void C4Draw::DrawBoxDw(C4Surface * sfcDest, int iX1, int iY1, int iX2, int iY2, DWORD dwClr)
841 {
842  if (!sfcDest->IsRenderTarget())
843  {
844  // Box on non-render target: Emulate by setting pixels
845  if (!sfcDest->Lock()) return;
846  for (int y = iY1; y <= iY2; ++y)
847  for (int x = iX1; x <= iX2; ++x)
848  sfcDest->SetPixDw(x,y, dwClr);
849  sfcDest->Unlock();
850  }
851  else
852  {
853  DrawBoxFade(sfcDest, float(iX1), float(iY1), float(iX2 - iX1 + 1), float(iY2 - iY1 + 1), dwClr, dwClr, dwClr, dwClr, nullptr);
854  }
855 }
#define X(sdl, oc)
bool DDrawInit(C4AbstractApp *pApp, unsigned int iXRes, unsigned int iYRes, unsigned int iMonitor)
Definition: C4Draw.cpp:790
C4Draw * pDraw
Definition: C4Draw.cpp:42
unsigned char color[4]
Definition: C4Draw.h:63
float tx
Definition: C4Draw.h:62
float ftx
Definition: C4Draw.h:64
void DwTo4UB(DWORD dwClr, unsigned char(&r)[4])
Definition: C4Draw.h:29
float ty
Definition: C4Draw.h:62
float fty
Definition: C4Draw.h:64
float ftz
Definition: C4Draw.h:64
#define STDFONT_NOMARKUP
Definition: C4FontLoader.h:33
#define STDFONT_CENTERED
Definition: C4FontLoader.h:28
#define STDFONT_RIGHTALGN
Definition: C4FontLoader.h:31
bool Log(const char *szMessage)
Definition: C4Log.cpp:204
#define a
#define b
const int ARight
Definition: C4Surface.h:41
const int C4SF_Tileable
Definition: C4Surface.h:49
const int ACenter
Definition: C4Surface.h:41
uint8_t BYTE
uint32_t DWORD
bool SCopySegmentEx(const char *szString, int iSegment, char *sTarget, char cSep1, char cSep2, int iMaxL, bool fSkipWhitespace)
Definition: Standard.cpp:298
bool Inside(T ival, U lbound, V rbound)
Definition: Standard.h:43
uint32_t RGBA(uint32_t r, uint32_t g, uint32_t b, uint32_t a)
Definition: StdColors.h:22
#define C4RGB(r, g, b)
Definition: StdColors.h:26
#define GetRedValue(rgb)
Definition: StdColors.h:29
#define GetGreenValue(rgb)
Definition: StdColors.h:28
#define GetBlueValue(rgb)
Definition: StdColors.h:27
C4Window * pWindow
Definition: C4App.h:80
void Error(const char *m)
Definition: C4App.h:99
void SetMoveScale(float dx, float dy, float sx, float sy)
bool SetAsInv(C4BltTransform &rOfTransform)
void SetRotate(float iAngle, float fOffX, float fOffY)
void Set(float fA, float fB, float fC, float fD, float fE, float fF, float fG, float fH, float fI)
void TransformPoint(float &rX, float &rY) const
Definition: C4Draw.h:85
bool SubPrimaryClipper(int iX1, int iY1, int iX2, int iY2)
Definition: C4Draw.cpp:196
virtual bool Error(const char *szMsg)
Definition: C4Draw.cpp:494
void DrawCircleDw(C4Surface *sfcTarget, float cx, float cy, float r, DWORD dwClr, float width=1.0f)
Definition: C4Draw.cpp:618
bool ClipAll
Definition: C4Draw.h:105
DWORD dwBlitMode
Definition: C4Draw.h:110
float fClipX2
Definition: C4Draw.h:102
bool ApplyPrimaryClipper(C4Surface *sfcSurface)
Definition: C4Draw.cpp:227
void RemoveZoom(float &X, float &Y)
Definition: C4Draw.cpp:784
bool Blit(C4Surface *sfcSource, float fx, float fy, float fwdt, float fhgt, C4Surface *sfcTarget, float tx, float ty, float twdt, float thgt, bool fSrcColKey=false, const C4BltTransform *pTransform=nullptr)
Definition: C4Draw.cpp:301
bool fUsePerspective
Definition: C4Draw.h:114
float ZoomY
Definition: C4Draw.h:112
void DrawFrameDw(C4Surface *sfcDest, int x1, int y1, int x2, int y2, DWORD dwClr, float width=1.0f)
Definition: C4Draw.cpp:635
void DrawPix(C4Surface *sfcDest, float tx, float ty, DWORD dwCol)
Definition: C4Draw.cpp:598
C4Surface * RenderTarget
Definition: C4Draw.h:107
virtual void BlitLandscape(C4Surface *sfcSource, float fx, float fy, C4Surface *sfcTarget, float tx, float ty, float wdt, float hgt)
Definition: C4Draw.cpp:245
void Grayscale(C4Surface *sfcSfc, int32_t iOffset=0)
Definition: C4Draw.cpp:695
float fStClipX1
Definition: C4Draw.h:103
void DrawQuadDw(C4Surface *sfcTarget, float *ipVtx, DWORD dwClr1, DWORD dwClr2, DWORD dwClr3, DWORD dwClr4, C4ShaderCall *shader_call)
Definition: C4Draw.cpp:653
const StdMeshMatrix * MeshTransform
Definition: C4Draw.h:113
float gammaOut[3]
Definition: C4Draw.h:98
friend class C4Surface
Definition: C4Draw.h:213
bool BlitSimple(C4Surface *sfcSource, int fx, int fy, int fwdt, int fhgt, C4Surface *sfcTarget, int tx, int ty, int twdt, int thgt, bool fTransparency=true)
Definition: C4Draw.cpp:463
int32_t iClipY2
Definition: C4Draw.h:104
bool NoPrimaryClipper()
Definition: C4Draw.cpp:237
float ZoomX
Definition: C4Draw.h:112
C4Rect GetClipRect() const
Definition: C4Draw.cpp:724
bool RestorePrimaryClipper()
Definition: C4Draw.cpp:210
C4Rect GetOutRect() const
Definition: C4Draw.cpp:733
bool BlitUnscaled(C4Surface *sfcSource, float fx, float fy, float fwdt, float fhgt, C4Surface *sfcTarget, float tx, float ty, float twdt, float thgt, bool fSrcColKey=false, const C4BltTransform *pTransform=nullptr)
Definition: C4Draw.cpp:309
bool GetSurfaceSize(C4Surface *sfcSurface, int &iWdt, int &iHgt)
Definition: C4Draw.cpp:191
float fClipY1
Definition: C4Draw.h:102
virtual bool RestoreDeviceObjects()=0
bool StringOut(const char *szText, CStdFont &rFont, float fZoom, C4Surface *sfcDest, float iTx, float iTy, DWORD dwFCol=0xffffffff, BYTE byForm=ALeft, bool fDoMarkup=true)
Definition: C4Draw.cpp:570
virtual bool UpdateClipper()=0
bool RenderMesh(StdMeshInstance &instance, C4Surface *sfcTarget, float tx, float ty, float twdt, float thgt, DWORD dwPlayerColor, C4BltTransform *pTransform)
Definition: C4Draw.cpp:397
float fStClipY1
Definition: C4Draw.h:103
bool BlitSurface(C4Surface *sfcSurface, C4Surface *sfcTarget, int tx, int ty, bool fBlitBase)
Definition: C4Draw.cpp:511
virtual void PerformMultiLines(C4Surface *sfcTarget, const C4BltVertex *vertices, unsigned int n_vertices, float width, C4ShaderCall *shader_call)=0
void DrawBoxFade(C4Surface *sfcDest, float iX, float iY, float iWdt, float iHgt, DWORD dwClr1, DWORD dwClr2, DWORD dwClr3, DWORD dwClr4, C4ShaderCall *shader_call)
Definition: C4Draw.cpp:824
void DrawBoxDw(C4Surface *sfcDest, int iX1, int iY1, int iX2, int iY2, DWORD dwClr)
Definition: C4Draw.cpp:840
bool GetPrimaryClipper(int &rX1, int &rY1, int &rX2, int &rY2)
Definition: C4Draw.cpp:716
void SetGamma(float r, float g, float b, int32_t iRampIndex)
Definition: C4Draw.cpp:738
bool DetachPrimaryClipper(C4Surface *sfcSurface)
Definition: C4Draw.cpp:232
bool StorePrimaryClipper()
Definition: C4Draw.cpp:203
void DrawLineDw(C4Surface *sfcTarget, float x1, float y1, float x2, float y2, DWORD dwClr, float width=1.0f)
Definition: C4Draw.cpp:608
bool CreatePrimaryClipper(unsigned int iXRes, unsigned int iYRes)
Definition: C4Draw.cpp:501
virtual void Clear()
Definition: C4Draw.cpp:184
bool Init(C4AbstractApp *pApp, unsigned int iXRes, unsigned int iYRes, unsigned int iMonitor)
Definition: C4Draw.cpp:809
bool Active
Definition: C4Draw.h:96
int32_t iClipX1
Definition: C4Draw.h:104
void Blit8Fast(CSurface8 *sfcSource, int fx, int fy, C4Surface *sfcTarget, int tx, int ty, int wdt, int hgt)
Definition: C4Draw.cpp:251
float fStClipX2
Definition: C4Draw.h:103
const C4FoWRegion * pFoW
Definition: C4Draw.h:111
void SetZoom(float X, float Y, float Zoom)
Definition: C4Draw.cpp:773
C4AbstractApp * pApp
Definition: C4Draw.h:95
void DrawPatternedCircle(C4Surface *sfcDest, int x, int y, int r, BYTE col, C4Pattern &Pattern, CStdPalette &rPal)
Definition: C4Draw.cpp:669
void ResetGamma()
Definition: C4Draw.cpp:754
bool SetPrimaryClipper(int iX1, int iY1, int iX2, int iY2)
Definition: C4Draw.cpp:217
int32_t iClipX2
Definition: C4Draw.h:104
virtual void PerformMesh(StdMeshInstance &instance, float tx, float ty, float twdt, float thgt, DWORD dwPlayerColor, C4BltTransform *pTransform)=0
C4ScriptUniform scriptUniform
Definition: C4Draw.h:100
float gamma[C4MaxGammaRamps][3]
Definition: C4Draw.h:97
float fClipY2
Definition: C4Draw.h:102
void ApplyZoom(float &X, float &Y)
Definition: C4Draw.cpp:778
DWORD ApplyGammaTo(DWORD dwClr)
Definition: C4Draw.cpp:766
bool BlitModulated
Definition: C4Draw.h:108
bool Blit8(C4Surface *sfcSource, int fx, int fy, int fwdt, int fhgt, C4Surface *sfcTarget, int tx, int ty, int twdt, int thgt, bool fSrcColKey=false, const C4BltTransform *pTransform=nullptr)
Definition: C4Draw.cpp:418
virtual bool PrepareRendering(C4Surface *sfcToSurface)=0
float fClipX1
Definition: C4Draw.h:102
int32_t iClipY1
Definition: C4Draw.h:104
virtual void PerformMultiTris(C4Surface *sfcTarget, const C4BltVertex *vertices, unsigned int n_vertices, const C4BltTransform *pTransform, C4TexRef *pTex, C4TexRef *pOverlay, C4TexRef *pNormal, DWORD dwOverlayClrMod, C4ShaderCall *shader_call)=0
virtual void Default()
Definition: C4Draw.cpp:169
bool BlitSurfaceTile(C4Surface *sfcSurface, C4Surface *sfcTarget, float iToX, float iToY, float iToWdt, float iToHgt, float iOffsetX, float iOffsetY, C4ShaderCall *shader_call)
Definition: C4Draw.cpp:529
float fStClipY2
Definition: C4Draw.h:103
virtual void PerformMultiPix(C4Surface *sfcTarget, const C4BltVertex *vertices, unsigned int n_vertices, C4ShaderCall *shader_call)=0
bool TextOut(const char *szText, CStdFont &rFont, float fZoom, C4Surface *sfcDest, float iTx, float iTy, DWORD dwFCol=0xffffffff, BYTE byForm=ALeft, bool fDoMarkup=true)
Definition: C4Draw.cpp:561
float Zoom
Definition: C4Draw.h:116
DWORD PatternClr(unsigned int iX, unsigned int iY) const
Definition: C4Draw.cpp:159
bool Set(class C4Surface *sfcSource, int iZoom=0)
Definition: C4Draw.cpp:114
C4Pattern & operator=(const C4Pattern &)
Definition: C4Draw.cpp:94
void Clear()
Definition: C4Draw.cpp:146
C4Pattern()
Definition: C4Draw.cpp:138
Definition: C4Rect.h:28
bool SetPixDw(int iX, int iY, DWORD dwCol)
Definition: C4Surface.cpp:576
int Wdt
Definition: C4Surface.h:65
DWORD GetPixDw(int iX, int iY, bool fApplyModulation)
Definition: C4Surface.cpp:491
int Scale
Definition: C4Surface.h:66
C4Surface * pNormalSfc
Definition: C4Surface.h:80
std::unique_ptr< C4TexRef > texture
Definition: C4Surface.h:78
bool GetSurfaceSize(int &irX, int &irY)
Definition: C4Surface.cpp:444
bool fPrimary
Definition: C4Surface.h:89
DWORD ClrByOwnerClr
Definition: C4Surface.h:81
bool Unlock()
Definition: C4Surface.cpp:464
C4Surface * pMainSfc
Definition: C4Surface.h:79
bool Lock()
Definition: C4Surface.cpp:453
bool BltPix(int iX, int iY, C4Surface *sfcSource, int iSrcX, int iSrcY, bool fTransparency)
Definition: C4Surface.cpp:591
bool IsRenderTarget()
Definition: C4Surface.cpp:144
int Hgt
Definition: C4Surface.h:65
int iSizeX
Definition: C4Surface.h:157
int iSizeY
Definition: C4Surface.h:158
C4Surface * pSurface
Definition: C4Window.h:275
int GetLineHeight() const
Definition: C4FontLoader.h:125
void DrawText(C4Surface *sfcDest, float iX, float iY, DWORD dwColor, const char *szText, DWORD dwFlags, C4Markup &Markup, float fZoom)
CStdPalette * pPal
Definition: CSurface8.h:31
BYTE GetPix(int iX, int iY) const
Definition: CSurface8.h:49
void ReorderFaces(StdMeshMatrix *global_trans)
Definition: StdMesh.cpp:1552
bool UpdateBoneTransforms()
Definition: StdMesh.cpp:1471
static StdMeshMatrix Identity()
DWORD GetClr(BYTE byCol)
Definition: StdColors.h:188