performantes Aero Overlay

rn_

I'm not online, that's just my bot.
7 Jan 2011
5,707
11,147
#1
Yo, hab mal meine alten Projekte durchstöbert, was gefunden und bisschen überarbeitet. Es gibt ja viele, die im external Bereich arbeiten und ihr Visuals mittels einem Aero Overlay und DirectX rendern. Kann man machen, allerdings ist DirectX in so einem Bereich nicht gerade das Beste. Das ganze basiert auf der D2D1(DirectDraw) + DirectWrite Schnitstelle und funktioniert ab Windows 7, eventuell auch unter Windows Vista. Außerdem benötigt man kein extra SDK wie für Direct X und hat dank Direct Write TrueType Unterstützung was Fontrendering angeht.
? --- auf nun mach mal schöne visuals x))

Github: https://github.com/HazeProductions/D2D1-Aero

Rendering support:
  • Bordered Box
  • Outlined Bordered Box
  • Line
  • Rounded Rectangle
  • Outlined rounded Rectangle
  • Rectangle
  • Outlined Rectangle
  • String

Example:
Code:
#include "Overlay.hpp"
#include <chrono>
#include <memory>
#include <thread>
using namespace std;
using namespace haze;

LRESULT CALLBACK WndProc( HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam )
{
    switch( msg ) {
    case WM_CLOSE:
        DestroyWindow( hwnd );
        exit( 0 );
    case WM_DESTROY:
        PostQuitMessage( 0 );
        break;
    default:
        return DefWindowProc( hwnd, msg, wParam, lParam );
    }
    return 0;
}

int32_t main( int32_t argc, char** argv )
{
    if( argc != 2 ) {
        cout << "usage: executable.exe <window title>" << endl;
        return 1;
    }

    auto pOverlay = make_unique< CDirect2DOverlay >();
    if( !pOverlay->Create( argv[ 1 ], WndProc ) ) {
        cout << "failed to create overlay" << endl;
        return 1;
    }

    auto* pFont = pOverlay->GetFont( "default", "Arial", 12.f );
    if( !pFont ) {
        cout << "failed to create font" << endl;
        return 1;
    }

    pOverlay->AddToRenderFrame( []( const CDirect2DOverlay::CDirect2DSurface* pSurface ) {
        pSurface->String( 5.f, 5.f, "default", Color( 0, 255, 0 ), "Overlay-FPS: %ju", pSurface->GetFramesPerSecond() );
    } );

    while( pOverlay->Render() ) {
        this_thread::sleep_for( chrono::milliseconds( 1 ) );
    }
    return 0;
}
Screen( man beachte die overlay fps): http://i.imgur.com/DnuMSF5.jpg

greetz
 

---

Coder
18 Oct 2010
2,276
2,244
#2
Was wolltest du mir nun sagen? 700fps in nem Overlay wo nichts derzeitig gedrawt wird is schlecht..

Edit: und ja ich gehe auf solche Anspielung gerne ein
 

Dr_Pepper

Active Member
11 May 2013
97
198
#3
basiert auf der D2D1(DirectDraw)
Direct2D ist alles, aber KEIN DirectDraw wrapper. Im Grafikbeschleunigten Modus ist Direct2D ein
DirectX10 Wrapper, und im GDI-Kompatiblen Modus wird auf der CPU mit GDI gerendert.


Überhaupt, wenn ich jetzt noch ein "Aero-Overlay" sehe bekomm ich das kotzen.
Code:
if( FAILED( DwmExtendFrameIntoClientArea( m_hOvHwnd, &DWM_MARGINS ) ) )
{
    return false;
}
Das ist API-Abuse of Doom. Denkt eigentlich mal irgendjemand nach, was hier
überhaupt gemacht wird? Die Funktion soll eigentlich den Fensterrand in die Clientarea
erweitern, z.B. so:



Den nicht vorhandenen Rand eines Layered-Windows in die Clientarea erweitern sollte
eigentlich garnicht funktionieren. Damit ein Overlay zu erstellen ist einfach nur unsauber.

Genauso wie die Methode Klicks durch das Fenster mithilfe von WS_EX_Layered durchfallen
zu lassen. Normalerweise kann man nicht einfach durch Layered-Windows durchklicken.
Das Funktioniert nur, weil die Windows-API nicht auf dem Framebuffer von DX10
zugreifen kann, welcher im GPU-Speicher ist, und somit auch kein Hittesting möglich ist.

Man könnte sich ja mal in der MSDN informieren, wie man Layered-Windows wirklich
benutzt, aber das würde ja Eigeninitiative erfordern.

Aber nein, stattdessen kopiert man halt die gleichen Kackmethoden von anderen CopyPastern
die schon seit Jahren im Internet herumgeistern.