/** * 技师数据,统一访问入口 */ import { BaseData } from "./BaseData"; import { GirlBriefData } from "./GirlBriefData"; import { GirlDetailData } from "./GirlDetailData"; import { GirlUnlockData } from "./GirlUnlockData"; import { GirlChatData } from "./GirlChatData"; import { GirlFavorabilityData } from "./GirlFavorabilityData"; import { DataId } from "./DataManager"; import proto from "db://assets/Scripts/proto/proto.pb.js"; // 分类的数据结构 interface CategoryBucket { // 技师的简要数据 briefs: Map; // 技师的详细数据 details: Map; // 技师的解锁数据 unlocks: Map; // 技师的聊天数据 chats: Map; // 技师的好感度数据 favorability: Map; // 技师的id girlIds: number[]; } // 每日推荐专用分类 const DAILY_BUCKET = "__daily__"; export class GirlData extends BaseData { // 大分类 private _categories = new Map(); public reset(): void { this._categories.clear(); } public clear(): void { this._categories.clear(); } public destroy(): void { super.destroy(); this._categories = null; } /** 保障 _categories 存在 */ private ensureCategories(): Map { if (!this._categories) { this._categories = new Map(); } return this._categories; } /** 获取或创建分类桶 */ private ensureBucket(categoryId: string): CategoryBucket { const cats = this.ensureCategories(); let bucket = cats.get(categoryId); if (!bucket) { bucket = { briefs: new Map(), details: new Map(), unlocks: new Map(), chats: new Map(), favorability: new Map(), girlIds: [], }; cats.set(categoryId, bucket); } return bucket; } /** 取分类下的全部 girlIds(若分类不存在返回空数组) */ public getGirlIds(categoryId: string): number[] { const b = this.ensureCategories().get(categoryId); return b ? b.girlIds : []; } /** 保存技师列表 */ public setGirlList( categoryId: string, data: proto.cs.ICSGetGirlListRes ): void { if (!data) return; this.setGirlBrief(categoryId, data.girls); this.setGirlUnlock(categoryId, data.girls); this.setGirlFavorability(categoryId, data.girls); const bucket = this.ensureBucket(categoryId); console.log("保存类别 ", categoryId, " 的技师列表: ", bucket); } /** 保存技师详细数据 */ public setGirlDetailData( categoryId: string, data: proto.cs.ICSGetGirlDetailRes ): void { if (!data) return; let details = []; details.push(data.girl); this.setGirlBrief(categoryId, details); this.setGirlDetail(categoryId, details); this.setGirlUnlock(categoryId, details); this.setGirlChat(categoryId, details); this.setGirlFavorability(categoryId, details); const bucket = this.ensureBucket(categoryId); console.log("保存类别 ", categoryId, " 的详细数据: ", bucket); } /** --------------------------------------------------------- 技师的简要数据 --------------------------------------------------------- */ /** * 合并一个简要数据到指定分类;并维护 girlIds 顺序(去重追加) */ private mergeOneBrief(categoryId: string, data: proto.cs.IGirls): void { if (!data) return; const bucket = this.ensureBucket(categoryId); // 用一个临时 Set 保存已有的 id,加速去重 const existed = new Set(bucket.girlIds); let id = data.id; const one = this.parseOneGirlBrief(data); if (!one) return; bucket.briefs.set(id, one); if (!existed.has(id)) { bucket.girlIds.push(id); } } /** * 合并一批简要数据到指定分类;并维护 girlIds 顺序(去重追加) */ private mergeBriefs( categoryId: string, respOrList: proto.cs.IGirlData[] ): void { if (!respOrList) return; const bucket = this.ensureBucket(categoryId); // 用一个临时 Set 保存已有的 id,加速去重 const existed = new Set(bucket.girlIds); for (const g of respOrList) { const one = this.parseOneGirlBrief(g.girl); if (!one) continue; bucket.briefs.set(g.id, one); if (!existed.has(g.id)) { bucket.girlIds.push(g.id); existed.add(g.id); } } } private parseOneGirlBrief(data: proto.cs.IGirls): GirlBriefData | null { if (!data) return null; let oneData = new GirlBriefData(); oneData.init?.(DataId.GirlBrief); oneData.setData(data); return oneData; } /** 保存技师的简要数据 */ private setGirlBrief(categoryId: string, data: proto.cs.IGirlData[]): void { this.mergeBriefs(categoryId, data); } /** 取某分类 + girlId 的简要数据 */ private getGrilBrief( categoryId: string, girlId: number ): GirlBriefData | null { const b = this.ensureCategories().get(categoryId); if (!b) return null; return b.briefs.get(girlId) ?? null; } /** 获取名字键 */ public getGrilName(categoryId: string, girlId: number): string { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return ""; return oneData.getGrilName(); } /** 获取年龄 */ public getGrilAge(categoryId: string, girlId: number): string { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return "0"; return oneData.getGrilAge(); } /** 获取主题枚举 */ public getGrilCategory(categoryId: string, girlId: number): number { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilCategory(); } /** 获取标签键 */ public getGrilTagKey(categoryId: string, girlId: number): string { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return ""; return oneData.getGrilTagKey(); } /** 获取付费类型 */ public getGrilPriceType(categoryId: string, girlId: number): number { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilPriceType(); } /** 获取原来的价格,除100 */ public getGrilOriginalPrice(categoryId: string, girlId: number): number { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return 0; let price = oneData.getGrilPrice(); return price / 100; } /** 获取价格 */ public getGrilPrice(categoryId: string, girlId: number): number { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilPrice(); } /** 获取VIP能否解锁 */ public getGrilVipUnlock(categoryId: string, girlId: number): number { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilVipUnlock(); } /** 获取头像路径 */ public getGrilAvatar(categoryId: string, girlId: number): string { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return ""; return oneData.getGrilAvatar(); } /** 获取list头像路径 */ public getGrilListAvatar(categoryId: string, girlId: number): string { let oneData = this.getGrilBrief(categoryId, girlId); if (!oneData) return ""; return oneData.getGrilListAvatar(); } /** 获取主题枚举,根据 id */ public getGrilCategoryById(girlId: number): number { const cats = this.ensureCategories(); // 遍历 for (const bucket of cats.values()) { // 先查简要信息 const brief = bucket.briefs.get(girlId); if (brief) { return brief.getGrilCategory(); } } // 未找到 return 0; } /** --------------------------------------------------------- 技师的详细数据 --------------------------------------------------------- */ // 解析技师详细数据,一个 private parseOneGirlDetail( data: proto.cs.IGirlsDetail ): GirlDetailData | null { if (!data) return null; let oneData = new GirlDetailData(); oneData.init?.(DataId.GirlDetail); oneData.setData(data); return oneData; } /** 保存技师的详细数据 */ private setGirlDetail(categoryId: string, data: proto.cs.IGirlData[]): void { if (!data) return; const bucket = this.ensureBucket(categoryId); for (const g of data) { const one = this.parseOneGirlDetail(g.detail); if (!one) continue; bucket.details.set(g.id, one); } } /** 取某分类 + girlId 的详细数据 */ public getGrilDetail( categoryId: string, girlId: number ): GirlDetailData | null { const b = this.ensureCategories().get(categoryId); if (!b) return null; return b.details.get(girlId) ?? null; } /** 获取技师描述 */ public getGrilDesc(categoryId: string, girlId: number): string { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return ""; return oneData.getGirlDesc(); } /** 获取所有技师图片数据的数量 */ public getAllGrilPhotoDataCount(categoryId: string, girlId: number): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; return oneData.getAllGrilPhotoDataCount(); } /** 获取所有技师图片的id */ public getAllGrilPhotoId(categoryId: string, girlId: number): number[] { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return []; return oneData.getAllGrilPhotoId(); } /** 获取所有用来展示在列表的技师图片的id */ public getAllDisplayGrilPhotoId( categoryId: string, girlId: number ): number[] { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return []; // 所有id let allId = oneData.getAllGrilPhotoId(); // 总聊天次数 let chatTotalCount = this.getChatTotalCount(categoryId, girlId); // 用来展示的id let displayIds = []; for (let id of allId) { let unlockCounts = oneData.getGrilPhotoUnlockCounts(id); let price = oneData.getGrilPhotoPrice(id); if (price <= 0) { // 价格为0,代表免费 displayIds.push({ id: id }); } else { // 价格大于0,代表付费 let isUnlock = this.isImageUnlock(categoryId, girlId, id); if (isUnlock) { // 已经解锁 displayIds.push({ id: id }); } else { // 总聊天次数 大于等于 触发次数 if (chatTotalCount >= unlockCounts) { displayIds.push({ id: id }); } } } } return displayIds; } /** 获取第一个技师图片的资源路径 */ public getFirstGrilPhotoPath(categoryId: string, girlId: number): string { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return ""; // 第一个 id const ids = this.getAllGrilPhotoId(categoryId, girlId); const length = ids.length; if (length <= 0) return ""; // 返回数据 return oneData.getGrilPhotoPath(ids[0]); } /** 获取技师图片的类型 */ public getGrilPhotoType( categoryId: string, girlId: number, id: number ): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilPhotoType(id); } /** 获取技师图片的聊天触发次数 */ public getGrilPhotoUnlockCounts( categoryId: string, girlId: number, id: number ): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilPhotoUnlockCounts(id); } /** 获取技师图片的原来价格,除100 */ public getGrilPhotoOriginalPrice( categoryId: string, girlId: number, id: number ): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; let price = oneData.getGrilPhotoPrice(id); return price / 100; } /** 获取技师图片的价格 */ public getGrilPhotoPrice( categoryId: string, girlId: number, id: number ): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilPhotoPrice(id); } /** 获取技师图片的资源路径 */ public getGrilPhotoPic( categoryId: string, girlId: number, id: number ): string { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return ""; return oneData.getGrilPhotoPath(id); } /** 获取所有技师视频数据的数量 */ public getAllGrilVideoDataCount(categoryId: string, girlId: number): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; return oneData.getAllGrilVideoDataCount(); } /** 获取所有技师视频的id */ public getAllGrilVideoId(categoryId: string, girlId: number): number[] { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return []; return oneData.getAllGrilVideoId(); } /** 获取所有用来展示在列表的技师视频的id */ public getAllDisplayGrilVideoId( categoryId: string, girlId: number ): number[] { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return []; // 所有id let allId = oneData.getAllGrilVideoId(); // 用来展示的id let displayIds = []; for (let id of allId) { let price = oneData.getGrilVideoPrice(id); if (price <= 0) { // 价格为0,代表免费 displayIds.push(id); } else { // 价格大于0,代表付费 let isUnlock = this.isVideoUnlock(categoryId, girlId, id); if (isUnlock) { // 已经解锁 displayIds.push(id); } } } return displayIds; } /** 获取第一个技师视频的资源路径 */ public getFirstGrilVideoPath(categoryId: string, girlId: number): string { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return ""; // 第一个 id const ids = this.getAllGrilVideoId(categoryId, girlId); const length = ids.length; if (length <= 0) return ""; // 返回数据 return oneData.getGrilVideoPath(ids[0]); } /** 获取技师视频的资源路径 */ public getGrilVideoPath( categoryId: string, girlId: number, id: number ): string { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return ""; return oneData.getGrilVideoPath(id); } /** 获取技师视频的关联情绪 */ public getGrilVideoEmotion( categoryId: string, girlId: number, id: number ): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilVideoEmotion(id); } /** 获取技师视频的原来价格,除100 */ public getGrilVideoOriginalPrice( categoryId: string, girlId: number, id: number ): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; let price = oneData.getGrilVideoPrice(id); return price / 100; } /** 获取技师视频的价格 */ public getGrilVideoPrice( categoryId: string, girlId: number, id: number ): number { let oneData = this.getGrilDetail(categoryId, girlId); if (!oneData) return 0; return oneData.getGrilVideoPrice(id); } /** --------------------------------------------------------- 技师的解锁数据 --------------------------------------------------------- */ // 解析技师解锁数据,一个 private parseOneGirlUnlock(data: proto.cs.IGirlData): GirlUnlockData | null { if (!data) return null; let oneData = new GirlUnlockData(); oneData.init?.(DataId.GirlUnlock); oneData.setId(data.id); oneData.setIsRelease(data.isRelease); if (data.images) { let ids = []; for (let one of data.images) { ids.push(one.resId); } oneData.setUnlockedImageIds(ids); } if (data.videos) { let ids = []; for (let one of data.videos) { ids.push(one.resId); } oneData.setUnlockedVideoIds(ids); } return oneData; } /** 保存技师的解锁数据 */ private setGirlUnlock(categoryId: string, data: proto.cs.IGirlData[]): void { if (!data) return; const bucket = this.ensureBucket(categoryId); for (const g of data) { const one = this.parseOneGirlUnlock(g); if (!one) continue; bucket.unlocks.set(g.id, one); } } /** 取某分类 + girlId 的解锁数据 */ private getGrilUnlock( categoryId: string, girlId: number ): GirlUnlockData | null { const b = this.ensureCategories().get(categoryId); if (!b) return null; return b.unlocks.get(girlId) ?? null; } /** 获取 付费技师是否已经解锁 */ public getIsRelease(categoryId: string, girlId: number): boolean { let oneData = this.getGrilUnlock(categoryId, girlId); if (!oneData) return false; return oneData.getIsRelease(); } /** 保存 付费技师是否已经解锁 */ public setIsRelease( categoryId: string, girlId: number, value: boolean ): void { let oneData = this.getGrilUnlock(categoryId, girlId); if (!oneData) return; oneData.setIsRelease(value); } /** 判断图片是否解锁 */ public isImageUnlock( categoryId: string, girlId: number, id: number ): boolean { let oneData = this.getGrilUnlock(categoryId, girlId); if (!oneData) return false; return oneData.isImageUnlock(id); } /** 解锁图片 */ public unlockImage(categoryId: string, girlId: number, id: number): void { let oneData = this.getGrilUnlock(categoryId, girlId); if (!oneData) return; return oneData.unlockImage(id); } /** 获取所有解锁图片的 id */ public getUnlockedImageIds(categoryId: string, girlId: number): number[] { let oneData = this.getGrilUnlock(categoryId, girlId); if (!oneData) return []; return oneData.getUnlockedImageIds(); } /** 判断视频是否解锁 */ public isVideoUnlock( categoryId: string, girlId: number, id: number ): boolean { let oneData = this.getGrilUnlock(categoryId, girlId); if (!oneData) return false; return oneData.isVideoUnlock(id); } /** 解锁视频 */ public unlockVideo(categoryId: string, girlId: number, id: number): void { let oneData = this.getGrilUnlock(categoryId, girlId); if (!oneData) return; return oneData.unlockVideo(id); } /** 获取所有解锁视频的 id */ public getUnlockedVideoIds(categoryId: string, girlId: number): number[] { let oneData = this.getGrilUnlock(categoryId, girlId); if (!oneData) return []; return oneData.getUnlockedVideoIds(); } /** --------------------------------------------------------- 技师的聊天数据 --------------------------------------------------------- */ // 解析技师聊天数据,一个 private parseOneGirlChat(data: proto.cs.IGirlData): GirlChatData | null { if (!data) return null; let oneData = new GirlChatData(); oneData.init?.(DataId.GirlChat); oneData.setId(data.id); oneData.setChatTotalCount(data.chatTotalCount); oneData.setChatRemainCount(data.chatRemainCount); return oneData; } /** 保存技师的聊天数据 */ private setGirlChat(categoryId: string, data: proto.cs.IGirlData[]): void { if (!data) return; const bucket = this.ensureBucket(categoryId); for (const g of data) { const one = this.parseOneGirlChat(g); if (!one) continue; bucket.chats.set(g.id, one); } } /** 取某分类 + girlId 的聊天数据 */ private getGrilChat(categoryId: string, girlId: number): GirlChatData | null { const b = this.ensureCategories().get(categoryId); if (!b) return null; return b.chats.get(girlId) ?? null; } /** 获取总聊天次数 */ public getChatTotalCount(categoryId: string, girlId: number): number { let oneData = this.getGrilChat(categoryId, girlId); if (!oneData) return 0; return oneData.getChatTotalCount(); } /** 保存总聊天次数 */ public setChatTotalCount( categoryId: string, girlId: number, value: number ): void { let oneData = this.getGrilChat(categoryId, girlId); if (!oneData) return; return oneData.setChatTotalCount(value); } /** 获取剩余聊天次数 */ public getChatRemainCount(categoryId: string, girlId: number): number { let oneData = this.getGrilChat(categoryId, girlId); if (!oneData) return 0; return oneData.getChatRemainCount(); } /** 保存剩余聊天次数 */ public setChatRemainCount( categoryId: string, girlId: number, value: number ): void { let oneData = this.getGrilChat(categoryId, girlId); if (!oneData) return; return oneData.setChatRemainCount(value); } /** 更新剩余聊天次数 */ public useChat(categoryId: string, girlId: number, times: number = 1): void { let oneData = this.getGrilChat(categoryId, girlId); if (!oneData) return; return oneData.useChat(times); } /** --------------------------------------------------------- 技师的好感度数据 --------------------------------------------------------- */ // 解析技师好感度数据,一个 private parseOneGirlFavorability( data: proto.cs.IGirlData ): GirlFavorabilityData | null { if (!data) return null; let oneData = new GirlFavorabilityData(); oneData.init?.(DataId.GirlFavorability); oneData.setId(data.id); oneData.setStar(data.star); return oneData; } /** 保存技师的好感度数据 */ private setGirlFavorability( categoryId: string, data: proto.cs.IGirlData[] ): void { if (!data) return; const bucket = this.ensureBucket(categoryId); for (const g of data) { const one = this.parseOneGirlFavorability(g); if (!one) continue; bucket.favorability.set(g.id, one); } } /** 取某分类 + girlId 的好感度数据 */ private getGrilFavorability( categoryId: string, girlId: number ): GirlFavorabilityData | null { const b = this.ensureCategories().get(categoryId); if (!b) return null; return b.favorability.get(girlId) ?? null; } /** 获取星级 */ public getStar(categoryId: string, girlId: number): number { let oneData = this.getGrilFavorability(categoryId, girlId); if (!oneData) return 0; return oneData.getStar(); } /** --------------------------------------------------------- 每日推荐 --------------------------------------------------------- */ /** 保存每日推荐:放入特殊分类 DAILY_BUCKET,并维护 id 索引 */ public setDailyRecommend(data: proto.cs.ICSDailyRecommendRes): void { if (!data) return; this.mergeOneBrief(DAILY_BUCKET, data.girl); const bucket = this.ensureBucket(DAILY_BUCKET); console.log("保存每日推荐: ", bucket); } /** 获取推荐id */ public getRecommendGirlId(): number { const bucket = this.ensureBucket(DAILY_BUCKET); const girlIds = bucket.girlIds; const length = girlIds.length; if (length <= 0) return 0; return girlIds[length - 1]; } /** 获取每日推荐的简要数据 */ private getRecommendGrilBrief(): GirlBriefData | null { const recId = this.getRecommendGirlId(); if (recId <= 0) return null; const data = this.getGrilBrief(DAILY_BUCKET, recId); return data; } /** 获取名字 */ public getRecommendGrilName(): string { let oneData = this.getRecommendGrilBrief(); if (!oneData) return ""; return oneData.getGrilName(); } /** 获取头像路径 */ public getRecommendGrilAvatar(): string { let oneData = this.getRecommendGrilBrief(); if (!oneData) return ""; return oneData.getGrilAvatar(); } }