| /* |
| * Copyright 2024 The Android Open Source Project |
| * |
| * Licensed under the Apache License, Version 2.0 (the "License"); |
| * you may not use this file except in compliance with the License. |
| * You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| #include <apex/display.h> |
| #include <utils/Errors.h> |
| |
| namespace android::display::impl { |
| |
| /** |
| * Implementation of ADisplayConfig |
| */ |
| struct DisplayConfigImpl { |
| /** |
| * The width in pixels of the display configuration. |
| */ |
| int32_t width{1080}; |
| |
| /** |
| * The height in pixels of the display configuration. |
| */ |
| |
| int32_t height{1920}; |
| |
| /** |
| * The refresh rate of the display configuration, in frames per second. |
| */ |
| float fps{60.0}; |
| |
| /** |
| * The vsync offset at which surfaceflinger runs, in nanoseconds. |
| */ |
| int64_t sfOffset{0}; |
| |
| /** |
| * The vsync offset at which applications run, in nanoseconds. |
| */ |
| int64_t appOffset{0}; |
| }; |
| |
| // DisplayConfigImpl allocation is not managed through C++ memory apis, so |
| // preventing calling the destructor here. |
| static_assert(std::is_trivially_destructible<DisplayConfigImpl>::value); |
| |
| /** |
| * Implementation of ADisplay |
| */ |
| struct DisplayImpl { |
| /** |
| * The type of the display, i.e. whether it is an internal or external |
| * display. |
| */ |
| ADisplayType type; |
| |
| /** |
| * The preferred WCG dataspace |
| */ |
| ADataSpace wcgDataspace; |
| |
| /** |
| * The preferred WCG pixel format |
| */ |
| AHardwareBuffer_Format wcgPixelFormat; |
| |
| /** |
| * The config for this display. |
| */ |
| DisplayConfigImpl config; |
| }; |
| |
| // DisplayImpl allocation is not managed through C++ memory apis, so |
| // preventing calling the destructor here. |
| static_assert(std::is_trivially_destructible<DisplayImpl>::value); |
| |
| } // namespace android::display::impl |
| |
| using namespace android; |
| using namespace android::display::impl; |
| |
| namespace android { |
| |
| int ADisplay_acquirePhysicalDisplays(ADisplay*** outDisplays) { |
| // This is running on host, so there are no physical displays available. |
| // Create 1 fake display instead. |
| DisplayImpl** const impls = reinterpret_cast<DisplayImpl**>( |
| malloc(sizeof(DisplayImpl*) + sizeof(DisplayImpl))); |
| DisplayImpl* const displayData = reinterpret_cast<DisplayImpl*>(impls + 1); |
| |
| displayData[0] = DisplayImpl{ADisplayType::DISPLAY_TYPE_INTERNAL, |
| ADataSpace::ADATASPACE_UNKNOWN, |
| AHardwareBuffer_Format::AHARDWAREBUFFER_FORMAT_R8G8B8A8_UNORM, |
| DisplayConfigImpl()}; |
| impls[0] = displayData; |
| *outDisplays = reinterpret_cast<ADisplay**>(impls); |
| return 1; |
| } |
| |
| void ADisplay_release(ADisplay** displays) { |
| if (displays == nullptr) { |
| return; |
| } |
| free(displays); |
| } |
| |
| float ADisplay_getMaxSupportedFps(ADisplay* display) { |
| DisplayImpl* impl = reinterpret_cast<DisplayImpl*>(display); |
| return impl->config.fps; |
| } |
| |
| ADisplayType ADisplay_getDisplayType(ADisplay* display) { |
| return reinterpret_cast<DisplayImpl*>(display)->type; |
| } |
| |
| void ADisplay_getPreferredWideColorFormat(ADisplay* display, ADataSpace* outDataspace, |
| AHardwareBuffer_Format* outPixelFormat) { |
| DisplayImpl* impl = reinterpret_cast<DisplayImpl*>(display); |
| *outDataspace = impl->wcgDataspace; |
| *outPixelFormat = impl->wcgPixelFormat; |
| } |
| |
| int ADisplay_getCurrentConfig(ADisplay* display, ADisplayConfig** outConfig) { |
| DisplayImpl* impl = reinterpret_cast<DisplayImpl*>(display); |
| *outConfig = reinterpret_cast<ADisplayConfig*>(&impl->config); |
| return OK; |
| } |
| |
| int32_t ADisplayConfig_getWidth(ADisplayConfig* config) { |
| return reinterpret_cast<DisplayConfigImpl*>(config)->width; |
| } |
| |
| int32_t ADisplayConfig_getHeight(ADisplayConfig* config) { |
| return reinterpret_cast<DisplayConfigImpl*>(config)->height; |
| } |
| |
| float ADisplayConfig_getFps(ADisplayConfig* config) { |
| return reinterpret_cast<DisplayConfigImpl*>(config)->fps; |
| } |
| |
| int64_t ADisplayConfig_getCompositorOffsetNanos(ADisplayConfig* config) { |
| return reinterpret_cast<DisplayConfigImpl*>(config)->sfOffset; |
| } |
| |
| int64_t ADisplayConfig_getAppVsyncOffsetNanos(ADisplayConfig* config) { |
| return reinterpret_cast<DisplayConfigImpl*>(config)->appOffset; |
| } |
| |
| } // namespace android |