[Xcb] RANDR + xcb_screen_t root, the fields (width_in_pixels/height_in_pixels) are not changed
Andrey Af
public.irkutsk at gmail.com
Sat Sep 4 06:22:04 UTC 2021
Hi,
After changing the screen size via utility xrandr -s 1 or the RANDR
API, why does the size information in screen root
width_in_pixels/height_in_pixels not change?
But if I make a new connection, then the information is correct.
How do I update the information in the current connection correctly?
test attachment:
//
// build: g++ -Wall -std=c++17 -I /usr/include/xcb -lxcb -lxcb-randr
test.cpp -o test
//
#include <xcb/xcb.h>
#include <xcb/randr.h>
#include <xcb/xproto.h>
#include <chrono>
#include <thread>
#include <iostream>
using namespace std::chrono_literals;
const xcb_query_extension_reply_t*
checkRandrExtension(xcb_connection_t* _conn)
{
auto _randr = xcb_get_extension_data(_conn, &xcb_randr_id);
if(! _randr || ! _randr->present)
return nullptr;
auto cookie = xcb_randr_query_version(_conn,
XCB_RANDR_MAJOR_VERSION,
XCB_RANDR_MINOR_VERSION);
if(auto reply = xcb_randr_query_version_reply(_conn, cookie, nullptr))
{
std::cout << "RANDR extension version: " <<
reply->major_version << "." << reply->minor_version <<
", query version: " << XCB_RANDR_MAJOR_VERSION << "." <<
XCB_RANDR_MINOR_VERSION << std::endl;
std::free(reply);
return _randr;
}
return nullptr;
}
int main(int argc, char** argv)
{
auto _conn = xcb_connect(":0", nullptr);
if(xcb_connection_has_error(_conn))
return EXIT_FAILURE;
if(auto _randr = checkRandrExtension(_conn))
{
auto setup = xcb_get_setup(_conn);
auto _screen = xcb_setup_roots_iterator(setup).data;
std::cout << "screen size: " << _screen->width_in_pixels <<
"x" << _screen->height_in_pixels << std::endl;
xcb_randr_select_input(_conn, _screen->root,
XCB_RANDR_NOTIFY_MASK_CRTC_CHANGE |
XCB_RANDR_NOTIFY_MASK_SCREEN_CHANGE |
XCB_RANDR_NOTIFY_MASK_OUTPUT_CHANGE);
xcb_flush(_conn);
while(true)
{
if(auto ev = xcb_poll_for_event(_conn))
{
int type = ev->response_type & ~0x80;
if(type == _randr->first_event + XCB_RANDR_NOTIFY)
{
auto rn = reinterpret_cast<xcb_randr_notify_event_t*>(ev);
if(rn->subCode == XCB_RANDR_NOTIFY_CRTC_CHANGE)
{
xcb_randr_crtc_change_t cc = rn->u.cc;
// window, crtc, mode, rotation, x, y, width, height
if(0 < cc.width && 0 < cc.height)
{
std::cout << "randr crtc change: " <<
cc.width << "x" << cc.height << ", screen
size: " <<
_screen->width_in_pixels << "x" <<
_screen->height_in_pixels << std::endl;
}
}
}
std::free(ev);
}
std::this_thread::sleep_for(1ms);
}
}
xcb_disconnect(_conn);
return 0;
}
More information about the Xcb
mailing list