Skip to content

Commit 493d9fb

Browse files
committed
Merge branch 'master' into next
2 parents afaabab + d965e06 commit 493d9fb

File tree

530 files changed

+5104
-10797
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

530 files changed

+5104
-10797
lines changed

.github/workflows/build.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ jobs:
2121

2222
- name: Download DirectX
2323
if: steps.cache-dxfiles.outputs.cache-hit != 'true'
24-
run: Invoke-WebRequest https://mirror.mtasa.com/bdata/DXFiles.zip -OutFile utils/DXFiles.zip
24+
run: Invoke-WebRequest https://mirror-cdn.multitheftauto.com/bdata/DXFiles.zip -OutFile utils/DXFiles.zip
2525
shell: powershell
2626

2727
- name: Extract DirectX

Client/cefweb/CWebView.cpp

Lines changed: 84 additions & 77 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,11 @@
1414
#include <cef3/cef/include/cef_task.h>
1515
#include "CWebDevTools.h"
1616

17+
namespace
18+
{
19+
const int CEF_PIXEL_STRIDE = 4;
20+
}
21+
1722
CWebView::CWebView(bool bIsLocal, CWebBrowserItem* pWebBrowserRenderItem, bool bTransparent)
1823
{
1924
m_bIsLocal = bIsLocal;
@@ -39,9 +44,6 @@ CWebView::~CWebView()
3944
// Ensure that CefRefPtr::~CefRefPtr doesn't try to release it twice (it has already been released in CWebView::OnBeforeClose)
4045
m_pWebView = nullptr;
4146

42-
// Make sure we don't dead lock the CEF render thread
43-
m_RenderData.cv.notify_all();
44-
4547
OutputDebugLine("CWebView::~CWebView");
4648
}
4749

@@ -75,9 +77,6 @@ void CWebView::CloseBrowser()
7577
// CefBrowserHost::CloseBrowser calls the destructor after the browser has been destroyed
7678
m_bBeingDestroyed = true;
7779

78-
// Make sure we don't dead lock the CEF render thread
79-
m_RenderData.cv.notify_all();
80-
8180
if (m_pWebView)
8281
m_pWebView->GetHost()->CloseBrowser(true);
8382
}
@@ -182,15 +181,17 @@ void CWebView::ClearTexture()
182181
IDirect3DSurface9* pD3DSurface = m_pWebBrowserRenderItem->m_pD3DRenderTargetSurface;
183182
if (!pD3DSurface)
184183
return;
185-
186-
D3DLOCKED_RECT LockedRect;
184+
187185
D3DSURFACE_DESC SurfaceDesc;
186+
if (FAILED(pD3DSurface->GetDesc(&SurfaceDesc)))
187+
return;
188188

189-
pD3DSurface->GetDesc(&SurfaceDesc);
190-
pD3DSurface->LockRect(&LockedRect, NULL, 0);
191-
192-
memset(LockedRect.pBits, 0xFF, SurfaceDesc.Width * SurfaceDesc.Height * 4);
193-
pD3DSurface->UnlockRect();
189+
D3DLOCKED_RECT LockedRect;
190+
if (SUCCEEDED(pD3DSurface->LockRect(&LockedRect, NULL, D3DLOCK_DISCARD)))
191+
{
192+
memset(LockedRect.pBits, 0xFF, SurfaceDesc.Height * LockedRect.Pitch);
193+
pD3DSurface->UnlockRect();
194+
}
194195
}
195196

196197
void CWebView::UpdateTexture()
@@ -210,61 +211,76 @@ void CWebView::UpdateTexture()
210211
{
211212
// Lock surface
212213
D3DLOCKED_RECT LockedRect;
213-
pSurface->LockRect(&LockedRect, nullptr, 0);
214-
215-
// Dirty rect implementation, don't use this as loops are significantly slower than memcpy
216-
auto surfaceData = static_cast<byte*>(LockedRect.pBits);
217-
auto sourceData = static_cast<const byte*>(m_RenderData.buffer);
218-
auto pitch = LockedRect.Pitch;
219-
220-
// Update view area
221-
if (m_RenderData.changed)
214+
if (SUCCEEDED(pSurface->LockRect(&LockedRect, nullptr, 0)))
222215
{
223-
// Update changed state
224-
m_RenderData.changed = false;
225-
226-
if (m_RenderData.dirtyRects.size() > 0 && m_RenderData.dirtyRects[0].width == m_RenderData.width &&
227-
m_RenderData.dirtyRects[0].height == m_RenderData.height)
216+
// Dirty rect implementation, don't use this as loops are significantly slower than memcpy
217+
const auto destData = static_cast<byte*>(LockedRect.pBits);
218+
const auto sourceData = static_cast<const byte*>(m_RenderData.buffer);
219+
const auto destPitch = LockedRect.Pitch;
220+
const auto sourcePitch = m_RenderData.width * CEF_PIXEL_STRIDE;
221+
222+
// Update view area
223+
if (m_RenderData.changed)
228224
{
229-
// Update whole texture
230-
memcpy(surfaceData, sourceData, m_RenderData.width * m_RenderData.height * 4);
231-
}
232-
else
233-
{
234-
// Update dirty rects
235-
for (auto& rect : m_RenderData.dirtyRects)
225+
// Update changed state
226+
m_RenderData.changed = false;
227+
228+
if (m_RenderData.dirtyRects.size() > 0 && m_RenderData.dirtyRects[0].width == m_RenderData.width &&
229+
m_RenderData.dirtyRects[0].height == m_RenderData.height)
236230
{
237-
for (int y = rect.y; y < rect.y + rect.height; ++y)
231+
// Note that D3D texture size can be hardware dependent(especially with dynamic texture)
232+
// When destination and source pitches differ we must copy pixels row by row
233+
if (destPitch == sourcePitch)
234+
memcpy(destData, sourceData, destPitch * m_RenderData.height);
235+
else
238236
{
239-
int index = y * pitch + rect.x * 4;
240-
memcpy(&surfaceData[index], &sourceData[index], rect.width * 4);
237+
for (int y = 0; y < m_RenderData.height; ++y)
238+
{
239+
const int sourceIndex = y * sourcePitch;
240+
const int destIndex = y * destPitch;
241+
242+
memcpy(&destData[destIndex], &sourceData[sourceIndex], std::min(sourcePitch, destPitch));
243+
}
244+
}
245+
}
246+
else
247+
{
248+
// Update dirty rects
249+
for (const auto& rect : m_RenderData.dirtyRects)
250+
{
251+
for (int y = rect.y; y < rect.y + rect.height; ++y)
252+
{
253+
// Note that D3D texture size can be hardware dependent(especially with dynamic texture)
254+
// We cannot be sure that source and destination pitches are the same
255+
const int sourceIndex = y * sourcePitch + rect.x * CEF_PIXEL_STRIDE;
256+
const int destIndex = y * destPitch + rect.x * CEF_PIXEL_STRIDE;
257+
258+
memcpy(&destData[destIndex], &sourceData[sourceIndex], rect.width * CEF_PIXEL_STRIDE);
259+
}
241260
}
242261
}
243262
}
244-
}
245263

246-
// Update popup area (override certain areas of the view texture)
247-
bool popupSizeMismatches = m_RenderData.popupRect.x + m_RenderData.popupRect.width >= (int)m_pWebBrowserRenderItem->m_uiSizeX ||
248-
m_RenderData.popupRect.y + m_RenderData.popupRect.height >= (int)m_pWebBrowserRenderItem->m_uiSizeY;
264+
// Update popup area (override certain areas of the view texture)
265+
const bool popupSizeMismatches = m_RenderData.popupRect.x + m_RenderData.popupRect.width >= (int)m_pWebBrowserRenderItem->m_uiSizeX ||
266+
m_RenderData.popupRect.y + m_RenderData.popupRect.height >= (int)m_pWebBrowserRenderItem->m_uiSizeY;
249267

250-
if (m_RenderData.popupShown && !popupSizeMismatches)
251-
{
252-
auto popupPitch = m_RenderData.popupRect.width * 4;
253-
for (int y = 0; y < m_RenderData.popupRect.height; ++y)
268+
if (m_RenderData.popupShown && !popupSizeMismatches)
254269
{
255-
int sourceIndex = y * popupPitch;
256-
int destIndex = (y + m_RenderData.popupRect.y) * pitch + m_RenderData.popupRect.x * 4;
270+
const auto popupPitch = m_RenderData.popupRect.width * CEF_PIXEL_STRIDE;
271+
for (int y = 0; y < m_RenderData.popupRect.height; ++y)
272+
{
273+
const int sourceIndex = y * popupPitch;
274+
const int destIndex = (y + m_RenderData.popupRect.y) * destPitch + m_RenderData.popupRect.x * CEF_PIXEL_STRIDE;
257275

258-
memcpy(&surfaceData[destIndex], &m_RenderData.popupBuffer[sourceIndex], popupPitch);
276+
memcpy(&destData[destIndex], &m_RenderData.popupBuffer[sourceIndex], popupPitch);
277+
}
259278
}
260-
}
261279

262-
// Unlock surface
263-
pSurface->UnlockRect();
280+
// Unlock surface
281+
pSurface->UnlockRect();
282+
}
264283
}
265-
266-
// Resume CEF render thread
267-
m_RenderData.cv.notify_all();
268284
}
269285

270286
void CWebView::ExecuteJavascript(const SString& strJavascriptCode)
@@ -431,9 +447,6 @@ void CWebView::Resize(const CVector2D& size)
431447
// Send resize event to CEF
432448
if (m_pWebView)
433449
m_pWebView->GetHost()->WasResized();
434-
435-
// Tell CEF to render a new frame
436-
m_RenderData.cv.notify_all();
437450
}
438451

439452
CVector2D CWebView::GetSize()
@@ -661,7 +674,7 @@ void CWebView::OnPopupSize(CefRefPtr<CefBrowser> browser, const CefRect& rect)
661674
m_RenderData.popupRect = rect;
662675

663676
// Resize buffer
664-
m_RenderData.popupBuffer.reset(new byte[rect.width * rect.height * 4]);
677+
m_RenderData.popupBuffer.reset(new byte[rect.width * rect.height * CEF_PIXEL_STRIDE]);
665678
}
666679

667680
////////////////////////////////////////////////////////////////////
@@ -677,31 +690,25 @@ void CWebView::OnPaint(CefRefPtr<CefBrowser> browser, CefRenderHandler::PaintEle
677690
if (m_bBeingDestroyed)
678691
return;
679692

693+
std::unique_lock<std::mutex> lock(m_RenderData.dataMutex);
694+
695+
// Copy popup buffer
696+
if (paintType == PET_POPUP)
680697
{
681-
std::lock_guard<std::mutex> lock(m_RenderData.dataMutex);
682-
683-
// Copy popup buffer
684-
if (paintType == PET_POPUP)
698+
if (m_RenderData.popupBuffer)
685699
{
686-
if (m_RenderData.popupBuffer)
687-
{
688-
memcpy(m_RenderData.popupBuffer.get(), buffer, width * height * 4);
689-
}
690-
691-
return; // We don't have to wait as we've copied the buffer already
700+
memcpy(m_RenderData.popupBuffer.get(), buffer, width * height * CEF_PIXEL_STRIDE);
692701
}
693702

694-
// Store render data
695-
m_RenderData.buffer = buffer;
696-
m_RenderData.width = width;
697-
m_RenderData.height = height;
698-
m_RenderData.dirtyRects = dirtyRects;
699-
m_RenderData.changed = true;
703+
return; // We don't have to wait as we've copied the buffer already
700704
}
701705

702-
// Wait for the main thread to handle drawing the texture
703-
std::unique_lock<std::mutex> lock(m_RenderData.cvMutex);
704-
m_RenderData.cv.wait(lock);
706+
// Store render data
707+
m_RenderData.buffer = buffer;
708+
m_RenderData.width = width;
709+
m_RenderData.height = height;
710+
m_RenderData.dirtyRects = dirtyRects;
711+
m_RenderData.changed = true;
705712
}
706713

707714
////////////////////////////////////////////////////////////////////

Client/cefweb/CWebView.h

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -176,7 +176,7 @@ class CWebView : public CWebViewInterface,
176176
CefRefPtr<CefBrowser> m_pWebView;
177177
CWebBrowserItem* m_pWebBrowserRenderItem;
178178

179-
bool m_bBeingDestroyed;
179+
std::atomic_bool m_bBeingDestroyed;
180180
bool m_bIsLocal;
181181
bool m_bIsRenderingPaused;
182182
bool m_bIsTransparent;
@@ -192,8 +192,6 @@ class CWebView : public CWebViewInterface,
192192
{
193193
bool changed = false;
194194
std::mutex dataMutex;
195-
std::mutex cvMutex;
196-
std::condition_variable cv;
197195

198196
const void* buffer;
199197
int width, height;

Client/core/CChat.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
#include "StdInc.h"
1313
#include <game/CGame.h>
14+
#include <game/CSettings.h>
1415

1516
using std::vector;
1617

Client/core/CClientVariables.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -329,7 +329,9 @@ void CClientVariables::LoadDefaults()
329329
DEFAULT("tyre_smoke_enabled", 1); // Enable tyre smoke
330330
DEFAULT("high_detail_vehicles", 0); // Disable rendering high detail vehicles all the time
331331
DEFAULT("high_detail_peds", 0); // Disable rendering high detail peds all the time
332+
DEFAULT("blur", 1); // Enable blur
332333
DEFAULT("corona_reflections", 0); // Disable corona rain reflections
334+
DEFAULT("dynamic_ped_shadows", 0); // Disable dynamic ped shadows
333335
DEFAULT("fast_clothes_loading", 1); // 0-off 1-auto 2-on
334336
DEFAULT("allow_screen_upload", 1); // 0-off 1-on
335337
DEFAULT("allow_external_sounds", 1); // 0-off 1-on

Client/core/CCommandFuncs.cpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
#include "StdInc.h"
1313
#include <game/CGame.h>
14+
#include <game/CHud.h>
1415

1516
using std::list;
1617

@@ -464,7 +465,7 @@ void CCommandFuncs::FakeLag(const char* szCmdLine)
464465
{
465466
if (!CCore::GetSingleton().IsFakeLagCommandEnabled())
466467
{
467-
g_pCore->GetConsole()->Print("fakelag command no enabled");
468+
g_pCore->GetConsole()->Print("fakelag command not enabled");
468469
return;
469470
}
470471

Client/core/CCommands.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -166,6 +166,13 @@ bool CCommands::Execute(const char* szCommand, const char* szParametersIn, bool
166166
val = val.substr(nOpIndex + 1);
167167
TrimWhiteSpace(val);
168168
CVARS_SET(key, val);
169+
170+
// HACK: recalculate frame rate limit on cvar change
171+
if (key == "fps_limit" && m_FpsLimitTimer.Get() >= 500 && CCore::GetSingleton().IsConnected())
172+
{
173+
CCore::GetSingleton().RecalculateFrameRateLimit(-1, true);
174+
m_FpsLimitTimer.Reset();
175+
}
169176
}
170177
else
171178
{

Client/core/CCommands.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ class CCommands : public CCommandsInterface, public CSingleton<CCommands>
4444
void ExecuteHandler(PFNCOMMAND pfnHandler, const char* szParameters);
4545

4646
std::list<COMMANDENTRY*> m_CommandList;
47+
CElapsedTime m_FpsLimitTimer;
4748

4849
pfnExecuteCommandHandler m_pfnExecuteHandler;
4950
};

Client/core/CCore.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
#include "StdInc.h"
1313
#include <game/CGame.h>
14+
#include <game/CSettings.h>
1415
#include <Accctrl.h>
1516
#include <Aclapi.h>
1617
#include "Userenv.h" // This will enable SharedUtil::ExpandEnvString
@@ -573,9 +574,12 @@ void CCore::ApplyGameSettings()
573574
CVARS_GET("tyre_smoke_enabled", bVal);
574575
m_pMultiplayer->SetTyreSmokeEnabled(bVal);
575576
pGameSettings->UpdateFieldOfViewFromSettings();
577+
pGameSettings->ResetBlurEnabled();
576578
pGameSettings->ResetVehiclesLODDistance();
577579
pGameSettings->ResetPedsLODDistance();
578580
pGameSettings->ResetCoronaReflectionsEnabled();
581+
CVARS_GET("dynamic_ped_shadows", bVal);
582+
pGameSettings->SetDynamicPedShadowsEnabled(bVal);
579583
pController->SetVerticalAimSensitivityRawValue(CVARS_GET_VALUE<float>("vertical_aim_sensitivity"));
580584
CVARS_GET("mastervolume", fVal);
581585
pGameSettings->SetRadioVolume(pGameSettings->GetRadioVolume() * fVal);

Client/core/CCrashDumpWriter.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@
1111

1212
#include "StdInc.h"
1313
#include <game/CGame.h>
14+
#include <game/CPools.h>
15+
#include <game/CRenderWare.h>
1416
#include <multiplayer/CMultiplayer.h>
1517

1618
#define LOG_EVENT_SIZE 200

0 commit comments

Comments
 (0)