var _excluded = ["triggerType", "buttonText", "placeholder", "showConfirmButton", "showHistory", "historyKey", "enableScanner", "onScannerData", "onSearch"];
function _extends() { _extends = Object.assign ? Object.assign.bind() : function (target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) { if (Object.prototype.hasOwnProperty.call(source, key)) { target[key] = source[key]; } } } return target; }; return _extends.apply(this, arguments); }
function _objectWithoutProperties(source, excluded) { if (source == null) return {}; var target = _objectWithoutPropertiesLoose(source, excluded); var key, i; if (Object.getOwnPropertySymbols) { var sourceSymbolKeys = Object.getOwnPropertySymbols(source); for (i = 0; i < sourceSymbolKeys.length; i++) { key = sourceSymbolKeys[i]; if (excluded.indexOf(key) >= 0) continue; if (!Object.prototype.propertyIsEnumerable.call(source, key)) continue; target[key] = source[key]; } } return target; }
function _objectWithoutPropertiesLoose(source, excluded) { if (source == null) return {}; var target = {}; var sourceKeys = Object.keys(source); var key, i; for (i = 0; i < sourceKeys.length; i++) { key = sourceKeys[i]; if (excluded.indexOf(key) >= 0) continue; target[key] = source[key]; } return target; }
import React, { forwardRef, useEffect, useImperativeHandle, useRef } from 'react';
import { locales as utilsLocales } from '@pisell/utils';
import { PisellLookup } from "../pisellLookup";
import useEngineContext from "../../hooks/useEngineContext";
import { getText } from "../../locales";

/**
 * 原生扫码事件名，对齐宿主端约定。
 */
export var SCAN_RESULT_EVENT = 'nativeScanResult';

/**
 * 扫码枪回传数据（对齐宿主 ScanResultPayload）
 * - code: 条码标识（如条码格式 / 业务字段）
 * - data: 扫描得到的字符串值（写入输入框的内容）
 */

/**
 * PisellFind Props
 * 继承 PisellLookup 的所有 Props，并扩展扫码枪监听相关字段。
 */

/**
 * PisellFind Ref
 * 继承 PisellLookup 的所有 Ref 方法
 */

/**
 * PisellFind 组件
 * 基于 PisellLookup 的组件内查找优化版本
 *
 * 核心特点：
 * - 默认使用 button 触发器
 * - 默认不显示确认按钮（输入即搜索）
 * - 默认开启搜索历史
 * - 默认不展示结果区（结果在页面其他位置展示）
 * - 通过 `enableScanner` 接入扫码枪：优先走宿主注入的「扫码焦点栈」
 *   （`appHelper.utils.acquireScanFocus`），保证同页多个 PisellFind 只有栈顶响应；
 *   宿主未注册时回退到直连 `app.pubsub.subscribe(SCAN_RESULT_EVENT, ...)`。
 *   每次扫码直接覆盖输入框内容并触发 onSearch / onScannerData；切回 false 时自动释放 / unsubscribe。
 *
 * @example
 * ```tsx
 * <PisellFind
 *   triggerType="input"
 *   enableScanner={isActive}
 *   onScannerData={(payload) => console.log('scan:', payload.data)}
 *   onSearch={(keyword) => filterData(keyword)}
 * />
 * ```
 */
export var PisellFind = /*#__PURE__*/forwardRef(function (props, ref) {
  var _engineContext$appHel, _engineContext$appHel2, _appHelperUtils$busin;
  var _props$triggerType = props.triggerType,
    triggerType = _props$triggerType === void 0 ? 'button' : _props$triggerType,
    _props$buttonText = props.buttonText,
    buttonText = _props$buttonText === void 0 ? function () {
      var key = 'pisell2.recordBoard.toolbar.find';
      var u = utilsLocales.getText(key);
      return u && u !== key ? u : getText(key) || getText('pisell-find-button-text');
    }() : _props$buttonText,
    _props$placeholder = props.placeholder,
    placeholder = _props$placeholder === void 0 ? function () {
      var key = 'pisell2.recordBoard.toolbar.findPlaceholder';
      var u = utilsLocales.getText(key);
      return u && u !== key ? u : getText(key) || getText('pisell-find-placeholder');
    }() : _props$placeholder,
    _props$showConfirmBut = props.showConfirmButton,
    showConfirmButton = _props$showConfirmBut === void 0 ? false : _props$showConfirmBut,
    _props$showHistory = props.showHistory,
    showHistory = _props$showHistory === void 0 ? true : _props$showHistory,
    _props$historyKey = props.historyKey,
    historyKey = _props$historyKey === void 0 ? 'pisell_find_history' : _props$historyKey,
    _props$enableScanner = props.enableScanner,
    enableScanner = _props$enableScanner === void 0 ? false : _props$enableScanner,
    onScannerData = props.onScannerData,
    onSearch = props.onSearch,
    restProps = _objectWithoutProperties(props, _excluded);
  var lookupRef = useRef(null);

  /** 透传给监听回调的最新引用，避免回调闭包 stale */
  var onScannerDataRef = useRef(onScannerData);
  var onSearchRef = useRef(onSearch);
  useEffect(function () {
    onScannerDataRef.current = onScannerData;
  }, [onScannerData]);
  useEffect(function () {
    onSearchRef.current = onSearch;
  }, [onSearch]);
  useImperativeHandle(ref, function () {
    return {
      open: function open() {
        var _lookupRef$current;
        return (_lookupRef$current = lookupRef.current) === null || _lookupRef$current === void 0 ? void 0 : _lookupRef$current.open();
      },
      close: function close() {
        var _lookupRef$current2;
        return (_lookupRef$current2 = lookupRef.current) === null || _lookupRef$current2 === void 0 ? void 0 : _lookupRef$current2.close();
      },
      getKeyword: function getKeyword() {
        var _lookupRef$current$ge, _lookupRef$current3;
        return (_lookupRef$current$ge = (_lookupRef$current3 = lookupRef.current) === null || _lookupRef$current3 === void 0 ? void 0 : _lookupRef$current3.getKeyword()) !== null && _lookupRef$current$ge !== void 0 ? _lookupRef$current$ge : '';
      },
      setKeyword: function setKeyword(v) {
        var _lookupRef$current4;
        return (_lookupRef$current4 = lookupRef.current) === null || _lookupRef$current4 === void 0 ? void 0 : _lookupRef$current4.setKeyword(v);
      }
    };
  }, []);

  /** 通过 useEngineContext 拿到宿主 app（含 pubsub.subscribe / unsubscribe）与扫码焦点栈 */
  var engineContext = useEngineContext();
  /**
   * 用 ref 稳定 getApp 引用：低代码环境下 engineContext 每次渲染可能返回新引用，
   * 若把 getApp 直接放进 effect 依赖会导致频繁 unsubscribe/subscribe（甚至漏掉扫码事件）。
   * effect 依赖只保留 enableScanner，运行时通过 ref 拿最新的 getApp。
   */
  var getAppRef = useRef(undefined);
  getAppRef.current = typeof (engineContext === null || engineContext === void 0 || (_engineContext$appHel = engineContext.appHelper) === null || _engineContext$appHel === void 0 || (_engineContext$appHel = _engineContext$appHel.utils) === null || _engineContext$appHel === void 0 ? void 0 : _engineContext$appHel.getApp) === 'function' ? engineContext.appHelper.utils.getApp : undefined;

  /**
   * 宿主可选注入的「扫码焦点栈」入口（acquireScanFocus）。
   * 申请焦点后只有栈顶组件的回调会被触发；返回的 token.release() 用于释放焦点。
   * 兼容两种注入位置：`appHelper.utils.acquireScanFocus` 或 `appHelper.utils.businessUtils.acquireScanFocus`
   * （后者为宿主通过 bootstrap actions.appHelper.businessUtils 注入的常见方式）。
   * 同样用 ref 稳定引用，effect 依赖只保留 enableScanner。
   */
  var acquireScanFocusRef = useRef(undefined);
  var appHelperUtils = engineContext === null || engineContext === void 0 || (_engineContext$appHel2 = engineContext.appHelper) === null || _engineContext$appHel2 === void 0 ? void 0 : _engineContext$appHel2.utils;
  acquireScanFocusRef.current = typeof (appHelperUtils === null || appHelperUtils === void 0 ? void 0 : appHelperUtils.acquireScanFocus) === 'function' ? appHelperUtils.acquireScanFocus : typeof (appHelperUtils === null || appHelperUtils === void 0 || (_appHelperUtils$busin = appHelperUtils.businessUtils) === null || _appHelperUtils$busin === void 0 ? void 0 : _appHelperUtils$busin.acquireScanFocus) === 'function' ? appHelperUtils.businessUtils.acquireScanFocus : undefined;
  useEffect(function () {
    if (!enableScanner) return undefined;

    /**
     * 监听回调：每次扫码直接覆盖输入框。
     * ScanResultPayload: { code, data }，取 data 作为输入框值与搜索关键词。
     * setKeyword 在受控模式下会触发外部 onChange；onSearch 需要显式触发以驱动后续搜索流程
     * （受控模式下宿主一般只通过 onSearch 拿到新关键词，不会在 onChange 里再触发一次 onSearch，
     *  因此这里不会产生重复请求。如需自定义合流，可绑定 onScannerData 自行处理）。
     *
     * 非法 payload（无 data 或 data 为空串）直接忽略，避免把输入框/搜索条件意外清空。
     */
    var onScan = function onScan(payload) {
      var _lookupRef$current5, _onSearchRef$current, _onScannerDataRef$cur;
      var data = payload === null || payload === void 0 ? void 0 : payload.data;
      if (typeof data !== 'string' || data.length === 0) {
        return;
      }
      (_lookupRef$current5 = lookupRef.current) === null || _lookupRef$current5 === void 0 || _lookupRef$current5.setKeyword(data);
      (_onSearchRef$current = onSearchRef.current) === null || _onSearchRef$current === void 0 || _onSearchRef$current.call(onSearchRef, data);
      (_onScannerDataRef$cur = onScannerDataRef.current) === null || _onScannerDataRef$cur === void 0 || _onScannerDataRef$cur.call(onScannerDataRef, payload);
    };

    // 优先：接入宿主注入的「扫码焦点栈」，保证同页多个实例只有栈顶响应。
    var acquireScanFocus = acquireScanFocusRef.current;
    if (typeof acquireScanFocus === 'function') {
      try {
        var token = acquireScanFocus(onScan);
        return function () {
          try {
            var _token$release;
            token === null || token === void 0 || (_token$release = token.release) === null || _token$release === void 0 || _token$release.call(token);
          } catch (e) {
            console.warn('[PisellFind] release scan focus failed:', e);
          }
        };
      } catch (e) {
        console.warn('[PisellFind] acquire scan focus failed, fallback to pubsub:', e);
      }
    }

    // 回退：宿主未注册焦点栈时，直连 pubsub（与改造前行为一致）。
    var getApp = getAppRef.current;
    if (typeof getApp !== 'function') return undefined;
    var app = getApp();
    var pubsub = app === null || app === void 0 ? void 0 : app.pubsub;
    if (!pubsub || typeof pubsub.subscribe !== 'function') {
      return undefined;
    }
    try {
      pubsub.subscribe(SCAN_RESULT_EVENT, onScan);
    } catch (e) {
      console.warn('[PisellFind] subscribe scanner failed:', e);
      return undefined;
    }
    return function () {
      try {
        var _pubsub$unsubscribe;
        (_pubsub$unsubscribe = pubsub.unsubscribe) === null || _pubsub$unsubscribe === void 0 || _pubsub$unsubscribe.call(pubsub, SCAN_RESULT_EVENT, onScan);
      } catch (e) {
        console.warn('[PisellFind] unsubscribe scanner failed:', e);
      }
    };
  }, [enableScanner]);
  return /*#__PURE__*/React.createElement(PisellLookup, _extends({
    ref: lookupRef,
    triggerType: triggerType,
    buttonText: buttonText,
    placeholder: placeholder,
    showConfirmButton: showConfirmButton,
    showHistory: showHistory,
    historyKey: historyKey,
    onSearch: onSearch
  }, restProps));
});
PisellFind.displayName = 'PisellFind';