mirror of
https://github.com/CloverHackyColor/CloverBootloader.git
synced 2024-11-23 11:35:19 +01:00
Merge branch 'master' of https://github.com/CloverHackyColor/CloverBootloader
This commit is contained in:
commit
98a2ae64a4
@ -8166,7 +8166,7 @@ SetDevices (LOADER_ENTRY *Entry)
|
||||
Status = gBS->AllocatePages (
|
||||
AllocateMaxAddress,
|
||||
EfiACPIReclaimMemory,
|
||||
EFI_SIZE_TO_PAGES (device_inject_stringlength + 1),
|
||||
EFI_SIZE_TO_PAGES ((UINTN)device_inject_stringlength + 1),
|
||||
&BufferPtr
|
||||
);
|
||||
|
||||
|
@ -1,42 +1,42 @@
|
||||
#include "XImage.h"
|
||||
|
||||
|
||||
XImage::XImage()
|
||||
{
|
||||
Width = 0;
|
||||
Height = 0;
|
||||
}
|
||||
|
||||
XImage::XImage(UINTN W, UINTN H)
|
||||
{
|
||||
Width = W;
|
||||
Height = H;
|
||||
PixelData.CheckSize(GetWidth()*GetHeight());
|
||||
}
|
||||
#if 0
|
||||
UINT8 Smooth(UINT8* P, int a01, int a10, int a11, int a21, int a12, int dx, int dy, float scale)
|
||||
{
|
||||
return (UINT8)((*(p + a01) * (scale - dx) * 3 + *(p + a10) * (scale - dy) * 3 + *(p + a21) * dx * 3 +
|
||||
*(p + a12) * dy * 3 + *(p + a11) * 2 *scale) / (scale * 8));
|
||||
}
|
||||
#endif
|
||||
|
||||
XImage::XImage(const XImage& Image, float scale)
|
||||
{
|
||||
Width = (UINTN)(Image.GetWidth() * scale);
|
||||
Height = (UINTN)(Image.GetHeight() * scale);
|
||||
PixelData.CheckSize(GetWidth()*GetHeight());
|
||||
#if 0
|
||||
UINTN Offset = OFFSET_OF(EFI_GRAPHICS_OUTPUT_BLT_PIXEL, Blue);
|
||||
|
||||
dst.Blue = Smooth(&src.Blue, a01, a10, a11, a21, a12, dx, dy, scale);
|
||||
|
||||
#include "XImage.h"
|
||||
|
||||
|
||||
XImage::XImage()
|
||||
{
|
||||
Width = 0;
|
||||
Height = 0;
|
||||
}
|
||||
|
||||
XImage::XImage(UINTN W, UINTN H)
|
||||
{
|
||||
Width = W;
|
||||
Height = H;
|
||||
PixelData.CheckSize(GetWidth()*GetHeight());
|
||||
}
|
||||
#if 0
|
||||
UINT8 Smooth(UINT8* P, int a01, int a10, int a11, int a21, int a12, int dx, int dy, float scale)
|
||||
{
|
||||
return (UINT8)((*(p + a01) * (scale - dx) * 3 + *(p + a10) * (scale - dy) * 3 + *(p + a21) * dx * 3 +
|
||||
*(p + a12) * dy * 3 + *(p + a11) * 2 *scale) / (scale * 8));
|
||||
}
|
||||
#endif
|
||||
|
||||
XImage::XImage(const XImage& Image, float scale)
|
||||
{
|
||||
Width = (UINTN)(Image.GetWidth() * scale);
|
||||
Height = (UINTN)(Image.GetHeight() * scale);
|
||||
PixelData.CheckSize(GetWidth()*GetHeight());
|
||||
#if 0
|
||||
UINTN Offset = OFFSET_OF(EFI_GRAPHICS_OUTPUT_BLT_PIXEL, Blue);
|
||||
|
||||
dst.Blue = Smooth(&src.Blue, a01, a10, a11, a21, a12, dx, dy, scale);
|
||||
|
||||
#define SMOOTH(P) \
|
||||
do { \
|
||||
((PIXEL*)dst_ptr)->P = (BYTE)((a01.P * (cx - dx) * 3 + a10.P * (cy - dy) * 3 + \
|
||||
a21.P * dx * 3 + a12.P * dy * 3 + a11.P * (cx + cy)) / ((cx + cy) * 4)); \
|
||||
} while(0)
|
||||
|
||||
|
||||
UINT x, y, z;
|
||||
PIXEL a10, a11, a12, a01, a21;
|
||||
int fx, cx, lx, dx, fy, cy, ly, dy;
|
||||
@ -84,233 +84,233 @@ do { \
|
||||
dst_ptr += dst_format->bytes_per_pixel;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
XImage::~XImage()
|
||||
{
|
||||
}
|
||||
|
||||
const XArray<EFI_GRAPHICS_OUTPUT_BLT_PIXEL>& XImage::GetData() const
|
||||
{
|
||||
return PixelData;
|
||||
}
|
||||
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL* XImage::GetPixelPtr(UINTN x, UINTN y)
|
||||
{
|
||||
return &PixelData[x + y * Width];
|
||||
}
|
||||
|
||||
const EFI_GRAPHICS_OUTPUT_BLT_PIXEL& XImage::GetPixel(UINTN x, UINTN y) const
|
||||
{
|
||||
return PixelData[x + y * Width];
|
||||
}
|
||||
|
||||
|
||||
UINTN XImage::GetWidth() const
|
||||
{
|
||||
return Width;
|
||||
}
|
||||
|
||||
UINTN XImage::GetHeight() const
|
||||
{
|
||||
return Height;
|
||||
}
|
||||
|
||||
UINTN XImage::GetSize() const
|
||||
{
|
||||
return Width * Height * sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL);
|
||||
}
|
||||
|
||||
void XImage::Fill(const EFI_GRAPHICS_OUTPUT_BLT_PIXEL& Color)
|
||||
{
|
||||
for (UINTN y = 0; y < Height; ++y)
|
||||
for (UINTN x = 0; x < Width; ++x)
|
||||
PixelData[y * Width + x] = Color;
|
||||
}
|
||||
|
||||
void XImage::FillArea(const EFI_GRAPHICS_OUTPUT_BLT_PIXEL& Color, const EgRect& Rect)
|
||||
{
|
||||
for (UINTN y = Rect.Ypos; y < Height && (y - Rect.Ypos) < Rect.Height; ++y) {
|
||||
// EFI_GRAPHICS_OUTPUT_BLT_PIXEL* Ptr = PixelData + y * Width + Rect.Xpos;
|
||||
for (UINTN x = Rect.Xpos; x < Width && (x - Rect.Xpos) < Rect.Width; ++x)
|
||||
// *Ptr++ = Color;
|
||||
PixelData[y * Width + x] = Color;
|
||||
}
|
||||
}
|
||||
|
||||
void XImage::Compose(int PosX, int PosY, const XImage& TopImage, bool Lowest) //lowest image is opaque
|
||||
{
|
||||
UINT32 TopAlpha;
|
||||
UINT32 RevAlpha;
|
||||
UINT32 FinalAlpha;
|
||||
UINT32 Temp;
|
||||
|
||||
for (UINTN y = PosY; y < Height && (y - PosY) < TopImage.GetHeight(); ++y) {
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL& CompPtr = *GetPixelPtr(PosX, y); // I assign a ref to avoid the operator ->. Compiler will produce the same anyway.
|
||||
for (UINTN x = PosX; x < Width && (x - PosX) < TopImage.GetWidth(); ++x) {
|
||||
TopAlpha = TopImage.GetPixel(x-PosX, y-PosY).Reserved;
|
||||
RevAlpha = 255 - TopAlpha;
|
||||
FinalAlpha = (255*255 - RevAlpha*(255 - CompPtr.Reserved)) / 255;
|
||||
|
||||
//final alpha =(1-(1-x)*(1-y)) =(255*255-(255-topA)*(255-compA))/255
|
||||
Temp = (CompPtr.Blue * RevAlpha) + (TopImage.GetPixel(x-PosX, y-PosY).Blue * TopAlpha);
|
||||
CompPtr.Blue = (UINT8)(Temp / 255);
|
||||
|
||||
Temp = (CompPtr.Green * RevAlpha) + (TopImage.GetPixel(x-PosX, y-PosY).Green * TopAlpha);
|
||||
CompPtr.Green = (UINT8)(Temp / 255);
|
||||
|
||||
Temp = (CompPtr.Red * RevAlpha) + (TopImage.GetPixel(x-PosX, y-PosY).Red * TopAlpha);
|
||||
CompPtr.Red = (UINT8)(Temp / 255);
|
||||
|
||||
if (Lowest) {
|
||||
CompPtr.Reserved = 255;
|
||||
} else {
|
||||
CompPtr.Reserved = (UINT8)FinalAlpha;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void XImage::FlipRB(bool WantAlpha)
|
||||
{
|
||||
UINTN ImageSize = (Width * Height);
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL* Pixel = GetPixelPtr(0,0);
|
||||
for (UINTN i = 0; i < ImageSize; ++i) {
|
||||
UINT8 Temp = Pixel->Blue;
|
||||
Pixel->Blue = Pixel->Red;
|
||||
Pixel->Red = Temp;
|
||||
if (!WantAlpha) Pixel->Reserved = 0xFF;
|
||||
Pixel++;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* The function converted plain array into XImage object
|
||||
*/
|
||||
unsigned XImage::FromPNG(const uint8_t * Data, UINTN Length)
|
||||
{
|
||||
uint8_t * PixelPtr = (uint8_t *)&PixelData[0];
|
||||
unsigned Error = eglodepng_decode(&PixelPtr, &Width, &Height, Data, Length);
|
||||
|
||||
FlipRB(true);
|
||||
return Error;
|
||||
}
|
||||
|
||||
/*
|
||||
* The function creates new array Data and inform about it size to be saved
|
||||
* as a file.
|
||||
* The caller is responsible to free the array.
|
||||
*/
|
||||
|
||||
unsigned XImage::ToPNG(uint8_t** Data, UINTN& OutSize)
|
||||
{
|
||||
size_t FileDataLength = 0;
|
||||
FlipRB(false);
|
||||
uint8_t * PixelPtr = (uint8_t *)&PixelData[0];
|
||||
unsigned Error = eglodepng_encode(Data, &FileDataLength, PixelPtr, Width, Height);
|
||||
OutSize = FileDataLength;
|
||||
return Error;
|
||||
}
|
||||
|
||||
// Screen operations
|
||||
/*
|
||||
* The function to get image from screen. Used in screenshot (full screen), Pointer (small area) and Draw (small area)
|
||||
* XImage must be created with UGAWidth, UGAHeight as egGetScreenSize(&UGAWidth, &UGAHeight); with PixelData allocated
|
||||
* egScreenWidth = GraphicsOutput->Mode->Info->HorizontalResolution;
|
||||
* egScreenHeight = GraphicsOutput->Mode->Info->VerticalResolution;
|
||||
*
|
||||
* be careful about alpha. This procedure can produce alpha = 0 which means full transparent
|
||||
*/
|
||||
void XImage::GetArea(const EgRect& Rect)
|
||||
{
|
||||
GetArea(Rect.Xpos, Rect.Ypos, Rect.Width, Rect.Height);
|
||||
}
|
||||
|
||||
void XImage::GetArea(UINTN x, UINTN y, UINTN W, UINTN H)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_GUID UgaDrawProtocolGuid = EFI_UGA_DRAW_PROTOCOL_GUID;
|
||||
EFI_UGA_DRAW_PROTOCOL *UgaDraw = NULL;
|
||||
EFI_GUID GraphicsOutputProtocolGuid = EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID;
|
||||
EFI_GRAPHICS_OUTPUT_PROTOCOL *GraphicsOutput = NULL;
|
||||
|
||||
Status = EfiLibLocateProtocol(&GraphicsOutputProtocolGuid, (VOID **)&GraphicsOutput);
|
||||
if (EFI_ERROR(Status)) {
|
||||
GraphicsOutput = NULL;
|
||||
Status = EfiLibLocateProtocol(&UgaDrawProtocolGuid, (VOID **)&UgaDraw);
|
||||
if (EFI_ERROR(Status))
|
||||
UgaDraw = NULL;
|
||||
}
|
||||
|
||||
INTN AreaWidth = (x + W > Width) ? (Width - x) : W;
|
||||
INTN AreaHeight = (y + H > Height) ? (Height - y) : H;
|
||||
|
||||
if (GraphicsOutput != NULL) {
|
||||
INTN LineBytes = GraphicsOutput->Mode->Info->HorizontalResolution * sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL);
|
||||
GraphicsOutput->Blt(GraphicsOutput,
|
||||
(EFI_GRAPHICS_OUTPUT_BLT_PIXEL *)&PixelData[0],
|
||||
EfiBltVideoToBltBuffer,
|
||||
x, y, 0, 0, AreaWidth, AreaHeight, LineBytes);
|
||||
}
|
||||
else if (UgaDraw != NULL) {
|
||||
UINT32 LineWidth = 0;
|
||||
UINT32 ScreenHeight = 0;
|
||||
UINT32 Depth = 0;
|
||||
UINT32 RefreshRate = 60;
|
||||
EFI_STATUS Status = UgaDraw->GetMode(UgaDraw, &LineWidth, &ScreenHeight, &Depth, &RefreshRate);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return; // graphics not available
|
||||
}
|
||||
UgaDraw->Blt(UgaDraw,
|
||||
(EFI_UGA_PIXEL *)&PixelData[0],
|
||||
EfiUgaVideoToBltBuffer,
|
||||
x, y, 0, 0, AreaWidth, AreaHeight, LineWidth * sizeof(EFI_UGA_PIXEL));
|
||||
}
|
||||
|
||||
Width = AreaWidth;
|
||||
Height = AreaHeight;
|
||||
}
|
||||
|
||||
void XImage::Draw(int x, int y, float scale)
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
XImage::~XImage()
|
||||
{
|
||||
}
|
||||
|
||||
const XArray<EFI_GRAPHICS_OUTPUT_BLT_PIXEL>& XImage::GetData() const
|
||||
{
|
||||
return PixelData;
|
||||
}
|
||||
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL* XImage::GetPixelPtr(UINTN x, UINTN y)
|
||||
{
|
||||
return &PixelData[x + y * Width];
|
||||
}
|
||||
|
||||
const EFI_GRAPHICS_OUTPUT_BLT_PIXEL& XImage::GetPixel(UINTN x, UINTN y) const
|
||||
{
|
||||
return PixelData[x + y * Width];
|
||||
}
|
||||
|
||||
|
||||
UINTN XImage::GetWidth() const
|
||||
{
|
||||
return Width;
|
||||
}
|
||||
|
||||
UINTN XImage::GetHeight() const
|
||||
{
|
||||
return Height;
|
||||
}
|
||||
|
||||
UINTN XImage::GetSize() const
|
||||
{
|
||||
return Width * Height * sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL);
|
||||
}
|
||||
|
||||
void XImage::Fill(const EFI_GRAPHICS_OUTPUT_BLT_PIXEL& Color)
|
||||
{
|
||||
for (UINTN y = 0; y < Height; ++y)
|
||||
for (UINTN x = 0; x < Width; ++x)
|
||||
PixelData[y * Width + x] = Color;
|
||||
}
|
||||
|
||||
void XImage::FillArea(const EFI_GRAPHICS_OUTPUT_BLT_PIXEL& Color, const EgRect& Rect)
|
||||
{
|
||||
for (UINTN y = Rect.Ypos; y < Height && (y - Rect.Ypos) < Rect.Height; ++y) {
|
||||
// EFI_GRAPHICS_OUTPUT_BLT_PIXEL* Ptr = PixelData + y * Width + Rect.Xpos;
|
||||
for (UINTN x = Rect.Xpos; x < Width && (x - Rect.Xpos) < Rect.Width; ++x)
|
||||
// *Ptr++ = Color;
|
||||
PixelData[y * Width + x] = Color;
|
||||
}
|
||||
}
|
||||
|
||||
void XImage::Compose(int PosX, int PosY, const XImage& TopImage, bool Lowest) //lowest image is opaque
|
||||
{
|
||||
UINT32 TopAlpha;
|
||||
UINT32 RevAlpha;
|
||||
UINT32 FinalAlpha;
|
||||
UINT32 Temp;
|
||||
|
||||
for (UINTN y = PosY; y < Height && (y - PosY) < TopImage.GetHeight(); ++y) {
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL& CompPtr = *GetPixelPtr(PosX, y); // I assign a ref to avoid the operator ->. Compiler will produce the same anyway.
|
||||
for (UINTN x = PosX; x < Width && (x - PosX) < TopImage.GetWidth(); ++x) {
|
||||
TopAlpha = TopImage.GetPixel(x-PosX, y-PosY).Reserved;
|
||||
RevAlpha = 255 - TopAlpha;
|
||||
FinalAlpha = (255*255 - RevAlpha*(255 - CompPtr.Reserved)) / 255;
|
||||
|
||||
//final alpha =(1-(1-x)*(1-y)) =(255*255-(255-topA)*(255-compA))/255
|
||||
Temp = (CompPtr.Blue * RevAlpha) + (TopImage.GetPixel(x-PosX, y-PosY).Blue * TopAlpha);
|
||||
CompPtr.Blue = (UINT8)(Temp / 255);
|
||||
|
||||
Temp = (CompPtr.Green * RevAlpha) + (TopImage.GetPixel(x-PosX, y-PosY).Green * TopAlpha);
|
||||
CompPtr.Green = (UINT8)(Temp / 255);
|
||||
|
||||
Temp = (CompPtr.Red * RevAlpha) + (TopImage.GetPixel(x-PosX, y-PosY).Red * TopAlpha);
|
||||
CompPtr.Red = (UINT8)(Temp / 255);
|
||||
|
||||
if (Lowest) {
|
||||
CompPtr.Reserved = 255;
|
||||
} else {
|
||||
CompPtr.Reserved = (UINT8)FinalAlpha;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void XImage::FlipRB(bool WantAlpha)
|
||||
{
|
||||
UINTN ImageSize = (Width * Height);
|
||||
EFI_GRAPHICS_OUTPUT_BLT_PIXEL* Pixel = GetPixelPtr(0,0);
|
||||
for (UINTN i = 0; i < ImageSize; ++i) {
|
||||
UINT8 Temp = Pixel->Blue;
|
||||
Pixel->Blue = Pixel->Red;
|
||||
Pixel->Red = Temp;
|
||||
if (!WantAlpha) Pixel->Reserved = 0xFF;
|
||||
Pixel++;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* The function converted plain array into XImage object
|
||||
*/
|
||||
unsigned XImage::FromPNG(const uint8_t * Data, UINTN Length)
|
||||
{
|
||||
uint8_t * PixelPtr = (uint8_t *)&PixelData[0];
|
||||
unsigned Error = eglodepng_decode(&PixelPtr, &Width, &Height, Data, Length);
|
||||
|
||||
FlipRB(true);
|
||||
return Error;
|
||||
}
|
||||
|
||||
/*
|
||||
* The function creates new array Data and inform about it size to be saved
|
||||
* as a file.
|
||||
* The caller is responsible to free the array.
|
||||
*/
|
||||
|
||||
unsigned XImage::ToPNG(uint8_t** Data, UINTN& OutSize)
|
||||
{
|
||||
size_t FileDataLength = 0;
|
||||
FlipRB(false);
|
||||
uint8_t * PixelPtr = (uint8_t *)&PixelData[0];
|
||||
unsigned Error = eglodepng_encode(Data, &FileDataLength, PixelPtr, Width, Height);
|
||||
OutSize = FileDataLength;
|
||||
return Error;
|
||||
}
|
||||
|
||||
// Screen operations
|
||||
/*
|
||||
* The function to get image from screen. Used in screenshot (full screen), Pointer (small area) and Draw (small area)
|
||||
* XImage must be created with UGAWidth, UGAHeight as egGetScreenSize(&UGAWidth, &UGAHeight); with PixelData allocated
|
||||
* egScreenWidth = GraphicsOutput->Mode->Info->HorizontalResolution;
|
||||
* egScreenHeight = GraphicsOutput->Mode->Info->VerticalResolution;
|
||||
*
|
||||
* be careful about alpha. This procedure can produce alpha = 0 which means full transparent
|
||||
*/
|
||||
void XImage::GetArea(const EgRect& Rect)
|
||||
{
|
||||
GetArea(Rect.Xpos, Rect.Ypos, Rect.Width, Rect.Height);
|
||||
}
|
||||
|
||||
void XImage::GetArea(UINTN x, UINTN y, UINTN W, UINTN H)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_GUID UgaDrawProtocolGuid = EFI_UGA_DRAW_PROTOCOL_GUID;
|
||||
EFI_UGA_DRAW_PROTOCOL *UgaDraw = NULL;
|
||||
EFI_GUID GraphicsOutputProtocolGuid = EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID;
|
||||
EFI_GRAPHICS_OUTPUT_PROTOCOL *GraphicsOutput = NULL;
|
||||
|
||||
Status = EfiLibLocateProtocol(&GraphicsOutputProtocolGuid, (VOID **)&GraphicsOutput);
|
||||
if (EFI_ERROR(Status)) {
|
||||
GraphicsOutput = NULL;
|
||||
Status = EfiLibLocateProtocol(&UgaDrawProtocolGuid, (VOID **)&UgaDraw);
|
||||
if (EFI_ERROR(Status))
|
||||
UgaDraw = NULL;
|
||||
}
|
||||
|
||||
INTN AreaWidth = (x + W > Width) ? (Width - x) : W;
|
||||
INTN AreaHeight = (y + H > Height) ? (Height - y) : H;
|
||||
|
||||
if (GraphicsOutput != NULL) {
|
||||
INTN LineBytes = GraphicsOutput->Mode->Info->HorizontalResolution * sizeof(EFI_GRAPHICS_OUTPUT_BLT_PIXEL);
|
||||
GraphicsOutput->Blt(GraphicsOutput,
|
||||
(EFI_GRAPHICS_OUTPUT_BLT_PIXEL *)&PixelData[0],
|
||||
EfiBltVideoToBltBuffer,
|
||||
x, y, 0, 0, AreaWidth, AreaHeight, LineBytes);
|
||||
}
|
||||
else if (UgaDraw != NULL) {
|
||||
UINT32 LineWidth = 0;
|
||||
UINT32 ScreenHeight = 0;
|
||||
UINT32 Depth = 0;
|
||||
UINT32 RefreshRate = 60;
|
||||
EFI_STATUS Status = UgaDraw->GetMode(UgaDraw, &LineWidth, &ScreenHeight, &Depth, &RefreshRate);
|
||||
if (EFI_ERROR(Status)) {
|
||||
return; // graphics not available
|
||||
}
|
||||
UgaDraw->Blt(UgaDraw,
|
||||
(EFI_UGA_PIXEL *)&PixelData[0],
|
||||
EfiUgaVideoToBltBuffer,
|
||||
x, y, 0, 0, AreaWidth, AreaHeight, LineWidth * sizeof(EFI_UGA_PIXEL));
|
||||
}
|
||||
|
||||
Width = AreaWidth;
|
||||
Height = AreaHeight;
|
||||
}
|
||||
|
||||
void XImage::Draw(int x, int y, float scale)
|
||||
{
|
||||
//prepare images
|
||||
INTN UGAWidth = 0;
|
||||
INTN UGAHeight = 0;
|
||||
egGetScreenSize(&UGAWidth, &UGAHeight);
|
||||
XImage Background(UGAWidth, UGAHeight);
|
||||
Background.GetArea(x, y, Width, Height);
|
||||
XImage Top(*this, scale);
|
||||
Background.Compose(x, y, Top, true);
|
||||
UINTN AreaWidth = (x + Width > Background.GetWidth()) ? (Background.GetWidth() - x) : Width;
|
||||
UINTN AreaHeight = (y + Height > Background.GetHeight()) ? (Background.GetHeight() - y) : Height;
|
||||
|
||||
// prepare protocols
|
||||
EFI_STATUS Status;
|
||||
EFI_GUID UgaDrawProtocolGuid = EFI_UGA_DRAW_PROTOCOL_GUID;
|
||||
EFI_UGA_DRAW_PROTOCOL *UgaDraw = NULL;
|
||||
EFI_GUID GraphicsOutputProtocolGuid = EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID;
|
||||
EFI_GRAPHICS_OUTPUT_PROTOCOL *GraphicsOutput = NULL;
|
||||
|
||||
Status = EfiLibLocateProtocol(&GraphicsOutputProtocolGuid, (VOID **)&GraphicsOutput);
|
||||
if (EFI_ERROR(Status)) {
|
||||
GraphicsOutput = NULL;
|
||||
Status = EfiLibLocateProtocol(&UgaDrawProtocolGuid, (VOID **)&UgaDraw);
|
||||
if (EFI_ERROR(Status))
|
||||
UgaDraw = NULL;
|
||||
}
|
||||
//output combined image
|
||||
if (GraphicsOutput != NULL) {
|
||||
GraphicsOutput->Blt(GraphicsOutput, (EFI_GRAPHICS_OUTPUT_BLT_PIXEL *)Background.GetPixelPtr(0, 0),
|
||||
EfiBltBufferToVideo,
|
||||
0, 0, x, y,
|
||||
AreaWidth, AreaHeight, Background.GetWidth() * 4);
|
||||
}
|
||||
else if (UgaDraw != NULL) {
|
||||
UgaDraw->Blt(UgaDraw, (EFI_UGA_PIXEL *)Background.GetPixelPtr(0, 0), EfiUgaBltBufferToVideo,
|
||||
0, 0, x, y,
|
||||
AreaWidth, AreaHeight, Background.GetWidth() * 4);
|
||||
}
|
||||
}
|
||||
XImage Background(UGAWidth, UGAHeight);
|
||||
Background.GetArea(x, y, Width, Height);
|
||||
XImage Top(*this, scale);
|
||||
Background.Compose(x, y, Top, true);
|
||||
UINTN AreaWidth = (x + Width > Background.GetWidth()) ? (Background.GetWidth() - x) : Width;
|
||||
UINTN AreaHeight = (y + Height > Background.GetHeight()) ? (Background.GetHeight() - y) : Height;
|
||||
|
||||
// prepare protocols
|
||||
EFI_STATUS Status;
|
||||
EFI_GUID UgaDrawProtocolGuid = EFI_UGA_DRAW_PROTOCOL_GUID;
|
||||
EFI_UGA_DRAW_PROTOCOL *UgaDraw = NULL;
|
||||
EFI_GUID GraphicsOutputProtocolGuid = EFI_GRAPHICS_OUTPUT_PROTOCOL_GUID;
|
||||
EFI_GRAPHICS_OUTPUT_PROTOCOL *GraphicsOutput = NULL;
|
||||
|
||||
Status = EfiLibLocateProtocol(&GraphicsOutputProtocolGuid, (VOID **)&GraphicsOutput);
|
||||
if (EFI_ERROR(Status)) {
|
||||
GraphicsOutput = NULL;
|
||||
Status = EfiLibLocateProtocol(&UgaDrawProtocolGuid, (VOID **)&UgaDraw);
|
||||
if (EFI_ERROR(Status))
|
||||
UgaDraw = NULL;
|
||||
}
|
||||
//output combined image
|
||||
if (GraphicsOutput != NULL) {
|
||||
GraphicsOutput->Blt(GraphicsOutput, (EFI_GRAPHICS_OUTPUT_BLT_PIXEL *)Background.GetPixelPtr(0, 0),
|
||||
EfiBltBufferToVideo,
|
||||
0, 0, x, y,
|
||||
AreaWidth, AreaHeight, Background.GetWidth() * 4);
|
||||
}
|
||||
else if (UgaDraw != NULL) {
|
||||
UgaDraw->Blt(UgaDraw, (EFI_UGA_PIXEL *)Background.GetPixelPtr(0, 0), EfiUgaBltBufferToVideo,
|
||||
0, 0, x, y,
|
||||
AreaWidth, AreaHeight, Background.GetWidth() * 4);
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user