mirror of
https://github.com/lightpanda-io/browser.git
synced 2025-12-14 23:38:57 +00:00
Screen and ScreenOrientation (legacy)
This commit is contained in:
@@ -119,7 +119,7 @@ pub fn dispatch(self: *EventManager, target: *EventTarget, event: *Event) !void
|
||||
|
||||
switch (target._type) {
|
||||
.node => |node| try self.dispatchNode(node, event, &was_handled),
|
||||
.xhr, .window, .abort_signal, .media_query_list, .message_port, .text_track_cue, .navigation => {
|
||||
.xhr, .window, .abort_signal, .media_query_list, .message_port, .text_track_cue, .navigation, .screen, .screen_orientation => {
|
||||
const list = self.lookup.getPtr(@intFromPtr(target)) orelse return;
|
||||
try self.dispatchAll(list, target, event, &was_handled);
|
||||
},
|
||||
|
||||
@@ -52,6 +52,7 @@ const Document = @import("webapi/Document.zig");
|
||||
const DocumentFragment = @import("webapi/DocumentFragment.zig");
|
||||
const ShadowRoot = @import("webapi/ShadowRoot.zig");
|
||||
const Performance = @import("webapi/Performance.zig");
|
||||
const Screen = @import("webapi/Screen.zig");
|
||||
const HtmlScript = @import("webapi/Element.zig").Html.Script;
|
||||
const MutationObserver = @import("webapi/MutationObserver.zig");
|
||||
const IntersectionObserver = @import("webapi/IntersectionObserver.zig");
|
||||
@@ -209,12 +210,14 @@ fn reset(self: *Page, comptime initializing: bool) !void {
|
||||
|
||||
if (comptime initializing == true) {
|
||||
const storage_bucket = try self._factory.create(storage.Bucket{});
|
||||
const screen = try Screen.init(self);
|
||||
self.window = try self._factory.eventTarget(Window{
|
||||
._document = self.document,
|
||||
._storage_bucket = storage_bucket,
|
||||
._performance = Performance.init(),
|
||||
._proto = undefined,
|
||||
._location = &default_location,
|
||||
._screen = screen,
|
||||
});
|
||||
} else {
|
||||
self.window._document = self.document;
|
||||
|
||||
@@ -17,5 +17,5 @@
|
||||
<script id=orientation>
|
||||
screen.orientation.addEventListener('change', () => {})
|
||||
// above shouldn't crash (it used to)
|
||||
testing.skip();
|
||||
testing.expectEqual(true, true);
|
||||
</script>
|
||||
|
||||
@@ -1,168 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<script src="../../testing.js"></script>
|
||||
<body>
|
||||
<template id="basic">
|
||||
<div class="container">
|
||||
<h1>Hello Template</h1>
|
||||
<p>This is template content</p>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<template id="nested">
|
||||
<div class="outer">
|
||||
<span id="inner1">First</span>
|
||||
<span id="inner2">Second</span>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<template id="empty"></template>
|
||||
|
||||
<script id=content_property>
|
||||
{
|
||||
const template = $('#basic');
|
||||
const content = template.content;
|
||||
|
||||
testing.expectEqual('[object DocumentFragment]', content.toString());
|
||||
testing.expectEqual(true, content instanceof DocumentFragment);
|
||||
}
|
||||
</script>
|
||||
|
||||
<script id=content_has_children>
|
||||
{
|
||||
const template = $('#basic');
|
||||
const content = template.content;
|
||||
|
||||
const div = content.firstElementChild;
|
||||
testing.expectTrue(div !== null);
|
||||
testing.expectEqual('DIV', div.tagName);
|
||||
testing.expectEqual('container', div.className);
|
||||
|
||||
const h1 = div.querySelector('h1');
|
||||
testing.expectTrue(h1 !== null);
|
||||
testing.expectEqual('Hello Template', h1.textContent);
|
||||
|
||||
const p = div.querySelector('p');
|
||||
testing.expectTrue(p !== null);
|
||||
testing.expectEqual('This is template content', p.textContent);
|
||||
}
|
||||
</script>
|
||||
|
||||
<script id=template_children_not_in_dom>
|
||||
{
|
||||
const template = $('#basic');
|
||||
|
||||
testing.expectEqual(0, template.children.length);
|
||||
testing.expectEqual(null, template.firstElementChild);
|
||||
|
||||
const h1InDoc = document.querySelector('#basic h1');
|
||||
testing.expectEqual(null, h1InDoc);
|
||||
}
|
||||
</script>
|
||||
|
||||
<script id=nested_template_content>
|
||||
{
|
||||
const template = $('#nested');
|
||||
const content = template.content;
|
||||
|
||||
const outer = content.firstElementChild;
|
||||
testing.expectEqual('DIV', outer.tagName);
|
||||
testing.expectEqual('outer', outer.className);
|
||||
|
||||
const inner1 = content.querySelector('#inner1');
|
||||
testing.expectTrue(inner1 !== null);
|
||||
testing.expectEqual('First', inner1.textContent);
|
||||
|
||||
const inner2 = content.querySelector('#inner2');
|
||||
testing.expectTrue(inner2 !== null);
|
||||
testing.expectEqual('Second', inner2.textContent);
|
||||
}
|
||||
</script>
|
||||
|
||||
<script id=empty_template>
|
||||
{
|
||||
const template = $('#empty');
|
||||
const content = template.content;
|
||||
|
||||
testing.expectEqual('[object DocumentFragment]', content.toString());
|
||||
testing.expectEqual(null, content.firstElementChild);
|
||||
testing.expectEqual(0, content.childElementCount);
|
||||
}
|
||||
</script>
|
||||
|
||||
<script id=query_selector_on_content>
|
||||
{
|
||||
const template = $('#nested');
|
||||
const content = template.content;
|
||||
|
||||
const spans = content.querySelectorAll('span');
|
||||
testing.expectEqual(2, spans.length);
|
||||
testing.expectEqual('inner1', spans[0].id);
|
||||
testing.expectEqual('inner2', spans[1].id);
|
||||
}
|
||||
</script>
|
||||
|
||||
<script id=modify_content>
|
||||
{
|
||||
const template = $('#basic');
|
||||
const content = template.content;
|
||||
|
||||
testing.expectEqual(1, content.childElementCount);
|
||||
|
||||
const newDiv = document.createElement('div');
|
||||
newDiv.id = 'added';
|
||||
newDiv.textContent = 'Added element';
|
||||
content.append(newDiv);
|
||||
|
||||
testing.expectEqual(2, content.childElementCount);
|
||||
}
|
||||
</script>
|
||||
|
||||
<script id=clone_template_content>
|
||||
{
|
||||
const template = $('#basic');
|
||||
const content = template.content;
|
||||
|
||||
const clone = content.cloneNode(true);
|
||||
testing.expectEqual('[object DocumentFragment]', clone.toString());
|
||||
|
||||
const div = clone.firstElementChild;
|
||||
testing.expectTrue(div !== null);
|
||||
testing.expectEqual('container', div.className);
|
||||
|
||||
const h1 = clone.querySelector('h1');
|
||||
testing.expectEqual('Hello Template', h1.textContent);
|
||||
}
|
||||
</script>
|
||||
|
||||
<script id=instantiate_template>
|
||||
{
|
||||
const template = $('#nested');
|
||||
const content = template.content;
|
||||
|
||||
const originalOuter = content.firstElementChild;
|
||||
testing.expectEqual(2, originalOuter.childElementCount);
|
||||
|
||||
const clone = content.cloneNode(true);
|
||||
|
||||
testing.expectEqual(1, clone.childElementCount);
|
||||
const clonedDiv = clone.firstElementChild;
|
||||
testing.expectEqual('DIV', clonedDiv.tagName);
|
||||
testing.expectEqual('outer', clonedDiv.className);
|
||||
testing.expectEqual(2, clonedDiv.childElementCount);
|
||||
|
||||
document.body.appendChild(clone);
|
||||
|
||||
testing.expectEqual(0, clone.childElementCount);
|
||||
|
||||
const outerInDoc = document.body.querySelector('.outer');
|
||||
testing.expectTrue(outerInDoc !== null);
|
||||
testing.expectEqual(clonedDiv, outerInDoc);
|
||||
|
||||
testing.expectEqual(2, outerInDoc.childElementCount);
|
||||
|
||||
const inner1 = outerInDoc.firstElementChild;
|
||||
testing.expectEqual('SPAN', inner1.tagName);
|
||||
testing.expectEqual('inner1', inner1.id);
|
||||
testing.expectEqual('First', inner1.textContent);
|
||||
}
|
||||
</script>
|
||||
21
src/browser/tests/window/screen.html
Normal file
21
src/browser/tests/window/screen.html
Normal file
@@ -0,0 +1,21 @@
|
||||
<!DOCTYPE html>
|
||||
<script src="../testing.js"></script>
|
||||
|
||||
<script id=screen>
|
||||
let screen = window.screen;
|
||||
testing.expectEqual(1920, screen.width);
|
||||
testing.expectEqual(1080, screen.height);
|
||||
|
||||
let orientation = screen.orientation;
|
||||
testing.expectEqual(0, orientation.angle);
|
||||
testing.expectEqual('landscape-primary', orientation.type);
|
||||
|
||||
// this shouldn't crash (it used to)
|
||||
screen.addEventListener('change', () => {});
|
||||
</script>
|
||||
|
||||
<script id=orientation>
|
||||
screen.orientation.addEventListener('change', () => {})
|
||||
// above shouldn't crash (it used to)
|
||||
testing.expectEqual(true, true);
|
||||
</script>
|
||||
@@ -38,6 +38,8 @@ pub const Type = union(enum) {
|
||||
message_port: *@import("MessagePort.zig"),
|
||||
text_track_cue: *@import("media/TextTrackCue.zig"),
|
||||
navigation: *@import("navigation/NavigationEventTarget.zig"),
|
||||
screen: *@import("Screen.zig"),
|
||||
screen_orientation: *@import("Screen.zig").Orientation,
|
||||
};
|
||||
|
||||
pub fn dispatchEvent(self: *EventTarget, event: *Event, page: *Page) !bool {
|
||||
|
||||
@@ -17,42 +17,65 @@
|
||||
// along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
|
||||
const js = @import("../js/js.zig");
|
||||
const Page = @import("../Page.zig");
|
||||
const EventTarget = @import("EventTarget.zig");
|
||||
|
||||
pub fn registerTypes() []const type {
|
||||
return &.{
|
||||
Screen,
|
||||
Orientation,
|
||||
};
|
||||
}
|
||||
|
||||
const Screen = @This();
|
||||
_pad: bool = false,
|
||||
|
||||
pub const init: Screen = .{};
|
||||
_proto: *EventTarget,
|
||||
_orientation: ?*Orientation = null,
|
||||
|
||||
pub fn init(page: *Page) !*Screen {
|
||||
return page._factory.eventTarget(Screen{
|
||||
._proto = undefined,
|
||||
._orientation = null,
|
||||
});
|
||||
}
|
||||
|
||||
pub fn asEventTarget(self: *Screen) *EventTarget {
|
||||
return self._proto;
|
||||
}
|
||||
|
||||
/// Total width of the screen in pixels
|
||||
pub fn getWidth(_: *const Screen) u32 {
|
||||
return 1920;
|
||||
}
|
||||
|
||||
/// Total height of the screen in pixels
|
||||
pub fn getHeight(_: *const Screen) u32 {
|
||||
return 1080;
|
||||
}
|
||||
|
||||
/// Available width (excluding OS UI elements like taskbar)
|
||||
pub fn getAvailWidth(_: *const Screen) u32 {
|
||||
return 1920;
|
||||
}
|
||||
|
||||
/// Available height (excluding OS UI elements like taskbar)
|
||||
pub fn getAvailHeight(_: *const Screen) u32 {
|
||||
return 1040; // 40px reserved for taskbar/dock
|
||||
}
|
||||
|
||||
/// Color depth in bits per pixel
|
||||
pub fn getColorDepth(_: *const Screen) u32 {
|
||||
return 24;
|
||||
}
|
||||
|
||||
/// Pixel depth in bits per pixel (typically same as colorDepth)
|
||||
pub fn getPixelDepth(_: *const Screen) u32 {
|
||||
return 24;
|
||||
}
|
||||
|
||||
pub fn getOrientation(self: *Screen, page: *Page) !*Orientation {
|
||||
if (self._orientation) |orientation| {
|
||||
return orientation;
|
||||
}
|
||||
const orientation = try Orientation.init(page);
|
||||
self._orientation = orientation;
|
||||
return orientation;
|
||||
}
|
||||
|
||||
pub const JsApi = struct {
|
||||
pub const bridge = js.Bridge(Screen);
|
||||
|
||||
@@ -60,14 +83,48 @@ pub const JsApi = struct {
|
||||
pub const name = "Screen";
|
||||
pub const prototype_chain = bridge.prototypeChain();
|
||||
pub var class_id: bridge.ClassId = undefined;
|
||||
pub const empty_with_no_proto = true;
|
||||
};
|
||||
|
||||
// Read-only properties
|
||||
pub const width = bridge.accessor(Screen.getWidth, null, .{});
|
||||
pub const height = bridge.accessor(Screen.getHeight, null, .{});
|
||||
pub const availWidth = bridge.accessor(Screen.getAvailWidth, null, .{});
|
||||
pub const availHeight = bridge.accessor(Screen.getAvailHeight, null, .{});
|
||||
pub const colorDepth = bridge.accessor(Screen.getColorDepth, null, .{});
|
||||
pub const pixelDepth = bridge.accessor(Screen.getPixelDepth, null, .{});
|
||||
pub const orientation = bridge.accessor(Screen.getOrientation, null, .{});
|
||||
};
|
||||
|
||||
pub const Orientation = struct {
|
||||
_proto: *EventTarget,
|
||||
|
||||
pub fn init(page: *Page) !*Orientation {
|
||||
return page._factory.eventTarget(Orientation{
|
||||
._proto = undefined,
|
||||
});
|
||||
}
|
||||
|
||||
pub fn asEventTarget(self: *Orientation) *EventTarget {
|
||||
return self._proto;
|
||||
}
|
||||
|
||||
pub fn getAngle(_: *const Orientation) u32 {
|
||||
return 0;
|
||||
}
|
||||
|
||||
pub fn getType(_: *const Orientation) []const u8 {
|
||||
return "landscape-primary";
|
||||
}
|
||||
|
||||
pub const JsApi = struct {
|
||||
pub const bridge = js.Bridge(Orientation);
|
||||
|
||||
pub const Meta = struct {
|
||||
pub const name = "ScreenOrientation";
|
||||
pub const prototype_chain = bridge.prototypeChain();
|
||||
pub var class_id: bridge.ClassId = undefined;
|
||||
};
|
||||
|
||||
pub const angle = bridge.accessor(Orientation.getAngle, null, .{});
|
||||
pub const @"type" = bridge.accessor(Orientation.getType, null, .{});
|
||||
};
|
||||
};
|
||||
|
||||
@@ -50,7 +50,7 @@ _css: CSS = .init,
|
||||
_crypto: Crypto = .init,
|
||||
_console: Console = .init,
|
||||
_navigator: Navigator = .init,
|
||||
_screen: Screen = .init,
|
||||
_screen: *Screen,
|
||||
_performance: Performance,
|
||||
_storage_bucket: *storage.Bucket,
|
||||
_on_load: ?js.Function = null,
|
||||
@@ -88,7 +88,7 @@ pub fn getNavigator(self: *Window) *Navigator {
|
||||
}
|
||||
|
||||
pub fn getScreen(self: *Window) *Screen {
|
||||
return &self._screen;
|
||||
return self._screen;
|
||||
}
|
||||
|
||||
pub fn getCrypto(self: *Window) *Crypto {
|
||||
|
||||
Reference in New Issue
Block a user