measure_data_helper.dart 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426
  1. // ignore_for_file: constant_identifier_names
  2. import 'dart:convert';
  3. import 'package:fis_common/logger/logger.dart';
  4. import 'package:fis_jsonrpc/rpc.dart';
  5. import 'package:fis_measure/process/workspace/measure_handler.dart';
  6. import 'package:fis_measure/process/workspace/rpc_bridge.dart';
  7. import 'package:fis_i18n/i18n.dart';
  8. import 'package:flutter/foundation.dart';
  9. class MeasureDataHelper {
  10. // static VidImageSource source = VidImageSource.Remedical;
  11. static get source => RPCBridge.ins.source;
  12. // 获取图像列表
  13. static Future<List<RemedicalItemList>> getRemedicalList(
  14. String patientCode, String recordCode) async {
  15. try {
  16. // 初始化为空列表
  17. List<RemedicalItemList> remedicalItems = [];
  18. // 当数据来源是 Consultation 时
  19. if (source == VidImageSource.Consultation) {
  20. // 获取咨询图片
  21. var images = await getConsultationImages(recordCode);
  22. // 遍历图片列表,将非空的 imageInfos 添加到 remedicalItems 中
  23. images.forEach((imageInfo) {
  24. var imageInfos = imageInfo.ultrasoundImageList ?? [];
  25. if (imageInfos.isNotEmpty) {
  26. remedicalItems.add(RemedicalItemList(
  27. remedicalList: imageInfos,
  28. ));
  29. }
  30. });
  31. }
  32. // 当数据来源是 Laboratory 时
  33. else if (source == VidImageSource.Laboratory) {
  34. // 获取患者的文件列表
  35. var getRecordsPage =
  36. await RPCBridge.ins.rpc.lab.getFileListByFolderAsync(
  37. GetFileListByFolderRequest(
  38. token: RPCBridge.ins.userToken,
  39. pageIndex: 1,
  40. pageSize: 100,
  41. folderCode: patientCode,
  42. ),
  43. );
  44. remedicalItems.add(RemedicalItemList(
  45. remedicalList: getRecordsPage.pageData,
  46. ));
  47. }
  48. // 当数据来源为ai结果编辑的
  49. else if (source == VidImageSource.AiResultModifier) {
  50. var result =
  51. await RPCBridge.ins.rpc.remedical.getPatientAISelectedInfosAsync(
  52. GetPatientAISelectedInfosRequest(
  53. token: RPCBridge.ins.userToken,
  54. recordCode: recordCode,
  55. ),
  56. );
  57. List<RemedicalInfoDTO> remedicalInfoList = [];
  58. result.forEach((element) {
  59. remedicalInfoList.add(RemedicalInfoDTO(
  60. recordCode: element.recordCode,
  61. remedicalCode: element.remedicalAISelectedInfoCode,
  62. terminalImages: TerminalImageDTO(
  63. previewUrl: element.previewFileToken,
  64. imageUrl: element.cdnFileToken,
  65. coverImageUrl: element.previewFileToken,
  66. originImageUrl: element.orginalFileToken,
  67. recommendedDownloadMode: element.recommendedDownloadMode,
  68. ),
  69. diagnosisConclusion: element.diagnosisConclusion,
  70. diagnosisOrgans: element.diagnosisOrgans,
  71. ));
  72. });
  73. remedicalItems.add(RemedicalItemList(
  74. remedicalList: remedicalInfoList,
  75. ));
  76. } else if (source == VidImageSource.RemoteUS) {
  77. // 获取患者的病历记录
  78. PageResult<RemedicalListResult> result =
  79. PageResult<RemedicalListResult>();
  80. result.pageData = [];
  81. try {
  82. result = await RPCBridge.ins.rpc.remoteUltrasound
  83. .vitalGetRemedicalListPagesAsync(
  84. GetRecordsPageRequest(
  85. token: RPCBridge.ins.userToken,
  86. pageIndex: 1,
  87. pageSize: 100,
  88. patientCode: patientCode,
  89. ),
  90. );
  91. } catch (e) {
  92. logger.e('MeasureDataHelper vitalGetRemedicalListPagesAsync ex:$e');
  93. }
  94. // 遍历病历记录列表,当某条记录的 recordCode 与传入的 recordCode 相同时,将其 remedicalItemList 添加到 remedicalItems 中
  95. if (result.pageData!.isNotEmpty) {
  96. var recordInfo = result.pageData!.firstWhere(
  97. (element) => element.recordCode == recordCode,
  98. orElse: () => RemedicalListResult());
  99. remedicalItems = recordInfo.remedicalItemList ?? [];
  100. }
  101. }
  102. // 当数据来源为其他情况时
  103. else {
  104. // 获取患者的病历记录
  105. PageResult<RemedicalListResult> result =
  106. PageResult<RemedicalListResult>();
  107. result.pageData = [];
  108. try {
  109. result = await RPCBridge.ins.rpc.remedical.getRemedicalListPagesAsync(
  110. GetRecordsPageRequest(
  111. token: RPCBridge.ins.userToken,
  112. pageIndex: 1,
  113. pageSize: 100,
  114. patientCode: patientCode,
  115. ),
  116. );
  117. } catch (e) {
  118. logger.e('MeasureDataHelper getRemedicalListPagesAsync ex:$e');
  119. }
  120. // 遍历病历记录列表,当某条记录的 recordCode 与传入的 recordCode 相同时,将其 remedicalItemList 添加到 remedicalItems 中
  121. if (result.pageData!.isNotEmpty) {
  122. var recordInfo = result.pageData!.firstWhere(
  123. (element) => element.recordCode == recordCode,
  124. orElse: () => RemedicalListResult());
  125. remedicalItems = recordInfo.remedicalItemList ?? [];
  126. }
  127. }
  128. // 返回最终的 remedicalItems 列表
  129. return remedicalItems;
  130. } catch (e) {
  131. logger.e('MeasureHomeController getRemedicalList ex:', e);
  132. // 出现异常时返回空列表
  133. return [];
  134. }
  135. }
  136. ///获取会诊图像
  137. static Future<List<ConsultationImagesDTO>> getConsultationImages(
  138. String consultationCode) async {
  139. try {
  140. if (consultationCode.isEmpty) {
  141. return [];
  142. }
  143. var realTimeConsultationImageList =
  144. await RPCBridge.ins.rpc.liveConsultation.getConsultationFilesAsync(
  145. FindConsultationDetailRequest(
  146. consultationCode: consultationCode, token: RPCBridge.ins.userToken),
  147. );
  148. return realTimeConsultationImageList;
  149. } catch (e) {
  150. logger.e('RealTimeConsultationImageController getConsultationImages ex:' +
  151. e.toString());
  152. }
  153. return [];
  154. }
  155. ///获取图像详情
  156. static Future<RemedicalInfoDTO?> getImageInfo(
  157. String remedicalCode,
  158. String? remedicalAISelectedInfoCode,
  159. ) async {
  160. try {
  161. RemedicalInfoDTO result;
  162. print(source);
  163. if (source == VidImageSource.AiResultModifier) {
  164. final remedicalAISelectedInfo =
  165. await RPCBridge.ins.rpc.remedical.getRemedicalAISelectedInfoAsync(
  166. GetRemedicalAISelectedInfoRequest(
  167. token: RPCBridge.ins.userToken,
  168. code: remedicalAISelectedInfoCode,
  169. ),
  170. );
  171. result = RemedicalInfoDTO(
  172. diagnosisResult: jsonEncode(
  173. [
  174. {
  175. 'DiagResultsForEachOrgan':
  176. jsonDecode(remedicalAISelectedInfo.diagnosisData ?? '')[
  177. 'DiagResultsForEachOrgan'],
  178. 'Index': jsonDecode(
  179. remedicalAISelectedInfo.diagnosisData ?? '')['Index'],
  180. 'PriorityScore':
  181. jsonDecode(remedicalAISelectedInfo.diagnosisData ?? '')[
  182. 'PriorityScore'],
  183. }
  184. ],
  185. ),
  186. terminalImages: TerminalImageDTO(
  187. previewUrl: remedicalAISelectedInfo.previewFileToken,
  188. imageUrl: remedicalAISelectedInfo.cdnFileToken,
  189. coverImageUrl: remedicalAISelectedInfo.previewFileToken,
  190. originImageUrl: remedicalAISelectedInfo.orginalFileToken,
  191. recommendedDownloadMode:
  192. remedicalAISelectedInfo.recommendedDownloadMode,
  193. ),
  194. diagnosisConclusion: DiagnosisConclusionEnum.Benign,
  195. );
  196. } else if (source == VidImageSource.RemoteUS) {
  197. result = await RPCBridge.ins.rpc.remoteUltrasound
  198. .vitalFindRemedicalByCodeAsync(
  199. FindRemedicalByCodeRequest(
  200. token: RPCBridge.ins.userToken,
  201. remedicalCode: remedicalCode,
  202. existDiagnosisResult: true,
  203. ),
  204. );
  205. } else {
  206. result = await RPCBridge.ins.rpc.remedical.findRemedicalByCodeAsync(
  207. FindRemedicalByCodeRequest(
  208. token: RPCBridge.ins.userToken,
  209. remedicalCode: remedicalCode,
  210. existDiagnosisResult: true,
  211. ),
  212. );
  213. }
  214. return result;
  215. } catch (e) {
  216. logger.e('MeasureHomeController getRemedicalInfo ex:', e);
  217. return null;
  218. }
  219. }
  220. ///获取测量项
  221. static Future<MeasureApplicationDTO?> getMeasureApplication(
  222. MeasureModeSelection args) async {
  223. try {
  224. return await RPCBridge.ins.rpc.remoteUltrasound
  225. .vitalGetMeasureApplicationAsync(
  226. GetMeasureApplicationRequest(
  227. token: RPCBridge.ins.userToken,
  228. applicationName: args.applicationName,
  229. categoryName: args.categoryName,
  230. measureModes: args.measureModes,
  231. ),
  232. );
  233. } catch (e) {
  234. print(e);
  235. logger.e('MeasureHomeController getMeasureApplication ex: ', e);
  236. return null;
  237. }
  238. }
  239. /// 保存测量的方法
  240. static Future<bool> saveUserDefinedMeasureApplicationAsync(
  241. MeasureModeSubmit args) async {
  242. var result = false;
  243. try {
  244. result = await RPCBridge.ins.rpc.remedical
  245. .saveUserDefinedMeasureApplicationAsync(
  246. SaveUserDefinedMeasureApplicationRequest(
  247. token: RPCBridge.ins.userToken,
  248. version: args.version,
  249. applicationName: args.applicationName,
  250. categoryName: args.categoryName,
  251. workingMode: args.workingMode,
  252. ),
  253. );
  254. } catch (e) {
  255. logger.e(
  256. 'MeasureHomeController saveUserDefinedMeasureApplicationAsync ex: ',
  257. e);
  258. }
  259. return result;
  260. }
  261. /// 保存样式
  262. static Future<void> saveMeasureSystemSettingAsync(
  263. MeasureSystemSettingDTO measureSystemSetting,
  264. ) async {
  265. await RPCBridge.ins.rpc.remedical.saveMeasureSystemSettingAsync(
  266. SaveMeasureSystemSettingRequest(
  267. systemSetting: measureSystemSetting,
  268. token: RPCBridge.ins.userToken,
  269. ),
  270. );
  271. }
  272. /// 获取样式
  273. static Future<MeasureSystemSettingDTO> getMeasureSystemSettingAsync() async {
  274. final result = await RPCBridge.ins.rpc.remoteUltrasound
  275. .vitalGetMeasureSystemSettingAsync(
  276. GetMeasureSystemSettingRequest(
  277. token: RPCBridge.ins.userToken,
  278. ),
  279. );
  280. return result;
  281. }
  282. /// 分享vid
  283. static Future<String> shareImage(
  284. String examFile,
  285. ) async {
  286. try {
  287. final result = await RPCBridge.ins.rpc.remedical.queryShareExamPageAsync(
  288. QueryShareExamPageRequest(
  289. examFileToken: examFile,
  290. token: RPCBridge.ins.userToken,
  291. languageCode: i18nBook.locale.toCodeString('-'),
  292. ),
  293. );
  294. return result.shareExamPageUrl ?? '';
  295. } catch (e) {
  296. logger.e("queryShareExamPageAsync exception:", e);
  297. }
  298. return '';
  299. }
  300. /// 获取注释
  301. static Future<CommentItemResultDTO?> getCommentsByApplicationAsync(
  302. String applicationName, String categoryName) async {
  303. try {
  304. if (RPCBridge.ins.source == VidImageSource.RemoteUS) {
  305. final result = await RPCBridge.ins.rpc.remoteUltrasound
  306. .vitalGetCommentsByApplicationAsync(
  307. GetCommentsByApplicationRequest(
  308. token: RPCBridge.ins.userToken,
  309. applicationName: applicationName,
  310. categoryName: categoryName,
  311. languageCode: i18nBook.locale.toCodeString('-'),
  312. ),
  313. );
  314. return result;
  315. } else {
  316. final result =
  317. await RPCBridge.ins.rpc.remedical.getCommentsByApplicationAsync(
  318. GetCommentsByApplicationRequest(
  319. token: RPCBridge.ins.userToken,
  320. applicationName: applicationName,
  321. categoryName: categoryName,
  322. languageCode: i18nBook.locale.toCodeString('-'),
  323. ),
  324. );
  325. return result;
  326. }
  327. } catch (e) {
  328. logger.e('MeasureHomeController getCommentsByApplicationAsync ex: ', e);
  329. return null;
  330. }
  331. }
  332. /// 保存注释
  333. static Future<bool?> saveUserDefinedCommentsAsync(
  334. String applicationName,
  335. String categoryName,
  336. List<CommentItemDTO>? addCommentItems,
  337. List<CommentItemDTO>? deleteCommentItems,
  338. List<UpdateCommentItemDTO>? updateCommentItems,
  339. ) async {
  340. try {
  341. final result =
  342. await RPCBridge.ins.rpc.remedical.saveUserDefinedCommentsAsync(
  343. SaveUserDefinedCommentsRequest(
  344. token: RPCBridge.ins.userToken,
  345. applicationName: applicationName,
  346. categoryName: categoryName,
  347. languageCode: i18nBook.locale.toCodeString('-'),
  348. // Store.app.systemLocale.languageCode.toLowerCase(),
  349. addCommentItems: addCommentItems,
  350. deletedCommentItems: deleteCommentItems,
  351. updateCommentItems: updateCommentItems),
  352. );
  353. return result;
  354. } catch (e) {
  355. logger.e('MeasureHomeController getCommentsByApplicationAsync ex: ', e);
  356. return null;
  357. }
  358. }
  359. /// 重置注释
  360. static Future<bool?> resetUserCommentsAsync(
  361. String applicationName,
  362. String categoryName,
  363. ) async {
  364. try {
  365. final result = await RPCBridge.ins.rpc.remedical.resetUserCommentsAsync(
  366. ResetUserCommentsRequest(
  367. token: RPCBridge.ins.userToken,
  368. applicationName: applicationName,
  369. categoryName: categoryName,
  370. ),
  371. );
  372. return result;
  373. } catch (e) {
  374. logger.e('MeasureHomeController resetUserCommentsAsync ex: ', e);
  375. return null;
  376. }
  377. }
  378. /// 获取预置的注释项
  379. static Future<PresetCommentItemResultDTO?> getPresetCommentsAsync() async {
  380. try {
  381. final result = await RPCBridge.ins.rpc.remedical.getPresetCommentsAsync(
  382. GetPresetCommentsRequest(
  383. token: RPCBridge.ins.userToken,
  384. languageCode: i18nBook.locale.toCodeString('-'),
  385. // Store.app.systemLocale.languageCode.toLowerCase(),
  386. ),
  387. );
  388. return result;
  389. } catch (e) {
  390. logger.e('MeasureHomeController getPresetCommentsAsync ex: ', e);
  391. return null;
  392. }
  393. }
  394. static Future<RemedicalInfoDTO?> getImageInfoByIndex(
  395. String recordCode, String token, String patientCode, int index) async {
  396. var imageList = await getRemedicalList(patientCode, recordCode);
  397. int imageIndex = 0;
  398. for (RemedicalItemList r in imageList) {
  399. for (RemedicalInfoDTO i in r.remedicalList ?? []) {
  400. imageIndex++;
  401. if (imageIndex == index) {
  402. return i;
  403. }
  404. }
  405. }
  406. return null;
  407. }
  408. }