Ich glaube inzwischen eine Lösung gefunden zu haben. Sieht zumindest so aus, dass es auch ohne Kenntnis des Skalierungsfaktors funktioniert:
local function guiUpdate()
if state.openWindow then -- trigger message
local winId = "wkjsAlertbox"
if not api.gui.util.getById(winId) then -- checks if window already exists to inhibit a new window every call :-)
state.window = api.gui.comp.Window.new(_("alertboxTitle"),api.gui.comp.TextView.new(_("alertboxText")))
state.window:addHideOnCloseHandler()
state.window:setIcon("ui/icons/windows/attention.tga")
state.window:setId(winId)
local parent = state.window:getParent() -- not the screen size but the usable part of the game window
uiSize = parent:getContentRect()
local newSize = api.gui.util.Size.new(500, 150) -- regular size without UI scaling
state.window:setSize(newSize)
state.window:setVisible(false, false) -- can we really notice the window opening at the wrong place?
state.window:setPosition(0, 0) -- opens the window, which must be opened extemporary to get the (scaled) size :-(
local winSize = state.window:getContentRect() -- now we can get the scaled size
local x = math.floor((uiSize.w - winSize.w) * .5 +.5)
local y = math.floor((uiSize.h - winSize.h) * .5 +.5)
state.window:setPosition(x, y) -- and now we can set the final position :-)
state.window:setVisible(true, false)
game.gui.playSoundEffect("attention") -- for warnings
state.openWindow = false
end
end
end
Alles anzeigen
An dieser Stelle gleich die Warnung, dass das alles noch experimentell und ohne Gewähr ist - für alle, die den Code übernehmen möchten.
Erstaunlich, welcher Aufwand getrieben werden muss, um ein simples Fenster zu öffnen. Erstaunlich auch, dass man wohl erst die tatsächlichen Maße des Fensters zurückgegeben bekommt, nachdem das Fenster bereits geöffnet wird. Aber immerhin hätten wir ein Workaround - womöglich schon den Königsweg. Vielleicht doch mal UG fragen ... 
Eine weitere Überlegung wäre noch, das Fenster schon in guiInit anzulegen und später an entsprechender Stelle aufzupoppen. Dort wird es witzigerweise unabhängig von den in setPosition angegebenen Werten in den unsichtbaren negativen Koordinatenbereich geschoben, allerdings so, dass ein Teil noch in den sichtbaren GUI-Bereich hineinragt. 
Ob setVisible überhaupt notwendig ist, ist mir nicht ganz klar. Für genau einen Frame müsste das Fenster an der falschen Stelle sichtbar sein. Alternativ könnte man es auch außerhalb des Bildschirms platzieren, in der Hoffnung, dass es dort nie jemand zu sehen bekommt. Und da scheint mir setVisible die sicherere Lösung zu sein.
Ganz sicher bin ich mir noch nicht, ob bei der obigen Anordnung irgendwelche Aktionen beim Framewechsel "verschluckt" werden könnten. 