diff --git a/CMakeLists.txt b/CMakeLists.txt
index 9ce83c3f76734f6beea4686fcc557e318952ba3e..accb300a7bedac98153af43dcc3310fb68c145b8 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -29,13 +29,12 @@ else()
   project(jami)
 endif()
 
+include(${PROJECT_SOURCE_DIR}/extras/build/cmake/extra_tools.cmake)
+
 option(WITH_DAEMON_SUBMODULE "Build with daemon submodule" ON)
 option(JAMICORE_AS_SUBDIR "Build Jami-core as a subdir dependency" OFF)
 option(ENABLE_TESTS "Build with tests" OFF)
 option(WITH_WEBENGINE "Build with WebEngine" ON)
-if(WITH_WEBENGINE)
-  add_definitions(-DWITH_WEBENGINE)
-endif()
 option(ENABLE_LIBWRAP "Enable libwrap (single process mode)" ON)
 if(NOT (${CMAKE_SYSTEM_NAME} MATCHES "Linux")
     OR ENABLE_LIBWRAP
@@ -51,6 +50,10 @@ if(ENABLE_ASAN AND NOT MSVC)
   set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -fsanitize=address")
 endif()
 
+# These values are exposed to QML and are better off being defined as values.
+define_macro_with_value(WITH_WEBENGINE)
+define_macro_with_value(APPSTORE)
+
 # jami-core
 if(NOT WITH_DAEMON_SUBMODULE)
   set(DAEMON_DIR ${PROJECT_SOURCE_DIR}/../daemon)
@@ -837,7 +840,6 @@ else()
           MACOSX_BUNDLE_COPYRIGHT "${PROJ_COPYRIGHT}")
       if(APPSTORE)
           message(STATUS "app store version")
-          add_definitions(-DAPPSTORE)
           set_target_properties(${PROJECT_NAME} PROPERTIES
                XCODE_ATTRIBUTE_CODE_SIGN_ENTITLEMENTS "${CMAKE_CURRENT_SOURCE_DIR}/resources/entitlements/appstore/Jami.entitlements")
       else()
diff --git a/extras/build/cmake/extra_tools.cmake b/extras/build/cmake/extra_tools.cmake
new file mode 100644
index 0000000000000000000000000000000000000000..3de624da58df731011eaa03ca7a5c3cc189e04cd
--- /dev/null
+++ b/extras/build/cmake/extra_tools.cmake
@@ -0,0 +1,38 @@
+# Copyright (C) 2024 Savoir-faire Linux Inc.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 3 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301 USA.
+
+# Function to define a macro with a specific value or default to 0 if not already set.
+# This is useful to if within the code we don't want to use #ifdef but rather use the
+# value of the macro.
+function(define_macro_with_value MACRO_NAME)
+  if(DEFINED ${MACRO_NAME})
+    # Convert ON/OFF to 1/0
+    if(${${MACRO_NAME}} STREQUAL "ON")
+      set(MACRO_VALUE "1")
+    elseif(${${MACRO_NAME}} STREQUAL "OFF")
+      set(MACRO_VALUE "0")
+    # If the macro is defined and its value is neither "ON" nor "OFF",
+    # set MACRO_VALUE to the macro's current value
+    else()
+      set(MACRO_VALUE "${${MACRO_NAME}}")
+    endif()
+  else()
+    set(MACRO_VALUE "0")
+  endif()
+
+  # Add the macro definition to the compiler command line
+  add_definitions("-D${MACRO_NAME}=${MACRO_VALUE}")
+endfunction()
diff --git a/src/app/mainapplication.cpp b/src/app/mainapplication.cpp
index f7efc018c1c23c37c7387a2fe4ac3c7025188965..c8573991efeedba5dbc25a7ea32a9fd9a8a30f11 100644
--- a/src/app/mainapplication.cpp
+++ b/src/app/mainapplication.cpp
@@ -25,9 +25,7 @@
 #include "appsettingsmanager.h"
 #include "connectivitymonitor.h"
 #include "systemtray.h"
-#include "videoprovider.h"
 #include "previewengine.h"
-#include "conversationlistmodel.h"
 
 #include <QWKQuick/qwkquickglobal.h>
 
@@ -257,18 +255,6 @@ MainApplication::init()
     // The presence of start URI should override the startMinimized setting for this instance.
     set_startMinimized(startMinimizedSetting && runOptions_[Option::StartUri].isNull());
 
-#ifdef WITH_WEBENGINE
-    engine_.get()->rootContext()->setContextProperty("WITH_WEBENGINE", QVariant(true));
-#else
-    engine_.get()->rootContext()->setContextProperty("WITH_WEBENGINE", QVariant(false));
-#endif
-
-#ifdef APPSTORE
-    engine_.get()->rootContext()->setContextProperty("APPSTORE", QVariant(true));
-#else
-    engine_.get()->rootContext()->setContextProperty("APPSTORE", QVariant(false));
-#endif
-
     initQmlLayer();
 
     settingsManager_->setValue(Settings::Key::StartMinimized,
@@ -413,13 +399,9 @@ MainApplication::initQmlLayer()
                          &screenInfo_,
                          this);
 
-    auto videoProvider = new VideoProvider(lrcInstance_->avModel(), this);
-    engine_->rootContext()->setContextProperty("videoProvider", videoProvider);
-
-    // Find modules (runtime) under the root source dir.
-    engine_->addImportPath("qrc:/");
-
     engine_->load(QUrl(QStringLiteral("qrc:/MainApplicationWindow.qml")));
+
+    // Report the render interface used.
     qCWarning(app_) << "Main window loaded using" << getRenderInterfaceString();
 }
 
diff --git a/src/app/mainapplication.h b/src/app/mainapplication.h
index 3bbba00a8758031f10ffadb84023df31cbd79224..d7117d6870061eadba56827fbb7b73239413f0dc 100644
--- a/src/app/mainapplication.h
+++ b/src/app/mainapplication.h
@@ -57,8 +57,8 @@ private:
 class MainApplication : public QApplication
 {
     Q_OBJECT
-    Q_DISABLE_COPY(MainApplication)
     QML_RO_PROPERTY(bool, startMinimized)
+
 public:
     explicit MainApplication(int& argc, char** argv);
     ~MainApplication();
diff --git a/src/app/qmlregister.cpp b/src/app/qmlregister.cpp
index bbd55300b7c94f3be64be9a0f8a7b05d4e495b82..57649f834b9903be176a219dc8e2eba45de14985 100644
--- a/src/app/qmlregister.cpp
+++ b/src/app/qmlregister.cpp
@@ -51,7 +51,7 @@
 #include "callparticipantsmodel.h"
 #include "pluginlistmodel.h"
 #include "pluginstorelistmodel.h"
-
+#include "videoprovider.h"
 #include "qrimageprovider.h"
 #include "avatarimageprovider.h"
 #include "avatarregistry.h"
@@ -74,6 +74,7 @@
 
 #include <QMetaType>
 #include <QQmlEngine>
+#include <QQmlContext>
 
 // clang-format off
 // TODO: remove this
@@ -272,6 +273,15 @@ registerTypes(QQmlEngine* engine,
 
     engine->addImageProvider(QLatin1String("qrImage"), new QrImageProvider(lrcInstance));
     engine->addImageProvider(QLatin1String("avatarimage"), new AvatarImageProvider(lrcInstance));
+
+    // Find modules (runtime) under the root source dir.
+    engine->addImportPath("qrc:/");
+
+    auto videoProvider = new VideoProvider(lrcInstance->avModel(), app);
+    engine->rootContext()->setContextProperty("videoProvider", videoProvider);
+
+    engine->rootContext()->setContextProperty("WITH_WEBENGINE", WITH_WEBENGINE);
+    engine->rootContext()->setContextProperty("APPSTORE", APPSTORE);
 }
 // clang-format on
 } // namespace Utils
diff --git a/src/app/utils.h b/src/app/utils.h
index 09891e9030b88623cf5de50bd234b5aabc9be9fb..e1cee798f8e31e44eeed2f9d0b5d3dc1a08322d0 100644
--- a/src/app/utils.h
+++ b/src/app/utils.h
@@ -22,6 +22,8 @@
 
 #pragma once
 
+#include "api/conversationmodel.h"
+
 #include <QCryptographicHash>
 #include <QDir>
 
@@ -47,10 +49,6 @@
 #define LPCWSTR char*
 #endif
 
-#include "api/account.h"
-#include "api/contactmodel.h"
-#include "api/conversationmodel.h"
-
 class LRCInstance;
 
 namespace Utils {
diff --git a/tests/qml/main.cpp b/tests/qml/main.cpp
index d25e81cebcfca2d46b40bdbfb1359dfbb3472295..d652a63edb8a400efd96b0bd58067a72bdff161e 100644
--- a/tests/qml/main.cpp
+++ b/tests/qml/main.cpp
@@ -21,7 +21,7 @@
 #include "previewengine.h"
 #include "qmlregister.h"
 #include "systemtray.h"
-#include "videoprovider.h"
+
 #include "api/profile.h"
 #include "api/account.h"
 #include "api/conversationmodel.h"
@@ -139,14 +139,6 @@ public Q_SLOTS:
                              previewEngine_.get(),
                              &screenInfo_,
                              this);
-
-        auto videoProvider = new VideoProvider(lrcInstance_->avModel(), this);
-        engine->rootContext()->setContextProperty("videoProvider", videoProvider);
-#ifdef WITH_WEBENGINE
-        engine->rootContext()->setContextProperty("WITH_WEBENGINE", QVariant(true));
-#else
-        engine->rootContext()->setContextProperty("WITH_WEBENGINE", QVariant(false));
-#endif
     }
 
     /*