mirror of
https://github.com/hyprwm/aquamarine.git
synced 2024-12-22 11:39:49 +01:00
output: rework state
This commit is contained in:
parent
229fd3a036
commit
03ed93e8b5
4 changed files with 133 additions and 27 deletions
|
@ -37,17 +37,52 @@ namespace Aquamarine {
|
|||
|
||||
class COutputState {
|
||||
public:
|
||||
// TODO: make this state private, this sucks
|
||||
Hyprutils::Math::CRegion damage;
|
||||
bool enabled = false;
|
||||
bool adaptiveSync = false;
|
||||
eOutputPresentationMode presentationMode = AQ_OUTPUT_PRESENTATION_VSYNC;
|
||||
std::vector<uint16_t> gammaLut;
|
||||
Hyprutils::Math::Vector2D lastModeSize;
|
||||
Hyprutils::Memory::CWeakPointer<SOutputMode> mode;
|
||||
Hyprutils::Memory::CSharedPointer<SOutputMode> customMode;
|
||||
uint32_t drmFormat = DRM_FORMAT_INVALID;
|
||||
Hyprutils::Memory::CSharedPointer<IBuffer> buffer;
|
||||
enum eOutputStateProperties : uint32_t {
|
||||
AQ_OUTPUT_STATE_DAMAGE = (1 << 0),
|
||||
AQ_OUTPUT_STATE_ENABLED = (1 << 1),
|
||||
AQ_OUTPUT_STATE_ADAPTIVE_SYNC = (1 << 2),
|
||||
AQ_OUTPUT_STATE_PRESENTATION_MODE = (1 << 3),
|
||||
AQ_OUTPUT_STATE_GAMMA_LUT = (1 << 4),
|
||||
AQ_OUTPUT_STATE_MODE = (1 << 5),
|
||||
AQ_OUTPUT_STATE_FORMAT = (1 << 6),
|
||||
AQ_OUTPUT_STATE_BUFFER = (1 << 7),
|
||||
};
|
||||
|
||||
struct SInternalState {
|
||||
uint32_t committed = 0; // enum eOutputStateProperties
|
||||
|
||||
Hyprutils::Math::CRegion damage;
|
||||
bool enabled = false;
|
||||
bool adaptiveSync = false;
|
||||
eOutputPresentationMode presentationMode = AQ_OUTPUT_PRESENTATION_VSYNC;
|
||||
std::vector<uint16_t> gammaLut;
|
||||
Hyprutils::Math::Vector2D lastModeSize;
|
||||
Hyprutils::Memory::CWeakPointer<SOutputMode> mode;
|
||||
Hyprutils::Memory::CSharedPointer<SOutputMode> customMode;
|
||||
uint32_t drmFormat = DRM_FORMAT_INVALID;
|
||||
Hyprutils::Memory::CSharedPointer<IBuffer> buffer;
|
||||
};
|
||||
|
||||
const SInternalState& state();
|
||||
|
||||
void addDamage(const Hyprutils::Math::CRegion& region);
|
||||
void clearDamage();
|
||||
void setEnabled(bool enabled);
|
||||
void setAdaptiveSync(bool enabled);
|
||||
void setPresentationMode(eOutputPresentationMode mode);
|
||||
void setGammaLut(const std::vector<uint16_t>& lut);
|
||||
void setMode(Hyprutils::Memory::CSharedPointer<SOutputMode> mode);
|
||||
void setCustomMode(Hyprutils::Memory::CSharedPointer<SOutputMode> mode);
|
||||
void setFormat(uint32_t drmFormat);
|
||||
void setBuffer(Hyprutils::Memory::CSharedPointer<IBuffer> buffer);
|
||||
|
||||
private:
|
||||
SInternalState internalState;
|
||||
|
||||
void onCommit(); // clears a few props like damage and committed.
|
||||
|
||||
friend class IOutput;
|
||||
friend class CWaylandOutput;
|
||||
};
|
||||
|
||||
class IOutput {
|
||||
|
@ -68,7 +103,6 @@ namespace Aquamarine {
|
|||
std::string name, description, make, model, serial;
|
||||
Hyprutils::Math::Vector2D physicalSize;
|
||||
bool enabled = false;
|
||||
bool adaptiveSync = false;
|
||||
bool nonDesktop = false;
|
||||
eSubpixelMode subpixel = AQ_SUBPIXEL_NONE;
|
||||
|
||||
|
|
|
@ -231,10 +231,12 @@ Aquamarine::CWaylandPointer::CWaylandPointer(SP<CCWlPointer> pointer_, Hyprutils
|
|||
backend->backend->log(AQ_LOG_DEBUG, "New wayland pointer wl_pointer");
|
||||
|
||||
pointer->setMotion([this](CCWlPointer* r, uint32_t serial, wl_fixed_t x, wl_fixed_t y) {
|
||||
if (!backend->focusedOutput || (!backend->focusedOutput->state->mode && !backend->focusedOutput->state->customMode))
|
||||
const auto STATE = backend->focusedOutput->state->state();
|
||||
|
||||
if (!backend->focusedOutput || (!STATE.mode && !STATE.customMode))
|
||||
return;
|
||||
|
||||
const Vector2D size = backend->focusedOutput->state->customMode ? backend->focusedOutput->state->customMode->pixelSize : backend->focusedOutput->state->mode->pixelSize;
|
||||
const Vector2D size = STATE.customMode ? STATE.customMode->pixelSize : STATE.mode->pixelSize;
|
||||
|
||||
Vector2D local = {wl_fixed_to_double(x), wl_fixed_to_double(y)};
|
||||
local = local / size;
|
||||
|
@ -496,16 +498,16 @@ bool Aquamarine::CWaylandOutput::commit() {
|
|||
Vector2D pixelSize = {};
|
||||
uint32_t refreshRate = 0;
|
||||
|
||||
if (state->customMode)
|
||||
pixelSize = state->customMode->pixelSize;
|
||||
else if (state->mode)
|
||||
pixelSize = state->mode->pixelSize;
|
||||
if (state->internalState.customMode)
|
||||
pixelSize = state->internalState.customMode->pixelSize;
|
||||
else if (state->internalState.mode)
|
||||
pixelSize = state->internalState.mode->pixelSize;
|
||||
else {
|
||||
backend->backend->log(AQ_LOG_ERROR, std::format("Output {}: pending state rejected: invalid mode", name));
|
||||
return false;
|
||||
}
|
||||
|
||||
uint32_t format = state->drmFormat;
|
||||
uint32_t format = state->internalState.drmFormat;
|
||||
|
||||
if (format == DRM_FORMAT_INVALID) {
|
||||
backend->backend->log(AQ_LOG_ERROR, std::format("Output {}: pending state rejected: invalid format", name));
|
||||
|
@ -522,12 +524,19 @@ bool Aquamarine::CWaylandOutput::commit() {
|
|||
return false;
|
||||
}
|
||||
|
||||
if (!state->buffer) {
|
||||
backend->backend->log(AQ_LOG_ERROR, std::format("Output {}: pending state rejected: no buffer", name));
|
||||
return false;
|
||||
if (!state->internalState.buffer) {
|
||||
// if the consumer explicitly committed a null buffer, that's a violation.
|
||||
if (state->internalState.committed & COutputState::AQ_OUTPUT_STATE_BUFFER) {
|
||||
backend->backend->log(AQ_LOG_ERROR, std::format("Output {}: pending state rejected: no buffer", name));
|
||||
return false;
|
||||
}
|
||||
|
||||
events.commit.emit();
|
||||
state->onCommit();
|
||||
return true;
|
||||
}
|
||||
|
||||
auto wlBuffer = wlBufferFromBuffer(state->buffer);
|
||||
auto wlBuffer = wlBufferFromBuffer(state->internalState.buffer);
|
||||
|
||||
if (!wlBuffer) {
|
||||
backend->backend->log(AQ_LOG_ERROR, std::format("Output {}: pending state rejected: no wlBuffer??", name));
|
||||
|
@ -547,6 +556,8 @@ bool Aquamarine::CWaylandOutput::commit() {
|
|||
|
||||
events.commit.emit();
|
||||
|
||||
state->onCommit();
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -26,3 +26,64 @@ void Aquamarine::IOutput::scheduleFrame() {
|
|||
Hyprutils::Math::Vector2D Aquamarine::IOutput::maxCursorSize() {
|
||||
return {}; // error
|
||||
}
|
||||
|
||||
const Aquamarine::COutputState::SInternalState& Aquamarine::COutputState::state() {
|
||||
return internalState;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::addDamage(const Hyprutils::Math::CRegion& region) {
|
||||
internalState.damage.add(region);
|
||||
internalState.committed |= AQ_OUTPUT_STATE_DAMAGE;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::clearDamage() {
|
||||
internalState.damage.clear();
|
||||
internalState.committed |= AQ_OUTPUT_STATE_DAMAGE;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::setEnabled(bool enabled) {
|
||||
internalState.enabled = enabled;
|
||||
internalState.committed |= AQ_OUTPUT_STATE_ENABLED;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::setAdaptiveSync(bool enabled) {
|
||||
internalState.adaptiveSync = enabled;
|
||||
internalState.committed |= AQ_OUTPUT_STATE_ADAPTIVE_SYNC;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::setPresentationMode(eOutputPresentationMode mode) {
|
||||
internalState.presentationMode = mode;
|
||||
internalState.committed |= AQ_OUTPUT_STATE_PRESENTATION_MODE;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::setGammaLut(const std::vector<uint16_t>& lut) {
|
||||
internalState.gammaLut = lut;
|
||||
internalState.committed |= AQ_OUTPUT_STATE_GAMMA_LUT;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::setMode(Hyprutils::Memory::CSharedPointer<SOutputMode> mode) {
|
||||
internalState.mode = mode;
|
||||
internalState.customMode = nullptr;
|
||||
internalState.committed |= AQ_OUTPUT_STATE_MODE;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::setCustomMode(Hyprutils::Memory::CSharedPointer<SOutputMode> mode) {
|
||||
internalState.mode.reset();
|
||||
internalState.customMode = mode;
|
||||
internalState.committed |= AQ_OUTPUT_STATE_MODE;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::setFormat(uint32_t drmFormat) {
|
||||
internalState.drmFormat = drmFormat;
|
||||
internalState.committed |= AQ_OUTPUT_STATE_FORMAT;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::setBuffer(Hyprutils::Memory::CSharedPointer<IBuffer> buffer) {
|
||||
internalState.buffer = buffer;
|
||||
internalState.committed |= AQ_OUTPUT_STATE_BUFFER;
|
||||
}
|
||||
|
||||
void Aquamarine::COutputState::onCommit() {
|
||||
internalState.committed = 0;
|
||||
internalState.damage.clear();
|
||||
}
|
||||
|
|
|
@ -34,16 +34,16 @@ void onFrame() {
|
|||
|
||||
auto buf = output->swapchain->next(nullptr);
|
||||
|
||||
output->state->buffer = buf;
|
||||
output->state->setBuffer(buf);
|
||||
output->commit();
|
||||
}
|
||||
|
||||
void onState(const Aquamarine::IOutput::SStateEvent& event) {
|
||||
std::cout << "[Client] onState with size " << std::format("{}", event.size) << "\n";
|
||||
|
||||
output->state->enabled = true;
|
||||
output->state->customMode = makeShared<Aquamarine::SOutputMode>(Aquamarine::SOutputMode{.pixelSize = event.size});
|
||||
output->state->drmFormat = DRM_FORMAT_XRGB8888;
|
||||
output->state->setEnabled(true);
|
||||
output->state->setCustomMode(makeShared<Aquamarine::SOutputMode>(Aquamarine::SOutputMode{.pixelSize = event.size}));
|
||||
output->state->setFormat(DRM_FORMAT_XRGB8888);
|
||||
|
||||
output->commit();
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue