package cc.winboll.studio.positions.activities;

/**
 * @Author ZhanGSKen&豆包大模型<zhangsken@qq.com>
 * @Date 2025/09/29 18:22
 * @Describe 位置列表页面（适配MainService GPS接口+规范服务交互+完善生命周期）
 */
import android.app.Activity;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Bundle;
import android.os.IBinder;
import android.view.View;
import android.view.inputmethod.InputMethodManager;
import android.widget.TextView;
import android.widget.Toast;
import androidx.appcompat.widget.Toolbar;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import cc.winboll.studio.libaes.interfaces.IWinBoLLActivity;
import cc.winboll.studio.libappbase.LogUtils;
import cc.winboll.studio.libappbase.ToastUtils;
import cc.winboll.studio.positions.R;
import cc.winboll.studio.positions.adapters.PositionAdapter;
import cc.winboll.studio.positions.models.PositionModel;
import cc.winboll.studio.positions.services.MainService;
import java.util.ArrayList;
import java.util.concurrent.atomic.AtomicBoolean;

/**
 * Java 7 语法适配：
 * 1. 服务绑定用匿名内部类实现 ServiceConnection
 * 2. Adapter 初始化传入 MainService 实例，确保数据来源唯一
 * 3. 所有位置/任务操作通过 MainService 接口执行
 */
public class LocationActivity extends WinBoLLActivity implements IWinBoLLActivity {
    public static final String TAG = "LocationActivity";

	private Toolbar mToolbar;

    private RecyclerView mRvPosition;
    private PositionAdapter mPositionAdapter;

    // MainService 引用+绑定状态（AtomicBoolean 确保多线程状态可见性）
    private MainService mMainService;
    private final AtomicBoolean isServiceBound = new AtomicBoolean(false);
    // 标记 Adapter 是否已初始化（避免重复初始化/销毁后初始化）
    private final AtomicBoolean isAdapterInited = new AtomicBoolean(false);

	// ---------------------- 新增：GPS监听核心变量 ----------------------
    private MainService.GpsUpdateListener mGpsUpdateListener; // GPS监听实例
    private PositionModel mCurrentGpsPos; // 缓存当前GPS位置（供页面使用）
    // 本地位置缓存（解决服务数据未同步时Adapter空数据问题）
    private final ArrayList<PositionModel> mLocalPosCache = new ArrayList<PositionModel>();


    // 服务连接（Java 7 匿名内部类实现，强化状态同步+数据预加载）
    private ServiceConnection mServiceConnection = new ServiceConnection() {
        @Override
        public void onServiceConnected(ComponentName name, IBinder service) {
            // 1. 安全获取服务实例（避免强转失败+服务未就绪）
            if (!(service instanceof MainService.LocalBinder)) {
                LogUtils.e(TAG, "服务绑定失败：Binder类型不匹配（非MainService.LocalBinder）");
                isServiceBound.set(false);
                return;
            }

            try {
                MainService.LocalBinder binder = (MainService.LocalBinder) service;
                mMainService = binder.getService();
                // 2. 标记服务绑定成功（原子操作，确保多线程可见）
                isServiceBound.set(true);
                LogUtils.d(TAG, "MainService绑定成功，开始同步数据+初始化Adapter");

                // 3. 同步服务数据到本地缓存（核心：先同步数据，再初始化Adapter）
                syncDataFromMainService();
                // 4. 注册GPS监听（确保监听在Adapter前初始化，数据不丢失）
                registerGpsListener();
                // 5. 初始化Adapter（传入本地缓存+服务实例，数据非空）
                initPositionAdapter();

            } catch (Exception e) {
                LogUtils.d(TAG, "服务绑定后初始化失败：" + e.getMessage());
                isServiceBound.set(false);
                mMainService = null;
                showToast("服务初始化失败，无法加载数据");
            }
        }

        @Override
        public void onServiceDisconnected(ComponentName name) {
            LogUtils.w(TAG, "MainService断开连接，清空引用+标记状态");
            // 1. 清空服务引用+标记绑定状态
            mMainService = null;
            isServiceBound.set(false);
            // 2. 标记Adapter未初始化（下次绑定需重新初始化）
            isAdapterInited.set(false);
        }
    };

    @Override
    public Activity getActivity() {
        return this;
    }

    @Override
    public String getTag() {
        return TAG;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_location);

		mToolbar = findViewById(R.id.toolbar);
        setSupportActionBar(mToolbar);
		mToolbar.setSubtitle(getTag());
        mToolbar.setTitleTextAppearance(this, R.style.Toolbar_TitleText);
		getSupportActionBar().setDisplayHomeAsUpEnabled(true);
        mToolbar.setNavigationOnClickListener(new View.OnClickListener() {
				@Override
				public void onClick(View v) {
					LogUtils.d(TAG, "【导航栏】点击返回");
					finish();
				}
			});

        // 1. 初始化视图（优先执行，避免Adapter初始化时视图为空）
        initView();
        // 2. 初始化GPS监听（提前创建，避免绑定服务后空指针）
        initGpsUpdateListener();
        // 3. 绑定MainService（最后执行，确保视图/监听已就绪）
        bindMainService();
    }

    /**
     * 初始化视图（RecyclerView）- 确保视图先于Adapter初始化
     */
    private void initView() {
        mRvPosition = (RecyclerView) findViewById(R.id.rv_position_list);
        // 1. 显式设置布局管理器（避免Adapter设置时无布局管理器崩溃）
        LinearLayoutManager layoutManager = new LinearLayoutManager(this);
        layoutManager.setOrientation(LinearLayoutManager.VERTICAL);
        mRvPosition.setLayoutManager(layoutManager);
        // 2. 初始化本地缓存（避免首次加载时缓存为空）
        mLocalPosCache.clear();
        LogUtils.d(TAG, "视图初始化完成（布局管理器+本地缓存已就绪）");
    }

    /**
     * 绑定MainService（Java 7 显式Intent，强化绑定安全性）
     */
    private void bindMainService() {
        // 1. 避免重复绑定（快速重建Activity时防止多绑定）
        if (isServiceBound.get()) {
            LogUtils.w(TAG, "无需重复绑定：MainService已绑定");
            return;
        }

        Intent serviceIntent = new Intent(this, MainService.class);
        // 2. 绑定服务（BIND_AUTO_CREATE：服务不存在时自动创建，增加绑定成功率）
        boolean bindSuccess = bindService(serviceIntent, mServiceConnection, BIND_AUTO_CREATE);
        if (!bindSuccess) {
            LogUtils.e(TAG, "发起MainService绑定请求失败（服务未找到/系统限制）");
            showToast("服务绑定失败，无法加载位置数据");
        } else {
            LogUtils.d(TAG, "MainService绑定请求已发起");
        }
    }

    /**
     * 从MainService同步数据到本地缓存（核心解决Adapter空数据问题）
     * 作用：1. 服务数据优先同步到本地，Adapter基于本地缓存初始化
     *      2. 避免服务数据更新时直接操作Adapter，通过缓存中转
     */
    private void syncDataFromMainService() {
        // 1. 安全校验（服务未绑定/服务空，用本地缓存兜底）
        if (!isServiceBound.get() || mMainService == null) {
            LogUtils.w(TAG, "同步数据：服务未就绪，使用本地缓存（当前缓存量=" + mLocalPosCache.size() + "）");
            return;
        }

        try {
            // 2. 从服务获取最新位置数据（同步操作，确保数据拿到后再返回）
            ArrayList<PositionModel> servicePosList = mMainService.getPositionList();
            // 3. 同步到本地缓存（清空旧数据+添加新数据，避免重复）
            synchronized (mLocalPosCache) { // 加锁避免多线程操作缓存冲突
                mLocalPosCache.clear();
                if (servicePosList != null && !servicePosList.isEmpty()) {
                    mLocalPosCache.addAll(servicePosList);
                }
            }
            LogUtils.d(TAG, "数据同步完成：服务位置数=" + (servicePosList == null ? 0 : servicePosList.size()) 
					   + "，本地缓存数=" + mLocalPosCache.size());

        } catch (Exception e) {
            LogUtils.d(TAG, "同步服务数据失败：" + e.getMessage());
            // 异常时保留本地缓存，避免Adapter无数据
            LogUtils.w(TAG, "同步失败，使用本地缓存兜底（缓存量=" + mLocalPosCache.size() + "）");
        }
    }

    /**
     * 初始化PositionAdapter（核心优化：基于本地缓存初始化，避免空数据）
     */
    private void initPositionAdapter() {
        // 1. 多重安全校验（避免销毁后初始化/重复初始化/依赖未就绪）
        if (isAdapterInited.get() || !isServiceBound.get() || mMainService == null || mRvPosition == null) {
            LogUtils.w(TAG, "Adapter初始化跳过：" 
					   + "已初始化=" + isAdapterInited.get() 
					   + "，服务绑定=" + isServiceBound.get() 
					   + "，视图就绪=" + (mRvPosition != null));
            return;
        }

        try {
            // 2. 基于本地缓存初始化Adapter（缓存已同步服务数据，非空）
            mPositionAdapter = new PositionAdapter(this, mLocalPosCache, mMainService);

            // 3. 设置删除回调（删除时同步服务+本地缓存+Adapter）
            mPositionAdapter.setOnDeleteClickListener(new PositionAdapter.OnDeleteClickListener() {
					@Override
					public void onDeleteClick(int position) {
						// 安全校验（索引有效+服务绑定+缓存非空）
						if (position < 0 || position >= mLocalPosCache.size() || !isServiceBound.get() || mMainService == null) {
							LogUtils.w(TAG, "删除位置失败：索引无效/服务未就绪（索引=" + position + "，缓存量=" + mLocalPosCache.size() + "）");
							return;
						}

						PositionModel deletePos = mLocalPosCache.get(position);
						if (deletePos != null && !deletePos.getPositionId().isEmpty()) {
							// 步骤1：调用服务删除（确保服务数据一致性）
							mMainService.removePosition(deletePos.getPositionId());
							// 步骤2：删除本地缓存（确保缓存与服务同步）
							synchronized (mLocalPosCache) {
								mLocalPosCache.remove(position);
							}
							// 步骤3：通知Adapter刷新（基于缓存操作，避免空数据）
							mPositionAdapter.notifyItemRemoved(position);
							showToast("删除位置成功：" + deletePos.getMemo());
							LogUtils.d(TAG, "删除位置完成：ID=" + deletePos.getPositionId() + "（服务+缓存已同步）");
						}
					}
				});

            // 4. 设置保存回调（保存时同步服务+本地缓存+Adapter）
            mPositionAdapter.setOnSavePositionClickListener(new PositionAdapter.OnSavePositionClickListener() {
					@Override
					public void onSavePositionClick(int position, PositionModel updatedPos) {
						// 安全校验（索引有效+服务绑定+数据非空）
						if (!isServiceBound.get() || mMainService == null 
							|| position < 0 || position >= mLocalPosCache.size() || updatedPos == null) {
							LogUtils.w(TAG, "保存位置失败：服务未就绪/索引无效/数据空");
							showToast("服务未就绪，保存失败");
							return;
						}

						// 步骤1：调用服务更新（确保服务数据一致性）
						mMainService.updatePosition(updatedPos);
						// 步骤2：更新本地缓存（确保缓存与服务同步）
						synchronized (mLocalPosCache) {
							mLocalPosCache.set(position, updatedPos);
						}
						// 步骤3：通知Adapter刷新（基于缓存操作，避免空数据）
						mPositionAdapter.notifyItemChanged(position);
						showToast("保存位置成功：" + updatedPos.getMemo());
						LogUtils.d(TAG, "保存位置完成：ID=" + updatedPos.getPositionId() + "（服务+缓存已同步）");
					}
				});

            // 5. 设置Adapter到RecyclerView（最后一步，确保Adapter已配置完成）
            mRvPosition.setAdapter(mPositionAdapter);
            // 6. 标记Adapter已初始化（避免重复初始化）
            isAdapterInited.set(true);
            LogUtils.d(TAG, "PositionAdapter初始化完成（基于本地缓存，数据量=" + mLocalPosCache.size() + "）");

        } catch (Exception e) {
            LogUtils.d(TAG, "Adapter初始化失败：" + e.getMessage());
            isAdapterInited.set(false);
            mPositionAdapter = null;
            showToast("位置列表初始化失败，请重试");
        }
    }

    /**
     * 显示Toast（Java 7 显式Toast.makeText，避免空Context）
     */
    private void showToast(String content) {
        if (isFinishing() || isDestroyed()) { // 避免Activity销毁后弹Toast崩溃
            LogUtils.w(TAG, "Activity已销毁，跳过Toast：" + content);
            return;
        }
        Toast.makeText(this, content, Toast.LENGTH_SHORT).show();
    }

	// ---------------------- 页面交互（新增位置逻辑保留，适配GPS数据） ----------------------
    /**
     * 新增位置（调用服务addPosition()，可选：用当前GPS位置初始化新位置）
     */
    public void addNewPosition(View view) {
        // 1. 隐藏软键盘（避免软键盘遮挡操作）
        InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
        if (imm != null && getCurrentFocus() != null) {
            imm.hideSoftInputFromWindow(getCurrentFocus().getWindowToken(), 0);
        }

        // 2. 安全校验（服务未绑定，不允许新增）
        if (!isServiceBound.get() || mMainService == null) {
            LogUtils.w(TAG, "新增位置失败：MainService未绑定");
            showToast("服务未就绪，无法新增位置");
            return;
        }

        // 3. 创建新位置模型（优化：优先用当前GPS位置初始化，无则用默认值）
        PositionModel newPos = new PositionModel();
        newPos.setPositionId(PositionModel.genPositionId()); // 生成唯一ID（需PositionModel实现）
        if (mCurrentGpsPos != null) {
            newPos.setLongitude(mCurrentGpsPos.getLongitude());
            newPos.setLatitude(mCurrentGpsPos.getLatitude());
            newPos.setMemo("当前GPS位置（可编辑）");
        } else {
            newPos.setLongitude(116.404267); // 北京经度（默认值）
            newPos.setLatitude(39.915119);  // 北京纬度（默认值）
            newPos.setMemo("默认位置（可编辑备注）");
        }
        newPos.setIsSimpleView(true);   // 默认简单视图
        newPos.setIsEnableRealPositionDistance(true); // 启用距离计算（依赖GPS）

        // 4. 调用服务新增+同步本地缓存（确保缓存与服务一致）
        mMainService.addPosition(newPos);
        synchronized (mLocalPosCache) {
            mLocalPosCache.add(newPos);
        }
        LogUtils.d(TAG, "通过服务新增位置：ID=" + newPos.getPositionId() + "，纬度=" + newPos.getLatitude() + "（缓存已同步）");

        // 5. 刷新Adapter（基于缓存操作，确保数据立即显示）
        if (isAdapterInited.get() && mPositionAdapter != null) {
            mPositionAdapter.notifyItemInserted(mLocalPosCache.size() - 1);
        }
        showToast("新增位置成功（已启用GPS距离计算）");
    }

	// ---------------------- 新增：GPS监听初始化+注册/反注册（核心适配逻辑） ----------------------
    /**
     * 初始化GPS监听：实现MainService.GpsUpdateListener，接收实时GPS数据
     */
    private void initGpsUpdateListener() {
        LogUtils.d(TAG, "initGpsUpdateListener()");
        mGpsUpdateListener = new MainService.GpsUpdateListener() {
            @Override
            public void onGpsPositionUpdated(PositionModel currentGpsPos) {
                if (currentGpsPos == null || isFinishing() || isDestroyed()) {
                    LogUtils.w(TAG, "GPS位置更新：数据为空或Activity已销毁");
                    return;
                }
                // 缓存当前GPS位置（供页面其他逻辑使用）
                mCurrentGpsPos = currentGpsPos;
                LogUtils.d(TAG, String.format("收到GPS更新：纬度=%.4f，经度=%.4f"
                                              , currentGpsPos.getLatitude(), currentGpsPos.getLongitude()));
                // 安全更新UI（避免Activity销毁后操作视图崩溃）
                ((TextView)findViewById(R.id.tv_latitude)).setText(String.format("当前纬度：%f", currentGpsPos.getLatitude()));
                ((TextView)findViewById(R.id.tv_longitude)).setText(String.format("当前经度：%f", currentGpsPos.getLongitude()));
            }

            @Override
            public void onGpsStatusChanged(String status) {
                if (status == null || isFinishing() || isDestroyed()) return;
                LogUtils.d(TAG, "GPS状态变化：" + status);
                if (status.contains("未开启") || status.contains("权限") || status.contains("失败")) {
                    ToastUtils.show("GPS提示：" + status);
                }
            }
        };
    }

	/**
     * 注册GPS监听：调用MainService的PUBLIC方法，绑定监听
     */
    private void registerGpsListener() {
        // 安全校验（避免Activity销毁/服务未绑定/监听为空时注册）
        if (isFinishing() || isDestroyed() || !isServiceBound.get() || mMainService == null || mGpsUpdateListener == null) {
            LogUtils.w(TAG, "GPS监听注册跳过：Activity状态异常/依赖未就绪");
            return;
        }
        try {
            mMainService.registerGpsUpdateListener(mGpsUpdateListener);
            LogUtils.d(TAG, "GPS监听已注册");
        } catch (Exception e) {
            LogUtils.d(TAG, "GPS监听注册失败：" + e.getMessage());
        }
    }

    /**
     * 反注册GPS监听：调用MainService的PUBLIC方法，解绑监听（核心防内存泄漏+数据异常）
     */
    private void unregisterGpsListener() {
        // 避免Activity销毁后调用服务方法（防止空指针/服务已解绑）
        if (mMainService == null || mGpsUpdateListener == null) {
            LogUtils.w(TAG, "GPS监听反注册跳过：服务/监听未初始化");
            return;
        }
        try {
            mMainService.unregisterGpsUpdateListener(mGpsUpdateListener);
            LogUtils.d(TAG, "GPS监听已反注册");
        } catch (Exception e) {
            LogUtils.d(TAG, "GPS监听反注册失败：" + e.getMessage());
        }
    }

    /**
     * 页面可见时同步数据（解决快速切回时数据未更新问题）
     * 场景：快速关闭再打开Activity，服务已绑定但数据未重新同步
     */
    @Override
    protected void onResume() {
        super.onResume();
        // 1. 服务已绑定但Adapter未初始化：重新同步数据+初始化Adapter
        if (isServiceBound.get() && mMainService != null && !isAdapterInited.get()) {
            LogUtils.d(TAG, "onResume：服务已绑定但Adapter未初始化，重新同步数据");
            syncDataFromMainService();
            initPositionAdapter();
        } else if (isServiceBound.get() && mMainService != null && isAdapterInited.get() && mPositionAdapter != null) {
            syncDataFromMainService();
            mPositionAdapter.notifyDataSetChanged();
            LogUtils.d(TAG, "onResume：刷新位置数据（与服务同步）");
        }
    }

    /**
     * 页面不可见时暂停操作（避免后台操作导致数据异常）
     */
    @Override
    protected void onPause() {
        super.onPause();
        // 避免后台时仍执行UI刷新（如GPS更新触发的视图操作）
        LogUtils.d(TAG, "onPause：页面不可见，暂停UI相关操作");
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        LogUtils.d(TAG, "onDestroy：开始释放资源");

        // 1. 反注册GPS监听（优先执行，避免服务持有Activity引用导致内存泄漏）
        unregisterGpsListener();

        // 2. 释放Adapter资源（反注册可能的监听，避免内存泄漏）
        if (mPositionAdapter != null) {
            mPositionAdapter.release();
            mPositionAdapter = null; // 清空引用，帮助GC回收
            LogUtils.d(TAG, "Adapter资源已释放");
        }

        // 3. 解绑MainService（最后执行，确保其他资源已释放）
        if (isServiceBound.get()) {
            try {
                unbindService(mServiceConnection);
                LogUtils.d(TAG, "MainService解绑完成");
            } catch (IllegalArgumentException e) {
                // 捕获“服务未绑定”异常（快速开关时可能出现，避免崩溃）
                LogUtils.d(TAG, "解绑MainService失败：服务未绑定（可能已提前解绑）");
            }
            // 重置绑定状态+服务引用
            isServiceBound.set(false);
            mMainService = null;
        }

        // 4. 清空本地缓存+GPS引用（帮助GC回收）
        synchronized (mLocalPosCache) {
            mLocalPosCache.clear();
        }
        mCurrentGpsPos = null;
        mGpsUpdateListener = null;
        isAdapterInited.set(false);
        LogUtils.d(TAG, "所有资源释放完成（onDestroy执行结束）");
    }

    // ---------------------- 移除重复定义：LocalBinder 统一在 MainService 中定义 ----------------------
    // 说明：原LocationActivity中的LocalBinder是重复定义（MainService已实现），会导致类型强转失败
    // 此处删除该类，确保Activity绑定服务时强转的是MainService中的LocalBinder
}


