Reactjs preload.ts中的contextBridge.exposeInMainWorld:ipcRenderer从main.ts接收消息,但渲染器不';我不明白

Reactjs preload.ts中的contextBridge.exposeInMainWorld:ipcRenderer从main.ts接收消息,但渲染器不';我不明白,reactjs,typescript,electron,ipc,preload,Reactjs,Typescript,Electron,Ipc,Preload,在一个Electron React Typescript应用程序中,我设法通过预加载中的contextBridge.exposeInMainWorld将消息从渲染器进程发送到main,但在返回的过程中,处理后的输出从main实际经过through并到达preload.ts,但它没有到达渲染器进程。 这一定是很“愚蠢”的事情,但我不知道“罪魁祸首”是什么。所以,我请求你的帮助 预加载.ts: const { contextBridge, ipcRenderer } = require(&q

在一个Electron React Typescript应用程序中,我设法通过预加载中的contextBridge.exposeInMainWorld将消息从渲染器进程发送到main,但在返回的过程中,处理后的输出从main实际经过through并到达preload.ts,但它没有到达渲染器进程。 这一定是很“愚蠢”的事情,但我不知道“罪魁祸首”是什么。所以,我请求你的帮助

预加载.ts:

const {
  contextBridge,
  ipcRenderer
} = require("electron")


contextBridge.exposeInMainWorld(
  "api", {
      send: (channel, data) => {
          ipcRenderer.invoke(channel, data).catch(e => console.log(e))
      },
      receive: (channel, func) => {
        ipcRenderer.on(channel, (event, ...args) => func(...args))
        //ipcRenderer.on(channel, (event, ...args) => {
          //console.log("ipcRenderer.on-args: ", args);
        //});
      }
)
索引d.ts:

declare interface Window {
    api: {
      send: (channel: string, ...arg: any) => void;
      receive: (channel: string, func: (event: any, ...arg: any) => void) => void;
    }
}
main.ts:

ipcMain.handle("path-to-url", (IpcMainEvent, path) => {
  console.log("received a request from viewerDemo");
  if (mainWindow) {
    let urlified = url.pathToFileURL(path);
    console.log("urlified = url.pathToFileURL(path) : ", urlified);
    console.log("urlified.href= ", urlified.href);
    console.log("urlified.pathname= ", url.pathToFileURL(path).pathname);
    mainWindow.webContents.on("dom-ready", () => {
      mainWindow.webContents.send("path-to-url", "ohhhhhhhhhhhhhhhh");
      mainWindow.webContents.send("path-to-url", url.pathToFileURL(path).pathname);
    });
  }
});
渲染器进程(其中数据未正确显示!):

viewerDemo.tsx

import * as React from 'react';
import Viewer from 'react-viewer';

let path_1 = './images/natural-scene.jpeg';
let url_path;

const pathToUrlFunc = (path): string => {
  console.log("pathToUrlFunc called");
  window.api.send("path-to-url", path);
  let urlPath;
  window.api.receive("path-to-url", (event, args) => {
    console.log("window.api.receive called!");
    console.log("window.api.receive-args[0]: ", args[0]);
    urlPath = args[0];
  });
  return urlPath;
}

function ViewerDemo() {
  const [ visible, setVisible ] = React.useState(false);

  let urlpath = pathToUrlFunc(path_1);
  console.log("urlpath: ", urlpath);

  return (
    <div>
      <button onClick={() => { setVisible(true); } }>show</button>
      <Viewer
      visible={visible}
      onClose={() => { setVisible(false); } }
      images={[{src: 'https://www.fotolip.com/wp-content/uploads/2016/05/Nature-Scenes-
21.jpg', alt: ''}]}
      //images={[{src: urlpath, alt: ''}]}

      />
    </div>
  );
}

export default ViewerDemo;
我不再收到该错误,在preload.ts中,会显示main.ts中的正确消息,但渲染器进程仍然没有收到该消息:


你现在可能已经找到了这个问题的答案,但只是为了以防万一,也为了任何遇到这个问题的人的利益;虽然我无法运行代码来证明这是问题所在,但我认为预加载接收函数存在问题:

ipcRenderer.on代理方法仅使用args参数的排列来调用“func”处理程序。但在viewerDemo.tsx中,传递给“receive”的处理程序方法将被称为“func”,它需要两个参数“event”和“args”。因此,在args中传递的单个参数可能在“event”参数中显示为单个元素数组

为了检验理论并希望解决这个问题,请使方法一致。您可以在viewerDemo.tsx中的处理程序中从

window.api.receive(“url的路径”,(事件,参数)=>{


window.api.receive(“url路径”(args)=>{

或在preload.ts中更改此行
ipcRenderer.on(通道,(事件,…参数)=>func(…参数))


ipcRenderer.on(通道,(事件,…参数)=>func(事件,…参数))


这两种方法都可以解决问题。

您现在可能已经找到了这个问题的答案,但这只是为了以防万一,也为了任何遇到这个问题的人的利益;虽然我无法运行代码来证明这就是问题所在,但我认为预加载接收函数存在问题:

ipcRenderer.on代理方法仅使用args参数的排列来调用“func”处理程序。但是在viewerDemo.tsx中,传递给“receive”的处理程序方法被称为“func”,它需要两个参数“event”和“args”。因此,在args中传递的单个参数可能在“事件”参数

要测试理论并希望解决这个问题,请使方法一致

window.api.receive(“url的路径”,(事件,参数)=>{


window.api.receive(“url路径”(args)=>{

或在preload.ts中更改此行
ipcRenderer.on(通道,(事件,…参数)=>func(…参数))


ipcRenderer.on(通道,(事件,…参数)=>func(事件,…参数))


任何一个都可以解决问题。

这就是问题所在。谢谢@hargrovm在StackOverflow中打开了一篇关于正确渲染第二个窗口的新帖子。您能看一看吗?提前谢谢:这就是问题所在。谢谢@hargrovm在StackOverflow中打开了一篇关于正确渲染第二个窗口的新帖子。您愿意吗您能看一下吗?提前谢谢您:
  receive: (channel, func) => {
    //ipcRenderer.on(channel, (event, ...args) => func(...args))
    ipcRenderer.on(channel, (event, ...args) => {
      console.log("ipcRenderer.on-args: ", args);
    });
  }