score_service.py 9.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167
  1. import cv2
  2. from app.core.config import settings
  3. from app.core.logger import get_logger
  4. from app.services.defect_service import DefectInferenceService
  5. from app.services.card_rectify_and_center import CardRectifyAndCenter
  6. from app.utils.score_inference.CardScorer import CardScorer
  7. import numpy as np
  8. import json
  9. logger = get_logger(__name__)
  10. class ScoreService:
  11. def __init__(self):
  12. self.scoring_config_path = settings.SCORE_CONFIG_PATH
  13. self.card_scorer = CardScorer(config_path=self.scoring_config_path)
  14. self.defect_service = DefectInferenceService()
  15. self.rectify_center_service = CardRectifyAndCenter()
  16. def score_inference(self, score_type: str, is_reflect_card: bool,
  17. img_bgr: np.ndarray) -> dict:
  18. logger.info("开始进行卡片居中和转正")
  19. img_bgr = self.rectify_center_service.rectify_and_center(img_bgr)
  20. imageHeight, imageWidth = img_bgr.shape[:2]
  21. logger.info("开始进行卡片分数推理")
  22. if score_type == 'front_ring' or score_type == 'front_coaxial':
  23. center_data = self.defect_service.defect_inference("pokemon_front_card_center", img_bgr.copy())
  24. else:
  25. center_data = self.defect_service.defect_inference("pokemon_back_card_center", img_bgr.copy())
  26. if is_reflect_card:
  27. if score_type == 'front_ring':
  28. defect_data = self.defect_service.defect_inference('pokemon_front_face_reflect_ring_light_defect',
  29. img_bgr.copy())
  30. elif score_type == 'front_coaxial':
  31. defect_data = self.defect_service.defect_inference('pokemon_front_face_reflect_coaxial_light_defect',
  32. img_bgr.copy())
  33. elif score_type == 'back_ring':
  34. defect_data = self.defect_service.defect_inference('pokemon_back_face_ring_light_defect',
  35. img_bgr.copy())
  36. elif score_type == 'back_coaxial':
  37. defect_data = self.defect_service.defect_inference('pokemon_back_face_coaxial_light_defect',
  38. img_bgr.copy())
  39. else:
  40. return {}
  41. else:
  42. if score_type == 'front_ring':
  43. defect_data = self.defect_service.defect_inference('pokemon_front_face_no_reflect_ring_light_defect',
  44. img_bgr.copy())
  45. elif score_type == 'front_coaxial':
  46. defect_data = self.defect_service.defect_inference('pokemon_front_face_no_reflect_coaxial_light_defect',
  47. img_bgr.copy())
  48. elif score_type == 'back_ring':
  49. defect_data = self.defect_service.defect_inference('pokemon_back_face_ring_light_defect',
  50. img_bgr.copy())
  51. elif score_type == 'back_coaxial':
  52. defect_data = self.defect_service.defect_inference('pokemon_back_face_coaxial_light_defect',
  53. img_bgr.copy())
  54. else:
  55. return {}
  56. logger.info("模型推理结束, 开始计算分数")
  57. if score_type == 'front_ring' or score_type == 'front_coaxial':
  58. card_aspect = "front"
  59. else:
  60. card_aspect = "back"
  61. if score_type == 'front_ring' or score_type == 'back_ring':
  62. card_light_type = "ring"
  63. else:
  64. card_light_type = "coaxial"
  65. if card_light_type == 'ring':
  66. center_score_data = self.card_scorer.calculate_centering_score(card_aspect, center_data, True)
  67. # 计算角, 边, 面的分数, 会把分数写入json, 然后传入刚写好的, 继续写边的分数
  68. defect_data = self.card_scorer.calculate_defect_score('corner', card_aspect, card_light_type,
  69. defect_data, True)
  70. defect_data = self.card_scorer.calculate_defect_score('edge', card_aspect, card_light_type,
  71. defect_data, True)
  72. defect_score_data = self.card_scorer.calculate_defect_score('face', card_aspect, card_light_type,
  73. defect_data, True)
  74. elif card_light_type == 'coaxial':
  75. # 居中
  76. center_score_data = {}
  77. # 同轴光照片只计算面缺陷
  78. defect_score_data = self.card_scorer.calculate_defect_score('face', card_aspect, card_light_type,
  79. defect_data, True)
  80. else:
  81. return {}
  82. result_json = self.card_scorer.formate_one_card_result(center_score_data, defect_score_data,
  83. card_light_type=card_light_type,
  84. card_aspect=card_aspect,
  85. imageHeight=imageHeight,
  86. imageWidth=imageWidth)
  87. temp_score_json_path = settings.TEMP_WORK_DIR / f'{score_type}_score.json'
  88. with open(temp_score_json_path, 'w', encoding='utf-8') as f:
  89. json.dump(result_json, f, ensure_ascii=False, indent=2)
  90. logger.info("分数推理完成 ")
  91. return result_json
  92. def recalculate_defect_score(self, score_type: str, json_data: dict):
  93. center_json_data = json_data["result"]['center_result']
  94. defect_json_data = json_data["result"]['defect_result']
  95. imageHeight = json_data["result"].get('imageHeight', 0)
  96. imageWidth = json_data["result"].get('imageWidth', 0)
  97. # 正反面类型分类
  98. if score_type == 'front_ring' or score_type == 'front_coaxial':
  99. card_aspect = "front"
  100. else:
  101. card_aspect = "back"
  102. if score_type == 'front_ring' or score_type == 'back_ring':
  103. card_light_type = "ring"
  104. else:
  105. card_light_type = "coaxial"
  106. logger.info("开始进行缺陷信息重计算")
  107. defect_data = self.defect_service.re_inference_from_json(card_light_type=card_light_type,
  108. center_json=center_json_data,
  109. defect_json=defect_json_data)
  110. logger.info("开始重新计算分数")
  111. if card_light_type == 'ring':
  112. logger.info("开始进行居中信息重计算")
  113. center_data = self.defect_service.re_inference_from_json(card_light_type="center",
  114. center_json=center_json_data,
  115. defect_json=defect_json_data)
  116. center_score_data = self.card_scorer.calculate_centering_score(card_aspect, center_data, True)
  117. # 计算角, 边, 面的分数, 会把分数写入json, 然后传入刚写好的, 继续写边的分数
  118. logger.info("开始重新计算:边角面")
  119. defect_data = self.card_scorer.calculate_defect_score('corner', card_aspect, card_light_type,
  120. defect_data, True)
  121. defect_data = self.card_scorer.calculate_defect_score('edge', card_aspect, card_light_type,
  122. defect_data, True)
  123. defect_score_data = self.card_scorer.calculate_defect_score('face', card_aspect, card_light_type,
  124. defect_data, True)
  125. elif card_light_type == 'coaxial':
  126. # 居中
  127. center_score_data = {}
  128. # 同轴光照片只计算面缺陷
  129. logger.info("开始重新计算:面")
  130. defect_score_data = self.card_scorer.calculate_defect_score('face', card_aspect, card_light_type,
  131. defect_data, True)
  132. else:
  133. return {}
  134. result_json = self.card_scorer.formate_one_card_result(center_score_data, defect_score_data,
  135. card_light_type=card_light_type,
  136. card_aspect=card_aspect,
  137. imageHeight=imageHeight,
  138. imageWidth=imageWidth)
  139. temp_score_json_path = settings.TEMP_WORK_DIR / f're_{score_type}_score.json'
  140. with open(temp_score_json_path, 'w', encoding='utf-8') as f:
  141. json.dump(result_json, f, ensure_ascii=False, indent=2)
  142. logger.info("分数推理完成 ")
  143. return result_json