我有一个如下所示的输入:

<input
    type="text"
    value={form().username}
    onInput={(e) => handleInput(e)}
/>

而TypeScrip表明,e是这样的类型:

(parameter) e: InputEvent & {
    currentTarget: HTMLInputElement;
    target: Element;
}

如果我使用它创建handleInput,则使用名称和值不会显示为类型定义的一部分,所以我添加了它们:

const handleInput = (e: InputEvent & {
    currentTarget: HTMLInputElement;
    target: Element & { name: string; value: string; };
}) => {
    setForm({
        ...form(),
        [e.target.name]: e.target.value,
    });
}

但是,这会使我的e在输入文本框中突出显示为错误:

Argument of type 'InputEvent & { currentTarget: HTMLInputElement; target: Element; }' is not assignable to parameter of type 'InputEvent & { currentTarget: HTMLInputElement; target: Element & { name: string; value: string; }; }'.
  Type 'InputEvent & { currentTarget: HTMLInputElement; target: Element; }' is not assignable to type '{ currentTarget: HTMLInputElement; target: Element & { name: string; value: string; }; }'.
    Types of property 'target' are incompatible.
      Type 'EventTarget & Element' is not assignable to type 'Element & { name: string; value: string; }'.
        Type 'EventTarget & Element' is missing the following properties from type '{ name: string; value: string; }': name, value

如何修复这种不兼容性,因为名称和值是事件目标类型的有效部分.

推荐答案

输入事件的正确事件类型如下:

import { JSX } from "solid-js";

export const App = () => {
  const handleInput: JSX.EventHandlerUnion<HTMLInputElement, InputEvent> = (event) => {
    // currentTarget: EventTarget & HTMLInputElement
    console.log(event.currentTarget.value);
  }

  return (
    <input onInput={handleInput} />
  );
};

直接注释事件不起作用,因为类型currentTarget是元素或null,但我们可以确定它的元素:

const handler = (event: InputEvent) => {
  // Property 'value' does not exist on type 'EventTarget'
  console.log(event.currentTarget.value);
}

如果不想使用联合类型,则可以 Select :

const handler: JSX.EventHandler<HTMLInputElement, InputEvent> = (event) => {
  // currentTarget: EventTarget & HTMLInputElement
  console.log(event.currentTarget.value);
}

PS:您有一个不必要的回调,除了将值传递给实际的回调外,它什么也不做:

<input onInput={(e) => handleInput(e)} />

如果我没记错的话,Reaction使用这个语法修复了它的一些奇怪之处,至少在它的早期是这样.在固体中,它没有任何作用.

当您需要将额外的值(如索引号)与事件一起传递时,此syTax可能很有用;当将同一处理程序附加到多个项时,此syTax可能很有用,但更好的 Select 是部分应用程序:

const handleInput = (index: number) => (event) => {
  console.log(index);
}

<input onInput={handleInput(index)} />

Typescript相关问答推荐

React-Native运行方法通过监听另一个状态来更新一个状态

如何为ViewContainerRef加载的Angular组件实现CanDeactivate保护?

具有动态键的泛型类型

学习Angular :无法读取未定义的属性(正在读取推送)

路由链接不会导航到指定router-outlet 的延迟加载模块

Material UI / MUI系统:我如何告诉TypeScript主题是由提供程序传递的?

TS2339:类型{}上不存在属性消息

类型脚本映射类型:从对象和字符串列表到键值对象

在对象中将缺省值设置为空值

如何在NX工作区项目.json中设置类似angular.json的两个项目构建配置?

使用KeyOf和Never的循环引用

重载函数的T helper参数

如何在省略一个参数的情况下从函数类型中提取参数类型?

判断映射类型内的键值的条件类型

TypeScrip-如何自动推断UNION变量的类型

我不明白使用打字脚本在模板中展开参考

如何解决&Quot;类型不可分配给TypeScrip IF语句中的类型&Quot;?

Route.ts文件中未导出HTTP方法

如何在TypeScript中声明逆变函数成员?

React 中如何比较两个对象数组并获取不同的值?