stgGclSubGatherFile.pas 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428
  1. unit stgGclSubGatherFile;
  2. // 导入导出汇总结果
  3. interface
  4. uses
  5. stgGclSubGatherFileDm, ADODB, sdDB, stgGclGatherDm, SysUtils, ProjectData,
  6. StageDm, mDataRecord, BillsTree, DetailExcelImport, OExport, stgGclImportHint;
  7. type
  8. TstgGclSubGatherFileHelper = class
  9. private
  10. FTempFile: string;
  11. FConnection: TADOConnection;
  12. FGatherData: TstgGclSubGatherData;
  13. public
  14. constructor Create;
  15. destructor Destroy; override;
  16. procedure Open(const AFileName: string);
  17. procedure Close;
  18. procedure SaveTo(const AFileName: string);
  19. property Connection: TADOConnection read FConnection;
  20. property GatherData: TstgGclSubGatherData read FGatherData;
  21. end;
  22. TstgGclSubGatherFileExportor = class(TstgGclSubGatherFileHelper)
  23. private
  24. procedure LoadMemoryRecord(ARec: TsdDataRecord);
  25. procedure LoadMemoryGatherData(AGatherData: TstgGclGatherData);
  26. public
  27. procedure ExportGatherDataTo(AGatherData: TstgGclGatherData; const AFileName: string);
  28. end;
  29. TstgGclSubGatherFileImportor = class(TstgGclSubGatherFileHelper)
  30. private
  31. FFails: TstgGclFailList;
  32. procedure ClearOldData(AStageData: TStageData);
  33. procedure ImportGatherData(AProjectData: TProjectData);
  34. public
  35. constructor Create;
  36. destructor Destroy; override;
  37. procedure ImportGatherDataTo(AProjectData: TProjectData; const AFileName: string);
  38. end;
  39. TstgGclSubGatherFileExcelImportor = class(TDetailExcelImport)
  40. private
  41. FCurRow: Integer;
  42. FB_CodeCol: Integer;
  43. FNameCol: Integer;
  44. FUnitsCol: Integer;
  45. FPriceCol: Integer;
  46. FDealQuantityCol: Integer;
  47. FFails: TstgGclFailList;
  48. procedure ClearOldData(AStageData: TStageData);
  49. function LoadColumnsFromHead(ASheet: TExportWorkSheet): Boolean;
  50. procedure LoadGatherData(ASheet: TExportWorkSheet);
  51. protected
  52. procedure BeginImport; override;
  53. procedure EndImport; override;
  54. procedure Import; override;
  55. public
  56. constructor Create(AProjectData: TProjectData); override;
  57. destructor Destroy; override;
  58. end;
  59. implementation
  60. uses
  61. UtilMethods, ZhAPI, Connections, stgGclTables, ScAutoUpdateUnit, Math,
  62. BillsMeasureDm, stgGclImportHintFrm;
  63. { TstgGclSubGatherFileExportor }
  64. procedure TstgGclSubGatherFileExportor.ExportGatherDataTo(
  65. AGatherData: TstgGclGatherData; const AFileName: string);
  66. begin
  67. Open(GetEmptyDataBaseFileName);
  68. try
  69. LoadMemoryGatherData(AGatherData);
  70. finally
  71. SaveTo(AFileName);
  72. end;
  73. end;
  74. procedure TstgGclSubGatherFileExportor.LoadMemoryRecord(ARec: TsdDataRecord);
  75. var
  76. vRec: TsdDataRecord;
  77. begin
  78. vRec := GatherData.sddBills.Add;
  79. vRec.ValueByName('B_Code').AsString := ARec.ValueByName('B_Code').AsString;
  80. vRec.ValueByName('Name').AsString := ARec.ValueByName('Name').AsString;
  81. vRec.ValueByName('Units').AsString := ARec.ValueByName('Units').AsString;
  82. vRec.ValueByName('Price').AsFloat := ARec.ValueByName('Price').AsFloat;
  83. vRec.ValueByName('DealQuantity').AsFloat := ARec.ValueByName('DealQuantity').AsFloat;
  84. vRec.ValueByName('DealTotalPrice').AsFloat := ARec.ValueByName('DealTotalPrice').AsFloat;
  85. vRec.ValueByName('QcQuantity').AsFloat := ARec.ValueByName('QcQuantity').AsFloat;
  86. vRec.ValueByName('QcTotalPrice').AsFloat := ARec.ValueByName('QcTotalPrice').AsFloat;
  87. vRec.ValueByName('QcBGLCode').AsString := ARec.ValueByName('QcBGLCode').AsString;
  88. vRec.ValueByName('QcBGLNum').AsString := ARec.ValueByName('QcBGLNum').AsString;
  89. end;
  90. procedure TstgGclSubGatherFileExportor.LoadMemoryGatherData(
  91. AGatherData: TstgGclGatherData);
  92. var
  93. i: Integer;
  94. vRec: TsdDataRecord;
  95. begin
  96. GatherData.sddBills.BeginUpdate;
  97. try
  98. for i := 0 to AGatherData.sddGatherGcl.RecordCount - 1 do
  99. begin
  100. vRec := AGatherData.sddGatherGcl.Records[i];
  101. LoadMemoryRecord(vRec);
  102. end;
  103. finally
  104. GatherData.sddBills.EndUpdate;
  105. end;
  106. end;
  107. { TstgGclSubGatherFileHelper }
  108. procedure TstgGclSubGatherFileHelper.Close;
  109. begin
  110. FConnection.Close;
  111. if FileExists(FTempFile) then
  112. DeleteFile(FTempFile);
  113. end;
  114. constructor TstgGclSubGatherFileHelper.Create;
  115. begin
  116. FConnection := TADOConnection.Create(nil);
  117. FConnection.LoginPrompt := False;
  118. FGatherData := TstgGclSubGatherData.Create(nil);
  119. end;
  120. destructor TstgGclSubGatherFileHelper.Destroy;
  121. begin
  122. Close;
  123. FGatherData.Free;
  124. FConnection.Free;
  125. inherited;
  126. end;
  127. procedure TstgGclSubGatherFileHelper.Open(const AFileName: string);
  128. procedure UpdateDataTables;
  129. var
  130. Updater: TScUpdater;
  131. begin
  132. Updater := TScUpdater.Create;
  133. try
  134. Updater.ForceUpdate := True;
  135. Updater.Open('', FConnection, '', '');
  136. Updater.AddTableDef(sStgGclBills, @tdStgGclBills, Length(tdStgGclBills), False, False);
  137. Updater.ExcuteUpdate;
  138. finally
  139. Updater.Free;
  140. end;
  141. end;
  142. begin
  143. FTempFile := GetTempFileName;
  144. CopyFileOrFolder(AFileName, FTempFile);
  145. FConnection.ConnectionString := Format(SAdoConnectStr, [FTempFile]);
  146. FConnection.Open;
  147. UpdateDataTables;
  148. GatherData.Open(FConnection);
  149. end;
  150. procedure TstgGclSubGatherFileHelper.SaveTo(const AFileName: string);
  151. begin
  152. FGatherData.Save;
  153. CopyFileOrFolder(FTempFile, AFileName);
  154. end;
  155. { TstgGclSubGatherFileImportor }
  156. procedure TstgGclSubGatherFileImportor.ClearOldData(AStageData: TStageData);
  157. var
  158. i: Integer;
  159. vRec: TStageRecord;
  160. begin
  161. for i := 0 to AStageData.sddStage.RecordCount - 1 do
  162. begin
  163. vRec := TStageRecord(AStageData.sddStage.Records[i]);
  164. vRec.DealQuantity.AsFloat := 0;
  165. vRec.DealTotalPrice.AsFloat := 0;
  166. vRec.DealFlag.AsInteger := 0;
  167. vRec.DealFormula.AsString := '';
  168. vRec.EndDealQuantity.AsFloat := vRec.PreDealQuantity.AsFloat;
  169. vRec.EndDealTotalPrice.AsFloat := vRec.PreDealTotalPrice.AsFloat;
  170. end;
  171. end;
  172. constructor TstgGclSubGatherFileImportor.Create;
  173. begin
  174. FFails := TstgGclFailList.Create;
  175. end;
  176. destructor TstgGclSubGatherFileImportor.Destroy;
  177. begin
  178. FFails.Free;
  179. inherited;
  180. end;
  181. procedure TstgGclSubGatherFileImportor.ImportGatherData(
  182. AProjectData: TProjectData);
  183. function FindBillsNode(ARec: TsdDataRecord): TBillsIDTreeNode;
  184. var
  185. i: Integer;
  186. vNode: TBillsIDTreeNode;
  187. begin
  188. Result := nil;
  189. for i := 0 to AProjectData.BillsMeasureData.BillsMeasureTree.Count - 1 do
  190. begin
  191. vNode := TBillsIDTreeNode(AProjectData.BillsMeasureData.BillsMeasureTree.Items[i]);
  192. if (vNode.HasChildren) then Continue;
  193. if (vNode.Rec.B_Code.AsString = ARec.ValueByName('B_Code').AsString) and
  194. (vNode.Rec.Name.AsString = ARec.ValueByName('Name').AsString) and
  195. (vNode.Rec.Units.AsString = ARec.ValueByName('Units').AsString) and
  196. (CommonRoundTo(vNode.Rec.Price.AsFloat - ARec.ValueByName('Price').AsFloat, -6) = 0) then
  197. begin
  198. Result := vNode;
  199. Break;
  200. end;
  201. end;
  202. end;
  203. var
  204. i: Integer;
  205. vNode: TBillsIDTreeNode;
  206. vOrgRec: TsdDataRecord;
  207. vStageRec: TStageRecord;
  208. begin
  209. for i := 0 to GatherData.sddBills.RecordCount - 1 do
  210. begin
  211. vOrgRec := GatherData.sddBills.Records[i];
  212. vNode := FindBillsNode(vOrgRec);
  213. if Assigned(vNode) then
  214. begin
  215. vStageRec := AProjectData.PhaseData.StageData.StageRecordWithAdd(vNode.ID);
  216. vStageRec.DealQuantity.AsFloat := vOrgRec.ValueByName('DealQuantity').AsFloat;
  217. end
  218. else
  219. FFails.AddFailGcl(vOrgRec.ValueByName('B_Code').AsString,
  220. vOrgRec.ValueByName('Name').AsString, vOrgRec.ValueByName('Units').AsString,
  221. vOrgRec.ValueByName('Price').AsFloat, vOrgRec.ValueByName('DealQuantity').AsFloat);
  222. end;
  223. end;
  224. procedure TstgGclSubGatherFileImportor.ImportGatherDataTo(
  225. AProjectData: TProjectData; const AFileName: string);
  226. begin
  227. Open(AFileName);
  228. AProjectData.PhaseData.StageData.sddStage.BeginUpdate;
  229. AProjectData.PhaseData.StageData.BeforeBatchOperation;
  230. try
  231. ClearOldData(AProjectData.PhaseData.StageData);
  232. ImportGatherData(AProjectData);
  233. finally
  234. AProjectData.PhaseData.StageData.AfterBatchOperation;
  235. AProjectData.PhaseData.StageData.sddStage.EndUpdate;
  236. end;
  237. if FFails.Count > 0 then
  238. ShowGclImportForm(FFails);
  239. end;
  240. { TstgGclSubGatherFileExcelImportor }
  241. procedure TstgGclSubGatherFileExcelImportor.BeginImport;
  242. begin
  243. inherited;
  244. ProjectData.PhaseData.StageData.sddStage.BeginUpdate;
  245. ProjectData.PhaseData.StageData.BeforeBatchOperation;
  246. end;
  247. procedure TstgGclSubGatherFileExcelImportor.ClearOldData(
  248. AStageData: TStageData);
  249. var
  250. i: Integer;
  251. vRec: TStageRecord;
  252. begin
  253. for i := 0 to AStageData.sddStage.RecordCount - 1 do
  254. begin
  255. vRec := TStageRecord(AStageData.sddStage.Records[i]);
  256. vRec.DealQuantity.AsFloat := 0;
  257. vRec.DealTotalPrice.AsFloat := 0;
  258. vRec.DealFlag.AsInteger := 0;
  259. vRec.DealFormula.AsString := '';
  260. vRec.EndDealQuantity.AsFloat := vRec.PreDealQuantity.AsFloat;
  261. vRec.EndDealTotalPrice.AsFloat := vRec.PreDealTotalPrice.AsFloat;
  262. end;
  263. end;
  264. constructor TstgGclSubGatherFileExcelImportor.Create(
  265. AProjectData: TProjectData);
  266. begin
  267. inherited Create(AProjectData);
  268. FFails := TstgGclFailList.Create;
  269. end;
  270. destructor TstgGclSubGatherFileExcelImportor.Destroy;
  271. begin
  272. FFails.Free;
  273. inherited;
  274. end;
  275. procedure TstgGclSubGatherFileExcelImportor.EndImport;
  276. begin
  277. ProjectData.PhaseData.StageData.AfterBatchOperation;
  278. ProjectData.PhaseData.StageData.sddStage.EndUpdate;
  279. if FFails.Count > 0 then
  280. ShowGclImportForm(FFails);
  281. inherited;
  282. end;
  283. procedure TstgGclSubGatherFileExcelImportor.Import;
  284. begin
  285. ClearOldData(ProjectData.PhaseData.StageData);
  286. FCurRow := 0;
  287. if LoadColumnsFromHead(OExport.OpenWorkSheet) then
  288. LoadGatherData(OExport.OpenWorkSheet)
  289. else
  290. ErrorMessage('导入的Excel格式有误!');
  291. inherited;
  292. end;
  293. function TstgGclSubGatherFileExcelImportor.LoadColumnsFromHead(
  294. ASheet: TExportWorkSheet): Boolean;
  295. var
  296. vRow: TExportRow;
  297. iCol: Integer;
  298. sColName: String;
  299. begin
  300. FB_CodeCol := -1;
  301. FNameCol := -1;
  302. FUnitsCol := -1;
  303. FPriceCol := -1;
  304. FDealQuantityCol := -1;
  305. vRow := ASheet.Rows[FCurRow];
  306. for iCol := 0 to vRow.Cells.Count - 1 do
  307. begin
  308. sColName := GetCellTrimStr(vRow, iCol);
  309. if (sColName = '清单编号') then
  310. FB_CodeCol := iCol
  311. else if sColName = '名称' then
  312. FNameCol := iCol
  313. else if sColName = '单位' then
  314. FUnitsCol := iCol
  315. else if sColName = '单价' then
  316. FPriceCol := iCol
  317. else if (sColName = '合同计量') then
  318. FDealQuantityCol := iCol;
  319. end;
  320. Result := (FB_CodeCol <> -1) and (FNameCol <> -1) and (FUnitsCol <> -1) and
  321. (FPriceCol <> -1) and (FDealQuantityCol <> -1);
  322. Inc(FCurRow);
  323. end;
  324. procedure TstgGclSubGatherFileExcelImportor.LoadGatherData(
  325. ASheet: TExportWorkSheet);
  326. function FindBillsNode(const AB_Code, AName, AUnits: string; APrice: Double): TBillsIDTreeNode;
  327. var
  328. i: Integer;
  329. vNode: TBillsIDTreeNode;
  330. begin
  331. Result := nil;
  332. for i := 0 to ProjectData.BillsMeasureData.BillsMeasureTree.Count - 1 do
  333. begin
  334. vNode := TBillsIDTreeNode(ProjectData.BillsMeasureData.BillsMeasureTree.Items[i]);
  335. if (vNode.HasChildren) then Continue;
  336. if (vNode.Rec.B_Code.AsString = AB_Code) and
  337. (vNode.Rec.Name.AsString = AName) and
  338. (vNode.Rec.Units.AsString = AUnits) and
  339. (CommonRoundTo(vNode.Rec.Price.AsFloat - APrice, -6) = 0) then
  340. begin
  341. Result := vNode;
  342. Break;
  343. end;
  344. end;
  345. end;
  346. var
  347. vRow: TExportRow;
  348. sB_Code, sName, sUnits: string;
  349. fPrice: Double;
  350. vNode: TBillsIDTreeNode;
  351. vStageRec: TStageRecord;
  352. begin
  353. while FCurRow < ASheet.Rows.Count do
  354. begin
  355. vRow := ASheet.Rows[FCurRow];
  356. Inc(FCurRow);
  357. sB_Code := Trim(GetCellStr(vRow, FB_CodeCol));
  358. sName := Trim(GetCellStr(vRow, FNameCol));
  359. sUnits := Trim(GetCellStr(vRow, FUnitsCol));
  360. fPrice := StrToFloatDef(GetCellStr(vRow, FPriceCol), 0);
  361. if (sB_Code = '') then Continue;
  362. vNode := FindBillsNode(sB_Code, sName, sUnits, fPrice);
  363. if Assigned(vNode) then
  364. begin
  365. vStageRec := ProjectData.PhaseData.StageData.StageRecordWithAdd(vNode.ID);
  366. vStageRec.DealQuantity.AsFloat := StrToFloatDef(GetCellStr(vRow, FDealQuantityCol), 0);
  367. end
  368. else
  369. FFails.AddFailGcl(sB_Code, sName, sUnits, fPrice, StrToFloatDef(GetCellStr(vRow, FDealQuantityCol), 0));
  370. end;
  371. end;
  372. end.