繁体   English   中英

使用 Javascript 获取 Blazor 页面的大小

[英]Getting the size of a Blazor page with Javascript

我正在学习 Blazor 的 JSInterop。我想获得 Blazor 页面的宽度和高度,大小为 à canvas。

我正在使用默认的 Blazor 模板和屏幕左侧的菜单栏。 在此处输入图像描述

在 Canvas 测试 1 页的 html 部分,我有:

@page "/canvas_test1"
@inject IJSRuntime JsRuntime
<canvas @ref="canvas1"></canvas>
<button @onclick="SetCanvasSize">Set canvas size</button>

在代码部分我有:

ElementReference canvas1;
async Task SetCanvasSize()
{
    await JsRuntime.InvokeVoidAsync("SetCanvasSize", canvas1);
}

在 Javascript 文件中,我有:

function SetCanvasSize(element) {
ctx = element.getContext('2d');
console.log(window.innerWidth);
console.log(document.documentElement.scrollWidth);
}

但是window.innerWidthdocument.documentElement.scrollWidth这两种方法都给出了整个 window 的宽度,而不仅仅是包含 canvas 的页面。

如何在没有侧面菜单的情况下仅获取页面的宽度?

谢谢

我认为您对 Blazor 中的页面是什么感到有点困惑。它基本上是您提供导航路径的组件。 如果您包括布局(通常默认设置),那实际上是页面的一部分。 页面上的所有内容,例如您的 canvas,都只是 html 个元素。 它正确地告诉您 window 的大小,如果您调整浏览器的大小,您可以看到它会发生变化。

html 元素具有属性“offsetWidth”和“offsetHeight”。 因此,为了您的使用,您想要传递要测量的元素,并使用element.offsetWidth

function GetCanvasSize(element) {
     alert ("Element measurements: " + element.offsetWidth + ", " + element.offsetHeight);
}

你可以在这里看到html元素的更多成员,包括常用的方法和事件: https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/offsetWidth

请注意,此列表缺少您想要了解的一些重要信息,尤其是您在移动客户端上拖动元素所需的各种触摸事件(鼠标事件在手机上不起作用)。

您需要获取包含元素的尺寸。 您还需要监听调整大小事件。

我使用的服务可以为任何元素获取 ref 并监听更改。

bCore.js

export function listenToWindowResize(dotNetHelper) {

    function resizeEventHandler() {
        dotNetHelper.invokeMethodAsync('WindowResizeEvent');
    }

    window.addEventListener("resize", resizeEventHandler);

    dotNetHelper.invokeMethodAsync('WindowResizeEvent');
}

export function getBoundingRectangle(element, parm) {
    return element.getBoundingClientRect();
}

export function getWindowSizeDetails(parm) {

    var e = window, a = 'inner';

    if (!('innerWidth' in window)) {
        a = 'client';
        e = document.documentElement || document.body;
    }

    let windowSize =
    {
        innerWidth: e[a + 'Width'],
        innerHeight: e[a + 'Height'],
        screenWidth: window.screen.width,
        screenHeight: window.screen.height
    };

    return windowSize;
}

JSInteropCoreService.cs

public class JSInteropCoreService : IJSInteropCoreService, IAsyncDisposable
{
    private readonly Lazy<Task<IJSObjectReference>> moduleTask;
    private bool isResizing;
    private System.Timers.Timer resizeTimer;
    private DotNetObjectReference<JSInteropCoreService> jsInteropCoreServiceRef;

    public JSInteropCoreService(IJSRuntime jsRuntime)
    {
        this.resizeTimer = new System.Timers.Timer(interval: 25);
        this.isResizing = false;
        this.resizeTimer.Elapsed += async (sender, elapsedEventArgs) => await DimensionsChanged(sender!, elapsedEventArgs);

        this.moduleTask = new(() => jsRuntime.InvokeAsync<IJSObjectReference>(
          identifier: "import", args: "./_content/BJSInteroptCore/bCore.js").AsTask());
    }

    public event NotifyResizing OnResizing;
    public event NotifyResize OnResize;

    public async ValueTask InitializeAsync()
    {
        IJSObjectReference module = await GetModuleAsync();

        this.jsInteropCoreServiceRef = DotNetObjectReference.Create(this);

        await module.InvokeVoidAsync(identifier: "listenToWindowResize", this.jsInteropCoreServiceRef);

        this.BrowserSizeDetails = await module.InvokeAsync<BrowserSizeDetails>(identifier: "getWindowSizeDetails");

    }

    public async ValueTask<BrowserSizeDetails> GetWindowSizeAsync()
    {
        IJSObjectReference module = await GetModuleAsync();
        return await module.InvokeAsync<BrowserSizeDetails>(identifier: "getWindowSizeDetails");
    }

    public async ValueTask<ElementBoundingRectangle> GetElementBoundingRectangleAsync(ElementReference elementReference)
    {
        IJSObjectReference module = await GetModuleAsync();
        return await module.InvokeAsync<ElementBoundingRectangle>(identifier: "getBoundingRectangle", elementReference);
    }

    [JSInvokable]
    public ValueTask WindowResizeEvent()
    {
        if (this.isResizing is not true)
        {
            this.isResizing = true;
            OnResizing?.Invoke(this.isResizing);
        }
        DebounceResizeEvent();
        return ValueTask.CompletedTask;
    }

    public BrowserSizeDetails BrowserSizeDetails { get; private set; } = new BrowserSizeDetails();

    private void DebounceResizeEvent()
    {
        if (this.resizeTimer.Enabled is false)
        {
            Task.Run(async () =>
            {
                this.BrowserSizeDetails = await GetWindowSizeAsync();
                isResizing = false;
                OnResizing?.Invoke(this.isResizing);
                OnResize?.Invoke();
            });
            this.resizeTimer.Restart();
        }
    }

    private async ValueTask DimensionsChanged(object sender, System.Timers.ElapsedEventArgs e)
    {
        this.resizeTimer.Stop();
        this.BrowserSizeDetails = await GetWindowSizeAsync();
        isResizing = false;
        OnResizing?.Invoke(this.isResizing);
        OnResize?.Invoke();
    }

    public async ValueTask DisposeAsync()
    {
        if (moduleTask.IsValueCreated)
        {
            IJSObjectReference module = await GetModuleAsync();
            await module.DisposeAsync();
        }
    }

    private async Task<IJSObjectReference> GetModuleAsync()
        => await this.moduleTask.Value;
}
public class ElementBoundingRectangle
{
    public double X { get; set; }
    public double Y { get; set; }
    public double Width { get; set; }
    public double Height { get; set; }
    public double Top { get; set; }
    public double Right { get; set; }
    public double Bottom { get; set; }
    public double Left { get; set; }
}
public class BrowserSizeDetails
{
    public double InnerWidth { get; set; }
    public double InnerHeight { get; set; }
    public int ScreenWidth { get; set; }
    public int ScreenHeight { get; set; }
}

我使用 25 毫秒的间隔对调整大小事件进行去抖动以防止延迟。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM