bool BoidsSimulation::OnEvent( MSG* msg ) { switch (msg->message) { case WM_MOUSEWHEEL: { auto delta = GET_WHEEL_DELTA_WPARAM( msg->wParam ); m_camera.ZoomRadius( -0.1f*delta ); } case WM_POINTERDOWN: case WM_POINTERUPDATE: case WM_POINTERUP: { auto pointerId = GET_POINTERID_WPARAM( msg->wParam ); POINTER_INFO pointerInfo; if (GetPointerInfo( pointerId, &pointerInfo )) { if (msg->message == WM_POINTERDOWN) { // Compute pointer position in render units POINT p = pointerInfo.ptPixelLocation; ScreenToClient( Core::g_hwnd, &p ); RECT clientRect; GetClientRect( Core::g_hwnd, &clientRect ); p.x = p.x * Core::g_config.swapChainDesc.Width / (clientRect.right - clientRect.left); p.y = p.y * Core::g_config.swapChainDesc.Height / (clientRect.bottom - clientRect.top); // Camera manipulation m_camera.AddPointer( pointerId ); } } // Otherwise send it to the camera controls m_camera.ProcessPointerFrames( pointerId, &pointerInfo ); if (msg->message == WM_POINTERUP) m_camera.RemovePointer( pointerId ); } } return false; }
// Event handler LRESULT CALLBACK MyWndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { gpRenderer->HandleEvent(message, wParam, lParam); switch (message) { case WM_CLOSE: gShouldClose = true; return 0; case WM_SIZE: { UINT ww = LOWORD(lParam); UINT wh = HIWORD(lParam); // Ignore resizing to minimized if (ww == 0 || wh == 0) return 0; gWindowWidth = (int)ww; gWindowHeight = (int)wh; gRenderWidth = (UINT)(double(gWindowWidth) * gRenderScale); gRenderHeight = (UINT)(double(gWindowHeight) * gRenderScale); // Update camera projection float aspect = (float)gRenderWidth / (float)gRenderHeight; gCamera.Projection(DirectX::XM_PIDIV2 * 0.8f * 3 / 2, aspect); ResizeApp(gWindowWidth, gWindowHeight); return 0; } case WM_MOUSEWHEEL: { auto delta = GET_WHEEL_DELTA_WPARAM(wParam); gCamera.ZoomRadius(-0.07f * delta); return 0; } case WM_POINTERDOWN: case WM_POINTERUPDATE: case WM_POINTERUP: { auto pointerId = GET_POINTERID_WPARAM(wParam); POINTER_INFO pointerInfo; if (GetPointerInfo(pointerId, &pointerInfo)) { if (message == WM_POINTERDOWN) { // Compute pointer position in render units POINT p = pointerInfo.ptPixelLocation; ScreenToClient(hWnd, &p); RECT clientRect; GetClientRect(hWnd, &clientRect); p.x = p.x * gRenderWidth / (clientRect.right - clientRect.left); p.y = p.y * gRenderHeight / (clientRect.bottom - clientRect.top); gCamera.AddPointer(pointerId); } // Otherwise send it to the camera controls gCamera.ProcessPointerFrames(pointerId, &pointerInfo); if (message == WM_POINTERUP) gCamera.RemovePointer(pointerId); } return 0; } default: return DefWindowProc(hWnd, message, wParam, lParam); } }
LRESULT CALLBACK WindowProcSubclass(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData) { CommonAPI* api = CommonAPI::getInstance(); POINTER_INFO pointerInfo = {}; HRESULT hr; switch (message) { case WM_POINTERDOWN: // Get frame id from current message if (GetPointerInfo(GET_POINTERID_WPARAM(wParam), &pointerInfo)) { asIScriptFunction* sf = api->module->GetFunctionByDecl("int OnPointerDown(int x, int y)"); if(sf == 0) FILE_LOG(logERROR) << "The script must have the function 'OnPointerDown'."; asIScriptContext* ctx = api->engine->CreateContext(); ctx->Prepare(sf); ctx->SetArgDWord(0, pointerInfo.ptPixelLocation.x); ctx->SetArgDWord(1, pointerInfo.ptPixelLocation.y); ctx->Execute(); int meow = ctx->GetReturnQWord(); if(meow >= 0 && sf != 0) { // Background was hit hr = AddPointerInteractionContext(api->interactionContexts[meow], GET_POINTERID_WPARAM(wParam)); if (SUCCEEDED(hr)) { api->pointers[meow].push_back(GET_POINTERID_WPARAM(wParam)); api->ProcessPointerFrames(wParam, pointerInfo, meow); } } } break; case WM_POINTERUPDATE: // Get frame id from current message if (GetPointerInfo(GET_POINTERID_WPARAM(wParam), &pointerInfo)) { // Background if (api->IsPointerInteraction(GET_POINTERID_WPARAM(wParam))) { api->ProcessPointerFrames(wParam, pointerInfo, 0); } } break; case WM_POINTERUP: // Get frame id from current message if (GetPointerInfo(GET_POINTERID_WPARAM(wParam), &pointerInfo)) { // Background int t = api->IsPointerInteraction(GET_POINTERID_WPARAM(wParam)); if (t >= 0) { api->ProcessPointerFrames(wParam, pointerInfo, t); hr = RemovePointerInteractionContext(api->interactionContexts[t], GET_POINTERID_WPARAM(wParam)); asIScriptFunction* sf = api->module->GetFunctionByDecl("void OnPointerUp(int)"); if(sf == 0) FILE_LOG(logERROR) << "The script must have the function 'OnPointerUp'."; asIScriptContext* ctx = api->engine->CreateContext(); ctx->Prepare(sf); ctx->SetArgDWord(0, t); ctx->Execute(); if (SUCCEEDED(hr)) { if (!api->pointers[t].empty()) api->pointers[t].remove(GET_POINTERID_WPARAM(wParam)); } } } break; default: return DefSubclassProc(hWnd, message, wParam, lParam); } return DefSubclassProc(hWnd, message, wParam, lParam); }