Use SetLayout
as TLama showed in his now deleted answer to switch the layout of the canvas before you draw.
function SetLayout(hdc: HDC; dwLayout: DWORD): DWORD; stdcall;
external 'gdi32' name 'SetLayout';
const
LAYOUT_RTL = $00000001;
procedure TForm1.FormPaint(Sender: TObject);
var
ExplorerTreeviewhTheme: HTHEME;
Details: TThemedElementDetails;
ARect: TRect;
Size: TSize;
begin
ExplorerTreeviewhTheme := OpenThemeData(Handle, 'Explorer::Treeview');
Details := ThemeServices.GetElementDetails(ttGlyphClosed);
GetThemePartSize(ExplorerTreeviewhTheme, Canvas.Handle, Details.Part,
Details.State, nil, TS_DRAW, Size);
ARect := Rect(20, 30, 20 + Size.cx, 30 + Size.cy);
// normal layout
DrawThemeBackground(ExplorerTreeviewhTheme, Canvas.Handle,
Details.Part, Details.State, ARect, nil);
// switched layout
SetLayout(Canvas.Handle, LAYOUT_RTL);
// calculate the rectangle for RTL as if it's in LTR
OffsetRect(ARect, 0, Size.cy); // align to the bottom of the first image so that we can see
ARect.Left := ClientWidth - ARect.Left - Size.cx;
ARect.Right := ARect.Left + Size.cx;
DrawThemeBackground(ExplorerTreeviewhTheme, Canvas.Handle,
Details.Part, Details.State, ARect, nil);
// restore layout
SetLayout(Canvas.Handle, 0);
CloseThemeData(ExplorerTreeviewhTheme);
end;
Output:
The theme api is drawing a 6px wide triangle in a 16px part size (W7-aero). Since you won't be able to know the placement of the image in the part, you won't be able to align it any better.