# Hyprland VRR Configuration: Enabling Variable Refresh Rate Per-Monitor and Globally

> Master Hyprland VRR configuration to enable Variable Refresh Rate per monitor or globally. Optimize your display performance with this essential guide.

- Repository: [Hypr Development/Hyprland](https://github.com/hyprwm/Hyprland)
- Tags: how-to-guide
- Published: 2026-07-27

---

**TLDR:** Hyprland enables Variable Refresh Rate through a monitor rule parser that reads `vrr` values in [`src/config/shared/monitor/Parser.cpp`](https://github.com/hyprwm/Hyprland/blob/main/src/config/shared/monitor/Parser.cpp), applies them via `CMonitorRuleManager::ensureVRR()` in [`MonitorRuleManager.cpp`](https://github.com/hyprwm/Hyprland/blob/main/MonitorRuleManager.cpp), and falls back to the `misc:vrr` integer setting when no per-monitor rule exists.

Hyprland VRR configuration controls adaptive sync behavior across displays in the Hyprland Wayland compositor. The repository implements a tiered system where per-monitor rules override a global `misc:vrr` fallback, with runtime state tracked in each `CMonitor` instance. Understanding this pipeline is essential for eliminating screen tearing without sacrificing performance.

## Parsing Hyprland VRR Configuration Rules

When a configuration line contains `vrr = <int>`, Hyprland routes the string to `CMonitorRuleParser::parseVRR` in [`src/config/shared/monitor/Parser.cpp`](https://github.com/hyprwm/Hyprland/blob/main/src/config/shared/monitor/Parser.cpp). This method validates that the input is numeric, converts it with `std::stoi`, and stores the result in `CMonitorRule::m_vrr`.

The parser treats negative values as an explicit disable, assigning `std::nullopt`, while zero or positive values are stored as an active optional integer:

```cpp
// src/config/shared/monitor/Parser.cpp
bool CMonitorRuleParser::parseVRR(const std::string& value) {
    if (!isNumber(value)) { m_error += "invalid vrr "; return false; }
    const auto VRR = std::stoi(value);
    m_rule.m_vrr = VRR < 0 ? std::nullopt : std::optional(VRR);
    return true;
}

```

*(source: [Parser.cpp L64‑L73](https://github.com/hyprwm/Hyprland/blob/main/src/config/shared/monitor/Parser.cpp#L64-L73))*

## Applying VRR Settings to Monitors

### CMonitorRuleManager::ensureVRR and Global Fallback

After the monitor configuration loads, `CMonitorRuleManager::ensureVRR()` is invoked for each output. The implementation in [`src/config/shared/monitor/MonitorRuleManager.cpp`](https://github.com/hyprwm/Hyprland/blob/main/src/config/shared/monitor/MonitorRuleManager.cpp) first queries the global fallback from `misc:vrr` using `CConfigValue<Config::INTEGER>("misc:vrr")`.

The effective VRR setting, `USEVRR`, prioritizes the monitor rule if present; otherwise it inherits the global value:

```cpp
// src/config/shared/monitor/MonitorRuleManager.cpp (excerpt)
void CMonitorRuleManager::ensureVRR(PHLMONITOR pMonitor) {
    static auto PVRR = CConfigValue<Config::INTEGER>("misc:vrr");
    const auto USEVRR = m->m_activeMonitorRule.m_vrr.has_value()
        ? m->m_activeMonitorRule.m_vrr.value() : *PVRR;
    // … logic that enables/disables VRR based on USEVRR and fullscreen state …
}

```

*(source: [MonitorRuleManager.cpp L195‑L210](https://github.com/hyprwm/Hyprland/blob/main/src/config/shared/monitor/MonitorRuleManager.cpp#L195-L210))*

Depending on `USEVRR`, the compositor either enables adaptive sync, forces it off, or decides dynamically based on fullscreen and window state.

### Runtime VRR State Tracking

Each `CMonitor` instance maintains a boolean flag reflecting whether VRR is currently active. In [`src/output/Monitor.hpp`](https://github.com/hyprwm/Hyprland/blob/main/src/output/Monitor.hpp), the member `m_vrrActive` is initialized to `false` and updated after `ensureVRR()` succeeds:

```cpp
// src/output/Monitor.hpp
bool m_vrrActive = false;   // true when adaptive‑sync (VRR) is active

```

*(source: [Monitor.hpp L107](https://github.com/hyprwm/Hyprland/blob/main/src/output/Monitor.hpp#L107))*

## Global VRR Fallback Behavior

### The misc:vrr Config Values

The global default is defined in [`src/config/values/ConfigValues.cpp`](https://github.com/hyprwm/Hyprland/blob/main/src/config/values/ConfigValues.cpp) under the key `misc:vrr`. According to the Hyprland source code, this integer controls the default adaptive sync policy when no per-monitor rule overrides it:

- **0** – VRR is never enabled.
- **1** – VRR is enabled unless a window explicitly disables it with the `no_vrr` rule.
- **2** – VRR is enabled only when a fullscreen window is present.
- **3** – VRR is enabled for fullscreen windows and when the content type is a game or video.

```cpp
// src/config/values/ConfigValues.cpp
MS<Int>("misc:vrr", "controls the VRR (Adaptive Sync) of your monitors", 0,

```

*(source: [ConfigValues.cpp L483‑L485](https://github.com/hyprwm/Hyprland/blob/main/src/config/values/ConfigValues.cpp#L483-L485))*

### Interaction with Fullscreen Windows and Window Rules

When a window specifies the `no_vrr` rule, `ensureVRR()` respects that restriction and may temporarily disable adaptive sync while that window is fullscreen. This logic is handled inside the fullscreen controller. You can force VRR off for specific applications with a window rule:

```ini
windowrule = no_vrr, class:Firefox

```

## Practical Hyprland VRR Configuration Examples

### Per-Monitor VRR Rules

To enable VRR on a single display, define the monitor rule with the `vrr` value. The following example sets a monitor and enables its adaptive sync:

```ini
monitor=HDMI-A-1,2560x1440,60,1  # last “1” enables VRR for this monitor

```

### Global VRR Settings

Use the `misc:vrr` key to set compositor-wide behavior. For instance, disabling VRR entirely or limiting it to fullscreen contexts:

```ini
misc:vrr = 0

```

```ini
misc:vrr = 2

```

The first snippet disables VRR globally. The second enables it only when a fullscreen window is active.

### Lua Configuration

For Lua-based setups, assign the rule table directly and set the global fallback:

```lua
-- Enable VRR for the primary monitor
monitorRule = {
    name = "eDP-1",
    vrr = 1,
}

-- Global fallback: VRR only when a fullscreen window is active
Config.misc.vrr = 2

```

## Summary

- **Per-monitor parsing:** `CMonitorRuleParser::parseVRR` in [`src/config/shared/monitor/Parser.cpp`](https://github.com/hyprwm/Hyprland/blob/main/src/config/shared/monitor/Parser.cpp) validates and stores the `vrr` integer as `std::optional<int>` in `m_rule.m_vrr`.
- **Rule application:** `CMonitorRuleManager::ensureVRR()` in [`src/config/shared/monitor/MonitorRuleManager.cpp`](https://github.com/hyprwm/Hyprland/blob/main/src/config/shared/monitor/MonitorRuleManager.cpp) resolves the effective VRR value by checking the monitor rule first, then the global `misc:vrr` fallback.
- **State tracking:** Each output stores its live adaptive sync status in `CMonitor::m_vrrActive`, defined in [`src/output/Monitor.hpp`](https://github.com/hyprwm/Hyprland/blob/main/src/output/Monitor.hpp).
- **Global fallback values:** `misc:vrr` accepts `0` through `3`, controlling whether VRR is off, always on, fullscreen-only, or content-type aware.
- **Window-level overrides:** The `no_vrr` window rule suppresses VRR for specific applications, even when fullscreen.

## Frequently Asked Questions

### How do I enable VRR for a specific monitor in Hyprland?

Define a per-monitor rule with the `vrr` field. As implemented in [`src/config/shared/monitor/Parser.cpp`](https://github.com/hyprwm/Hyprland/blob/main/src/config/shared/monitor/Parser.cpp), `parseVRR()` converts a positive integer into an enabled rule stored in `CMonitorRule::m_vrr`, which `ensureVRR()` then applies to that output. For example, set `monitor=HDMI-A-1,2560x1440,60,1` to target that display.

### What does the misc:vrr setting control?

`misc:vrr` acts as the global fallback when no per-monitor rule exists. Defined in [`src/config/values/ConfigValues.cpp`](https://github.com/hyprwm/Hyprland/blob/main/src/config/values/ConfigValues.cpp), it accepts values `0` through `3`: `0` disables adaptive sync entirely, `1` enables it by default, `2` restricts it to fullscreen windows, and `3` includes game or video content types.

### Can I disable VRR for individual windows?

Yes. The `no_vrr` window rule instructs the fullscreen controller to temporarily suspend adaptive sync for matching clients. `CMonitorRuleManager::ensureVRR()` checks this condition and can force VRR off while the restricted window is active.

### Where is the active VRR state stored at runtime?

Each monitor object tracks its current adaptive sync status in the `m_vrrActive` boolean, declared in [`src/output/Monitor.hpp`](https://github.com/hyprwm/Hyprland/blob/main/src/output/Monitor.hpp) at line 107. Additional layout-wide queries are available through `isVRRActiveOnAnyMonitor()` in [`src/state/MonitorLayoutController.hpp`](https://github.com/hyprwm/Hyprland/blob/main/src/state/MonitorLayoutController.hpp).