You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Ant Design中Radio内嵌Dropdown点击触发重渲染无法选值的解决方法

解决Ant Design Radio内嵌Select时下拉无法选择的问题

问题复现代码

import React, { useState } from "react";
import "./index.css";
import type { RadioChangeEvent } from "antd";
import { Radio, Space, Select } from "antd";

const App: React.FC = () => {
  const [value, setValue] = useState(1);

  const onChange = (e: RadioChangeEvent) => {
    console.log("radio checked", e.target.value);
    setValue(e.target.value);
  };

  return (
    <Radio.Group onChange={onChange} value={value}>
      <Space direction="vertical">
        <Radio value={1}>Option A</Radio>
        <Radio value={2}>Option B</Radio>
        <Radio value={3}>Option C</Radio>
        <Radio value={4}>
          <Select
            defaultValue="lucy"
            style={{ width: 120 }}
            options={[
              { value: "jack", label: "Jack" },
              { value: "lucy", label: "Lucy" },
              { value: "Yiminghe", label: "yiminghe" },
              { value: "disabled", label: "Disabled", disabled: true },
            ]}
            onClick={(e) => e.stopPropagation()}
          />
        </Radio>
      </Space>
    </Radio.Group>
  );
};

export default App;

问题原因

点击Select下拉选项时,事件会向上冒泡到外层Radio组件,触发Radio的选中状态变更,进而触发Radio.Group的onChange回调更新value,导致组件重渲染,Select下拉菜单被强制关闭,无法完成选择。

解决方案

以下两种方式均可有效阻止事件冒泡,解决该问题:

方式一:自定义下拉菜单容器拦截事件

通过Select的dropdownRender属性,给下拉菜单外层包裹容器并阻止事件冒泡:

import React, { useState } from "react";
import "./index.css";
import type { RadioChangeEvent } from "antd";
import { Radio, Space, Select } from "antd";

const App: React.FC = () => {
  const [value, setValue] = useState(1);

  const onChange = (e: RadioChangeEvent) => {
    console.log("radio checked", e.target.value);
    setValue(e.target.value);
  };

  return (
    <Radio.Group onChange={onChange} value={value}>
      <Space direction="vertical">
        <Radio value={1}>Option A</Radio>
        <Radio value={2}>Option B</Radio>
        <Radio value={3}>Option C</Radio>
        <Radio value={4}>
          <Select
            defaultValue="lucy"
            style={{ width: 120 }}
            options={[
              { value: "jack", label: "Jack" },
              { value: "lucy", label: "Lucy" },
              { value: "Yiminghe", label: "yiminghe" },
              { value: "disabled", label: "Disabled", disabled: true },
            ]}
            onClick={(e) => e.stopPropagation()}
            dropdownRender={(menu) => (
              <div onClick={(e) => e.stopPropagation()}>{menu}</div>
            )}
          />
        </Radio>
      </Space>
    </Radio.Group>
  );
};

export default App;

方式二:在Radio点击事件中过滤Select操作

给Radio添加onClick事件,判断点击目标是否属于Select组件,若是则阻止事件传播和默认行为:

import React, { useState } from "react";
import "./index.css";
import type { RadioChangeEvent } from "antd";
import { Radio, Space, Select } from "antd";

const App: React.FC = () => {
  const [value, setValue] = useState(1);

  const onChange = (e: RadioChangeEvent) => {
    console.log("radio checked", e.target.value);
    setValue(e.target.value);
  };

  return (
    <Radio.Group onChange={onChange} value={value}>
      <Space direction="vertical">
        <Radio value={1}>Option A</Radio>
        <Radio value={2}>Option B</Radio>
        <Radio value={3}>Option C</Radio>
        <Radio 
          value={4}
          onClick={(e) => {
            const isSelectElement = e.target.closest(".ant-select") !== null;
            if (isSelectElement) {
              e.stopPropagation();
              e.preventDefault();
            }
          }}
        >
          <Select
            defaultValue="lucy"
            style={{ width: 120 }}
            options={[
              { value: "jack", label: "Jack" },
              { value: "lucy", label: "Lucy" },
              { value: "Yiminghe", label: "yiminghe" },
              { value: "disabled", label: "Disabled", disabled: true },
            ]}
          />
        </Radio>
      </Space>
    </Radio.Group>
  );
};

export default App;

说明

  • 方式一针对下拉菜单事件单独拦截,保留了Radio正常点击选中的功能;
  • 方式二直接过滤Radio的误触发场景,逻辑更直观,适合不需要通过点击Select区域选中Radio的场景。

内容的提问来源于stack exchange,提问作者Cường Nguyễn Đức

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.16 15:01:03