{*******************************************************} { } { ProcessPrintWater } { } { Copyright (C) 2025 kku } { } {*******************************************************} unit ProcessPrintWater; interface uses Winapi.Windows, System.SysUtils, System.Classes, Vcl.Imaging.pngimage, Vcl.Graphics, Tocsg.Graphic, CttSchDefine; function GetPrtWaterText(sPrtDocId: String): String; function ProcessWatermarkToImage(png: TPngImage; aDest: HDC; nW, nH: Integer; WInfo: TPrtWaterEnt; fST: Double; sTopText, sBottomText: String; var bmpWaterP: TBitmap; sMaskImg: String = ''): Boolean; implementation uses {$IFDEF _HE_} ManagerService, ManagerModel, {$ELSE} Define, Tocsg.Network, Tocsg.WinInfo, {$ENDIF} Condition, Tocsg.Path, GlobalDefine, STLabGuardModule, Tocsg.Safe, Tocsg.Exception, Tocsg.Trace, Winapi.GDIPAPI, Tocsg.Strings, Vcl.Imaging.jpeg, EM.DelphiZXIngQRCode; const WORD_GAP = ' '; var _bmpST: TBitmap = nil; _sOutCode: AnsiString = ''; function GetPrtWaterText(sPrtDocId: String): String; begin try {$IFDEF _HE_} case CUSTOMER_TYPE of CUSTOMER_WELFND, CUSTOMER_WELFNI : begin var sTemp: String := sPrtDocId; if sTemp.Length > 20 then SetLength(sTemp, 20); Result := gMgSvc.EmpNo + '/' + sTemp; end; CUSTOMER_KORENTAL : begin if gMgSvc.UName <> '' then Result := Format('%s/%s/%s/%s/%s', [gMgSvc.EmpNo, gMgSvc.DeptName, gMgSvc.UName, gMgSvc.NicService.GetIP, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) else if gMgSvc.DeptName <> '' then Result := Format('%s/%s/%s/%s', [gMgSvc.EmpNo, gMgSvc.DeptName, gMgSvc.NicService.GetIP, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) else Result := Format('%s/%s/%s', [gMgSvc.EmpNo, gMgSvc.NicService.GetIP, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) end; CUSTOMER_CJONS : begin var sDept: String := ExtrLastDelimiterStr(gMgSvc.DeptName, ';'); var sUName: String := gMgSvc.UName; if sUName = '' then sUname := gMgSvc.EmpNo; if sDept <> '' then Result := Format('%s/%s/%s', [sUName, sDept, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) else Result := Format('%s/%s', [sUName, FormatDateTime('yyyy-mm-dd hh:nn', Now)]); end; CUSTOMER_SHSC : begin var sEmpNo: String := gMgSvc.EmpNo; if sEmpNo.Length > 2 then sEmpNo[3] := '*'; if sEmpNo.Length > 3 then sEmpNo[4] := '*'; if gMgSvc.UName <> '' then begin var sUName: String := gMgSvc.UName; if sUName.Length > 1 then sUName[2] := '*'; Result := Format('%s / %s / %s', [sUName, sEmpNo, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) end else Result := Format('%s / %s', [sEmpNo, FormatDateTime('yyyy-mm-dd hh:nn', Now)]); end; CUSTOMER_SHCI : begin if gMgSvc.UName <> '' then begin var sUName: String := gMgSvc.UName; if sUName.Length > 1 then sUName[2] := '*'; Result := Format('%s / %s / %s / %s', [gMgSvc.EmpNo, sUName, gMgSvc.DeptName, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]) end else if gMgSvc.DeptName <> '' then Result := Format('%s / %s / %s', [gMgSvc.EmpNo, gMgSvc.DeptName, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]) else Result := Format('%s / %s', [gMgSvc.EmpNo, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]); end; CUSTOMER_SKEC : begin if gMgSvc.UName <> '' then Result := Format('%s / %s / %s / %s', [FormatDateTime('yyyy-mm-dd hh:nn', Now), gMgSvc.DeptName, gMgSvc.UName, gMgSvc.EmpNo]) else if gMgSvc.DeptName <> '' then Result := Format('%s / %s / %s', [FormatDateTime('yyyy-mm-dd hh:nn', Now), gMgSvc.DeptName, gMgSvc.EmpNo]) else Result := Format('%s / %s', [FormatDateTime('yyyy-mm-dd hh:nn', Now), gMgSvc.EmpNo]); end; CUSTOMER_GIORDANO : begin Result := Format('%s / %s', [gMgSvc.EmpNo, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]); end; CUSTOMER_UNITUS, CUSTOMER_MOTRAS : begin if gMgSvc.UName <> '' then Result := Format('%s / %s / %s / %s / %s', [gMgSvc.UName, gMgSvc.DeptName, gMgSvc.EmpNo, gMgSvc.NicService.GetIP, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) else if gMgSvc.DeptName <> '' then Result := Format('%s / %s / %s / %s', [gMgSvc.DeptName, gMgSvc.EmpNo, gMgSvc.NicService.GetIP, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) else Result := Format('%s / %s / %s', [gMgSvc.EmpNo, gMgSvc.NicService.GetIP, FormatDateTime('yyyy-mm-dd hh:nn', Now)]); end; CUSTOMER_SOLMIX : begin Result := Format('%s / %s / ', [gMgSvc.EmpNo, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]); end; CUSTOMER_SANKYO : begin if gMgSvc.UName <> '' then Result := Format('%s / %s / %s', [gMgSvc.UName, gMgSvc.EmpNo, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) else Result := Format('%s / %s', [gMgSvc.EmpNo, FormatDateTime('yyyy-mm-dd hh:nn', Now)]); end; CUSTOMER_SERVE1 : begin if gMgSvc.DeptName <> '' then begin var sDept: String := ExtrLastDelimiterStr(gMgSvc.DeptName, ';'); Result := Format('%s / %s / %s / %s / %s', [sDept, gMgSvc.UName, gMgSvc.EmpNo, gMgSvc.NicService.GetIP, FormatDateTime('yyyy-mm-dd hh:nn', Now)]); end else Result := Format('%s / %s / %s', [gMgSvc.EmpNo, gMgSvc.NicService.GetIP, FormatDateTime('yyyy-mm-dd hh:nn', Now)]); end; CUSTOMER_DEMO : begin Result := sPrtDocId; end; else begin if gMgSvc.UName <> '' then Result := Format('%s / %s / %s / %s', [gMgSvc.UName, gMgSvc.DeptName, gMgSvc.EmpNo, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) else if gMgSvc.DeptName <> '' then Result := Format('%s / %s / %s', [gMgSvc.DeptName, gMgSvc.EmpNo, FormatDateTime('yyyy-mm-dd hh:nn', Now)]) else Result := Format('%s / %s', [gMgSvc.EmpNo, FormatDateTime('yyyy-mm-dd hh:nn', Now)]); end; end; {$ENDIF} except on E: Exception do begin Result := 'Error...'; ETgException.TraceException(E, 'Fail .. GetPrtWaterText()'); end; end; end; function MaskPrtST: Boolean; var sWDir, sStKey, sStPng: String; nResult: Integer; begin try Result := false; if not FileExists(GetRunExePathDir + DIR_CONF + DLL_ST) then exit; // sStKey := GetRunExePathDir + DIR_CONF + DAT_SNAPTAGKEY_P; sWDir := 'C:\ProgramData\HE\'; sStKey := sWDir + DAT_SNAPTAGKEY_P; if not FileExists(sStKey) and ForceDirectories(sWDir) then begin var StrList: TStringList; Guard(StrList, TStringList.Create); StrList.Text := ST_Key_P; StrList.SaveToFile(sStKey, TEncoding.ANSI); end; if FileExists(sStKey) then begin sStPng := sWDir + PNG_SNAPTAGDATA_PRT; nResult := labGuardPS(sStKey, sStPng, 2, 1{3블루}, 1 {유저코드?}, FormatDateTime('yyyy/mm/dd hh:nn', Now), _sOutCode); Result := nResult = 0; if not Result then TTgTrace.T('Fail .. MaskPrtST() .. Snaptag .. code = %d', [nResult], 1); end; except on E: Exception do ETgException.TraceException(E, 'Fail .. MaskPrtST()'); end; end; function GetUseSnapTag: Boolean; begin {$IFDEF _HE_} Result := IsUseSnaptag; {$ELSE} Result := gParam.UseSnaptag; {$ENDIF} end; procedure ProcessSnaptag(png: TPngImage; fST: Double); var sStPng: String; pngST: TPngImage; nsX, nsY: Integer; begin if not GetUseSnapTag then exit; if not MaskPrtST then exit; try if _bmpST = nil then begin // sStPng := GetRunExePathDir + DIR_CONF + PNG_SNAPTAGDATA_PRT; sStPng := 'C:\ProgramData\HE\' + PNG_SNAPTAGDATA_PRT; if FileExists(sStPng) then begin Guard(pngST, TPngImage.Create); pngST.LoadFromFile(sStPng); _bmpST := TBitmap.Create; _bmpST.PixelFormat := pf4bit; _bmpST.SetSize(png.Width div 5, png.Height div 5); nsX := 0; while nsX < (_bmpST.Width + pngST.Width) do begin nsY := 0; while nsY < (_bmpST.Height + pngST.Height) do begin _bmpST.Canvas.Draw(nsX, nsY, pngST); Inc(nsY, pngST.Height); end; Inc(nsX, pngST.Width); end; end; end; if _bmpST <> nil then begin // _bmpST.SaveToFile('C:\Users\kku\Desktop\이전 바탕화면\출력 추출 데이터\test.bmp'); var cTrMatrix: TColorMatrix; ZeroMemory(@cTrMatrix, SizeOf(cTrMatrix)); // 회색 // cTrMatrix[0][0] := 0.299; // cTrMatrix[0][1] := 0.299; // cTrMatrix[0][2] := 0.299; // cTrMatrix[1][0] := 0.587; // cTrMatrix[1][1] := 0.587; // cTrMatrix[1][2] := 0.587; // cTrMatrix[2][0] := 0.114; // cTrMatrix[2][1] := 0.114; // cTrMatrix[2][2] := 0.114; // cTrMatrix[3][3] := 0.10; // 투명도 1.0 ~ 2.22 // cTrMatrix[4][4] := 1.0; cTrMatrix := MakeColorMatrix(0.2, 0.2, 0.2, fST); DrawBitmapWaterEx(png.Canvas.Handle, 0, 0, _bmpST, @cTrMatrix, png.Width, png.Height); end; except on E: Exception do ETgException.TraceException(E, 'Fail .. ProcessSnaptag()'); end; end; function GetPrtDPI: Integer; begin {$IFDEF _HE_} Result := gMgSvc.PrefModel.PrtDPI; {$ELSE} Result := gParam.PrtDPI; {$ENDIF} end; function GetPWC: TPrtWaterCfg; begin {$IFDEF _HE_} Result := gMgSvc.PrefModel.PrtWaterCfg; {$ELSE} Result := gParam.PrtWaterCfg; {$ENDIF} end; function GetIpAddr: String; begin {$IFDEF _HE_} Result := gMgSvc.NicService.GetIP; {$ELSE} Result := gParam.IP; {$ENDIF} end; function GetMac: String; begin {$IFDEF _HE_} Result := gMgSvc.NicService.GetMAC; {$ELSE} Result := GetMACAddr; {$ENDIF} end; function GetComN: String; begin {$IFDEF _HE_} Result := gMgSvc.ComName; {$ELSE} Result := GetComName; {$ENDIF} end; function GetEmpNo: String; begin {$IFDEF _HE_} Result := gMgSvc.EmpNo; {$ELSE} Result := gParam.EmpNo; {$ENDIF} end; function GetUName: String; begin {$IFDEF _HE_} Result := gMgSvc.UName; {$ELSE} Result := gParam.UName; {$ENDIF} end; function GetDeptName: String; begin {$IFDEF _HE_} Result := gMgSvc.DeptName; {$ELSE} Result := gParam.DeptName; {$ENDIF} end; function GetLabelName: String; begin {$IFDEF _HE_} Result := gMgSvc.RecentLabel; {$ELSE} Result := gParam.LabelName; {$ENDIF} end; function GetDPI_Size(nSize: Integer): Integer; begin case GetPrtDPI of 100 : Result := nSize - ((nSize div 6) * 5); 200 : Result := nSize - ((nSize div 6) * 4); 300 : Result := nSize - ((nSize div 6) * 3); 400 : Result := nSize - ((nSize div 6) * 2); 500 : Result := nSize - (nSize div 6); else Result := nSize; end; end; procedure DrawRotatedText(Canvas: TCanvas; X, Y, Angle: Integer; const Text: string); var LogFont: TLogFont; OldFont, RotatedFont: HFONT; begin // 기존 폰트를 기반으로 로그폰트 가져오기 GetObject(Canvas.Font.Handle, SizeOf(LogFont), @LogFont); // 회전 각도 설정 (0.1도 단위, 즉 450 = 45도) LogFont.lfEscapement := Angle * 10; LogFont.lfOrientation := Angle * 10; // 안티앨리어싱 등 품질 향상 옵션 LogFont.lfQuality := ANTIALIASED_QUALITY; // 회전 폰트 생성 RotatedFont := CreateFontIndirect(LogFont); OldFont := SelectObject(Canvas.Handle, RotatedFont); // 텍스트 출력 TextOut(Canvas.Handle, X, Y, PChar(Text), Length(Text)); // 자원 정리 SelectObject(Canvas.Handle, OldFont); DeleteObject(RotatedFont); end; function CalcSizeDIP(n300: Integer): Integer; var nSize: Integer; begin nSize := n300 * 2; case GetPrtDPI of 100 : Result := nSize - ((nSize div 6) * 5); 200 : Result := nSize - ((nSize div 6) * 4); 300 : Result := nSize - ((nSize div 6) * 3); 400 : Result := nSize - ((nSize div 6) * 2); 500 : Result := nSize - (nSize div 6); else Result := nSize; end; end; function ProcessWatermarkToImage(png: TPngImage; aDest: HDC; nW, nH: Integer; WInfo: TPrtWaterEnt; fST: Double; sTopText, sBottomText: String; var bmpWaterP: TBitmap; sMaskImg: String = ''): Boolean; procedure SetImgFontSize(nSize: Integer); begin png.Canvas.Font.Size := GetDPI_Size(nSize); end; var nTmp, nLeft, nTop: Integer; sWText: String; PWC: TPrtWaterCfg; begin if png = nil then Exit(false); Result := true; ProcessSnaptag(png, fST); // 가로출력인데 세로로 되어 있으면 돌려준다. 24_0819 16:57:41 kku if not WInfo.bPaperV and (png.Width < png.Height) then RotatePng(png, 90); // if ProcType <> ptPng then // begin // Result := false; // exit; // end; if not WInfo.bUseWM then begin Result := false; exit; end; try // if IsUsePrintMask then // begin // if sPrtMaskingStr_ <> '' then // begin // // 마스킹 처리... 24_0529 16:16:06 kku // if (sMaskImg <> '') and FileExists(sMaskImg) then // begin // var sOcrPath: String := GetRunExePathDir + DIR_CONF + EXE_OCR; // var sTmpPath: String := 'C:\ProgramData\HE\Task\'; // if FileExists(sOcrPath) and ForceDirectories(sTmpPath) then // begin // sTmpPath := sTmpPath + '$TmpOcr.dat'; // ExecuteAppWaitUntilTerminate(sOcrPath, // Format('-r "%s" "%s"', [sMaskImg, sTmpPath]), SW_HIDE, 10000); // // if FileExists(sTmpPath) then // begin // var MgMsk: TManagerImgMskData; // Guard(MgMsk, TManagerImgMskData.Create(sTmpPath)); // DeleteFile(PChar(sTmpPath)); // // var StrList: TStringList; // Guard(StrList, TStringList.Create); // SplitString(sPrtMaskingStr_, ',', StrList, false, true); // // var MskLst: TMskEntList; // Guard(MskLst, TMskEntList.Create); // var cc, nn: Integer; // for cc := 0 to StrList.Count - 1 do // begin // if MgMsk.MatchToList(StrList[cc], MskLst) > 0 then // begin // for nn := 0 to MskLst.Count - 1 do // DoMasking(MskLst[nn]); // end; // end; // end; // end; // end; // end; // end; PWC := GetPWC; if PWC.bActive then begin SetBkMode(png.Canvas.Handle, TRANSPARENT); png.Canvas.Font.Color := clSilver; var sText: String := ''; nLeft := 0; nTop := 0; if (PWC.sTopText <> '') and (PWC.nTopSize > 0) then begin SetImgFontSize(Round(Double(42) * (Double(PWC.nTopSize) / 10))); sText := StrsReplace(PWC.sTopText, ['{IpAddr}', '{HostName}', '{MacAddr}', '{EmpNo}', '{Dept}', '{UserName}', '{DateTime}'], [GetIpAddr, GetComN, GetMac, GetEmpNo, GetDeptName, GetUName, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]); case PWC.nTopPos of 1 : nLeft := 0; // 왼쪽 2 : nLeft := (png.Width div 2) - (png.Canvas.TextWidth(sText) div 2); // 가운데 3 : nLeft := png.Width - png.Canvas.TextWidth(sText); // 오른쪽 end; png.Canvas.TextOut(nLeft, nTop, sText); end; if (PWC.sBotText <> '') and (PWC.nBotSize > 0) then begin SetImgFontSize(Round(Double(42) * (Double(PWC.nBotSize) / 10))); sText := StrsReplace(PWC.sBotText, ['{IpAddr}', '{HostName}', '{MacAddr}', '{EmpNo}', '{Dept}', '{UserName}', '{DateTime}'], [GetIpAddr, GetComN, GetMac, GetEmpNo, GetDeptName, GetUName, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]); case PWC.nBotPos of 1 : nLeft := 0; // 왼쪽 2 : nLeft := (png.Width div 2) - (png.Canvas.TextWidth(sText) div 2); // 가운데 3 : nLeft := png.Width - png.Canvas.TextWidth(sText); // 오른쪽 end; nTop := png.Height - png.Canvas.TextHeight(sText); png.Canvas.TextOut(nLeft, nTop, sText); end; end else if not IgrPrintWaterDefText then begin SetBkMode(png.Canvas.Handle, TRANSPARENT); SetImgFontSize(42); png.Canvas.Font.Color := clSilver; if sTopText <> '' then begin nLeft := 0; nTop := 0; // if cbTopTextPos.ItemIndex <> 0 then // nLeft := bmp.Width - bmp.Canvas.TextWidth(sTopText); // bmp.Canvas.TextOut(nLeft, nTop, sTopText); png.Canvas.TextOut(nLeft, nTop, sTopText); end; if sBottomText <> '' then begin // bmp.Canvas.Font.Size := 10 * 7; // nLeft := 0; // nTop := bmp.Height - bmp.Canvas.TextHeight(sBottomText); //// if cbBottomTextPos.ItemIndex <> 0 then // nLeft := bmp.Width - bmp.Canvas.TextWidth(sBottomText); // bmp.Canvas.TextOut(nLeft, nTop, sBottomText); if CUSTOMER_TYPE = CUSTOMER_SOLIDEO then begin SetImgFontSize(42); png.Canvas.Font.Color := $969696; sBottomText := '(주)솔리데오'; if GetDeptName <> '' then begin var sDept: String := GetDeptName; var nPos: Integer := Pos(';', sDept); if nPos > 0 then Delete(sDept, nPos, sDept.Length - nPos + 1); SumString(sBottomText, sDept, ' / '); end; if GetUName <> '' then SumString(sBottomText, GetUName, ' / ') else SumString(sBottomText, GetEmpNo, ' / '); SumString(sBottomText, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now), ' / ') end; if (png.Height > nH) and (WInfo.sPdfPath = '') then // 이거 왜 이렇게 했는지... 까먹음.. 24_0626 14:18:50 kku nTop := (png.Height - ((png.Height - nH) div 2)) - png.Canvas.TextHeight(sBottomText) else nTop := png.Height - png.Canvas.TextHeight(sBottomText); if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - ((png.Width - nW) div 2)) - png.Canvas.TextWidth(sBottomText) else nLeft := png.Width - png.Canvas.TextWidth(sBottomText); case CUSTOMER_TYPE of CUSTOMER_LOCAL : // CUSTOMER_DEMO begin // for 포스코 // if (png.Width > nW) and (WInfo.sPdfPath = '') then // png.Canvas.TextOut((png.Width - nW) div 2, nTop, sBottomText) // else // png.Canvas.TextOut(0, nTop, sBottomText); // QR 코드, todo : 함수로 만들필요 있음 var QRCode: TDelphiZXingQRCode; Guard(QRCode, TDelphiZXingQRCode.Create); QRCode.Data := '"' + sBottomText + '"'; QRCode.QuietZone := 4; var QrBmp: TBitmap; Guard(QrBmp, TBitmap.Create); QrBmp.SetSize(QRCode.Rows, QRCode.Columns); var R, C, nX, nY, nQrSize: Integer; for R := 0 to QRCode.Rows - 1 do begin for C := 0 to QRCode.Columns - 1 do begin if (QRCode.IsBlack[R, C]) then begin QrBmp.Canvas.Pixels[C, R] := clBlack; end else begin QrBmp.Canvas.Pixels[C, R] := clWhite; end; end; end; if (png.Width > nW) and (WInfo.sPdfPath = '') then nX := (png.Width - nW) div 2 else nX := 0; if (png.Height > nH) and (WInfo.sPdfPath = '') then nY := (png.Height - nH) div 2 else nY := 0; var rc: TRect; if png.Width < png.Height then nQrSize := png.Width div 20 else nQrSize := png.Height div 20; rc.Left := nX + png.Width - nQrSize; rc.Right := nX + png.Width; rc.Top := nY + png.Height - nQrSize; rc.Bottom := nY + png.Height; png.Canvas.StretchDraw(rc, QrBmp); // 사선 텍스트 var bmp: TBitmap := nil; // todo : 재사용 가능하게 if bmp = nil then begin // var sText: String := Format('%s / %s / %s', [GetComN, GetIpAddr, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]); var sText: String := Format('%s / %s', [GetComN, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]); sText := sText + ' ' + sText + ' ' + sText + ' ' + sText; try bmp := TBitmap.Create; bmp.PixelFormat := pf4bit; // 이거 켜면 흑백 출력시 안됨 24_0807 15:52:56 kku bmp.Canvas.Font.Assign(png.Canvas.Font); bmp.Canvas.Font.Color := clGray; bmp.Canvas.Font.Size := 60; bmp.TransparentColor := clWhite; bmp.Transparent := true; var nTW: Integer := bmp.Canvas.TextWidth(sText); bmp.SetSize(nTW, nTW); // _bmpWaterP.SetSize(500, 500); // TTgTrace.T('bmp.Canvas.Font.Name=%s', [bmp.Canvas.Font.Name]); DrawRotatedText(bmp.Canvas, bmp.Canvas.TextHeight(sText), 0, -45, sText); except // .. end; end; if bmp <> nil then begin var cTrMatrix: TColorMatrix; ZeroMemory(@cTrMatrix, SizeOf(cTrMatrix)); cTrMatrix := MakeColorMatrix(0.2, 0.2, 0.2, 0.15); DrawBitmapWaterEx(png.Canvas.Handle, Round(nW / 3) * -1, 0, bmp, @cTrMatrix); DrawBitmapWaterEx(png.Canvas.Handle, 0, 0, bmp, @cTrMatrix); DrawBitmapWaterEx(png.Canvas.Handle, Round(nW / 3), 0, bmp, @cTrMatrix); end; // if WInfo.LogJson <> '' then begin // 파일 이름으로 보안등급 출력 try // var OLog: ISuperObject := SO(WInfo.LogJson); // if OLog <> nil then begin // var sFName: String := OLog.S['COMPONENT_FILENAME']; var sFName: String := WInfo.sDocName; // 엑셀에 [ 가 ( 로 변경되서 급한대로 아래처럼 처리 24_1023 10:07:45 kku sFName := StringReplace(sFName, '(', '[', [rfReplaceAll]); sFName := StringReplace(sFName, ')', ']', [rfReplaceAll]); // if (sFName <> '') and (sFName[1] = '[') then if sFName.Contains('[') then begin SetImgFontSize(png.Canvas.Font.Size * 2); sWText := GetCapsuleStr('[', ']', sFName); if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - ((png.Width - nW) div 2)) - png.Canvas.TextWidth(sWText) else nLeft := png.Width - png.Canvas.TextWidth(sWText); png.Canvas.TextOut(nLeft, 0, sWText); end; end; except // ... end; end; end; CUSTOMER_KORENTAL : begin png.Canvas.Font.Color := clBlack; SetImgFontSize(45); // 좌측 상단 png.Canvas.TextOut(0, 0, sBottomText); if (png.Height > nH) and (WInfo.sPdfPath = '') then // 이거 왜 이렇게 했는지... 까먹음.. 24_0626 14:18:50 kku nTop := (png.Height - ((png.Height - nH) div 2)) - png.Canvas.TextHeight(sBottomText) else nTop := png.Height - png.Canvas.TextHeight(sBottomText); // 가운데 하단 sWText := '본 문서는 한국렌탈의 정보 자산이며 무단 반출 시 당사 사규와 관련 법규에 의해 제재를 받을 수 있습니다.'; if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := ((png.Width - ((png.Width - nW) div 2)) div 2) - (png.Canvas.TextWidth(sWText) div 2) else nLeft := (png.Width div 2) - (png.Canvas.TextWidth(sWText) div 2); png.Canvas.TextOut(nLeft, nTop, sWText); end; CUSTOMER_WELFND, CUSTOMER_WELFNI : begin png.Canvas.Font.Color := clSilver; SetImgFontSize(50); if (png.Height > nH) and (WInfo.sPdfPath = '') then // 이거 왜 이렇게 했는지... 까먹음.. 24_0626 14:18:50 kku nTop := (png.Height - ((png.Height - nH) div 2)) - png.Canvas.TextHeight(sBottomText) else nTop := png.Height - png.Canvas.TextHeight(sBottomText); // var nTW: Integer := png.Canvas.TextWidth(sBottomText); // 좌측 상단 png.Canvas.TextOut(0, 0, sBottomText); // 우측 상단 if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - ((png.Width - nW) div 2)) - png.Canvas.TextWidth(sBottomText) else nLeft := png.Width - png.Canvas.TextWidth(sBottomText); png.Canvas.TextOut(nLeft, 0, sBottomText); // 좌측 하단 png.Canvas.TextOut(0, nTop, sBottomText); // 우측 하단 sWText := '본 문서에 대한 소유권은 회사에 있으며, 무단으로 반출 시 법적 책임을 받게 됩니다.'; if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - ((png.Width - nW) div 2)) - png.Canvas.TextWidth(sWText) else nLeft := png.Width - png.Canvas.TextWidth(sWText); png.Canvas.TextOut(nLeft, nTop, sWText); // QR 코드, todo : 함수로 만들필요 있음 var QRCode: TDelphiZXingQRCode; Guard(QRCode, TDelphiZXingQRCode.Create); QRCode.Data := '"' + sBottomText + '"'; QRCode.QuietZone := 4; var QrBmp: TBitmap; Guard(QrBmp, TBitmap.Create); QrBmp.SetSize(QRCode.Rows, QRCode.Columns); var R, C, nX, nY, nQrSize: Integer; for R := 0 to QRCode.Rows - 1 do begin for C := 0 to QRCode.Columns - 1 do begin if (QRCode.IsBlack[R, C]) then begin QrBmp.Canvas.Pixels[C, R] := clBlack; end else begin QrBmp.Canvas.Pixels[C, R] := clWhite; end; end; end; if (png.Width > nW) and (WInfo.sPdfPath = '') then nX := (png.Width - nW) div 2 else nX := 0; if (png.Height > nH) and (WInfo.sPdfPath = '') then nY := (png.Height - nH) div 2 else nY := 0; var rc: TRect; if png.Width < png.Height then nQrSize := png.Width div 20 else nQrSize := png.Height div 20; rc.Left := nX + png.Width - nQrSize; rc.Right := nX + png.Width; rc.Top := nY + png.Height - nQrSize - png.Canvas.TextHeight(sWText); rc.Bottom := nY + png.Height - png.Canvas.TextHeight(sWText); png.Canvas.StretchDraw(rc, QrBmp); // sBottomText := GetEmpNo + '/' + sPrtDocId; if png.Width > png.Height then begin nLeft := CalcSizeDIP(936); //(png.Width div 2) - nTW - Round(nTW / 2); nTop := CalcSizeDIP(292); //Round(png.Height / 8.5); DrawRotatedText(png.Canvas, nLeft, nTop, -45, sBottomText); // _Trace('**************** 1번째 대각선 : L=%d, T=%d', [nLeft, nTop]); nLeft := CalcSizeDIP(2298); // (png.Width div 2) + png.Canvas.TextWidth(sBottomText); nTop := CalcSizeDIP(1652); // png.Height - (png.Height div 3); DrawRotatedText(png.Canvas, nLeft, nTop, -45, sBottomText); // _Trace('**************** 2번째 대각선 : L=%d, T=%d', [nLeft, nTop]); end else begin nLeft := CalcSizeDIP(347);//(png.Width div 4) - png.Canvas.TextWidth(sBottomText) div 2; nTop := CalcSizeDIP(779); // Round(png.Height / 4.5); DrawRotatedText(png.Canvas, nLeft, nTop, -45, sBottomText); // _Trace('**************** 1번째 대각선 : L=%d, T=%d', [nLeft, nTop]); nLeft := CalcSizeDIP(1784); //(png.Width div 2) + png.Canvas.TextWidth(sBottomText); nTop := CalcSizeDIP(2338); //png.Height - (png.Height div 3); DrawRotatedText(png.Canvas, nLeft, nTop, -45, sBottomText); // _Trace('**************** 2번째 대각선 : L=%d, T=%d', [nLeft, nTop]); end; end; CUSTOMER_SOLMIX : begin png.Canvas.Font.Color := clGray; SetImgFontSize(50); if (png.Height > nH) and (WInfo.sPdfPath = '') then // 이거 왜 이렇게 했는지... 까먹음.. 24_0626 14:18:50 kku nTop := (png.Height - ((png.Height - nH) div 2)) - png.Canvas.TextHeight(sBottomText) else nTop := png.Height - png.Canvas.TextHeight(sBottomText); // var nTW: Integer := png.Canvas.TextWidth(sBottomText); sWText := sBottomText + WInfo.sDocName; // 좌측 상단 png.Canvas.TextOut(0, 0, sWText); // 좌측 하단 sWText := sBottomText + '이 문서는 솔믹스 보안 문서로서 무단 복사 및 외부 유출을 금합니다.'; png.Canvas.TextOut(0, nTop, sWText); // 가운데 사선 if png.Width < png.Height then SetImgFontSize(png.Width div 9) else SetImgFontSize(png.Height div 9); sWText := GetEmpNo; var bmpW: TBitmap; Guard(bmpW, TBitmap.Create); bmpW.SetSize(png.Canvas.TextWidth(sWText), png.Canvas.TextHeight(sWText)); bmpW.Canvas.Font := png.Canvas.Font; bmpW.Canvas.Font.Color := clGray; bmpW.Canvas.TextOut(0, 0, sWText); bmpW.TransparentColor := clWhite; bmpW.Transparent := true; RotateBitmap_PlgBlt(bmpW, -0.8, true, clWhite); var cTrMatrix: TColorMatrix; ZeroMemory(@cTrMatrix, SizeOf(cTrMatrix)); // 회색 cTrMatrix[0][0] := 0.299; cTrMatrix[0][1] := 0.299; cTrMatrix[0][2] := 0.299; cTrMatrix[1][0] := 0.587; cTrMatrix[1][1] := 0.587; cTrMatrix[1][2] := 0.587; cTrMatrix[2][0] := 0.114; cTrMatrix[2][1] := 0.114; cTrMatrix[2][2] := 0.114; cTrMatrix[3][3] := 0.22; // 투명도 1.0 ~ 2.22 cTrMatrix[4][4] := 1.0; var nX: Integer := png.Width - (png.Width div 2) - (bmpW.Width div 2); var nY: Integer := png.Height - (png.Height div 2) - (bmpW.Height div 2); DrawBitmapWaterEx(png.Canvas.Handle, nX, nY, bmpW, @cTrMatrix); end; CUSTOMER_GIORDANO, CUSTOMER_CJONS : begin png.Canvas.Font.Color := $969696; // 우측 하단 if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - ((png.Width - nW) div 2)) - png.Canvas.TextWidth(sBottomText) else nLeft := png.Width - png.Canvas.TextWidth(sBottomText); png.Canvas.TextOut(nLeft, nTop, sBottomText); end; CUSTOMER_SHSC : begin png.Canvas.Font.Color := $969696; // 좌측 하단 sWText := '고객정보 무단 반출시 법적 제재를 받을 수 있으며, 모든 출력물은 모니터링 됩니다.'; if (png.Width > nW) and (WInfo.sPdfPath = '') then png.Canvas.TextOut((png.Width - nW) div 2, nTop, sWText) else png.Canvas.TextOut(0, nTop, sWText); // 우측 하단 if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - ((png.Width - nW) div 2)) - png.Canvas.TextWidth(sBottomText) else nLeft := png.Width - png.Canvas.TextWidth(sBottomText); png.Canvas.TextOut(nLeft, nTop, sBottomText); end; CUSTOMER_SHCI : begin png.Canvas.Font.Color := $969696; nTop := png.Height - png.Canvas.TextHeight(sBottomText); // 우측 상단 sWText := '고객정보 무단 반출시 법적 제재를 받을 수 있으며, 모든 출력물은 모니터링 됩니다.'; // if (png.Width > nW) and (WInfo.sPdfPath = '') then // nLeft := (png.Width - ((png.Width - nW) div 2)) - png.Canvas.TextWidth(sWText) // else nLeft := png.Width - png.Canvas.TextWidth(sWText); png.Canvas.TextOut(nLeft, 0, sWText); // 좌측 하단 // if (png.Width > nW) and (WInfo.sPdfPath = '') then // png.Canvas.TextOut((png.Width - nW) div 2, nTop, sBottomText) // else png.Canvas.TextOut(0, nTop, sBottomText); end; CUSTOMER_WINSTN : begin png.Canvas.Font.Color := $969696; if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - nW) div 2 else nLeft := 0; // 좌측 하단 sWText := Format('%s / %s', [WInfo.sDocName, sBottomText]); png.Canvas.TextOut(nLeft, nTop, sWText); var nTextH: Integer := png.Canvas.TextHeight(sWText); Dec(nTop, nTextH + (nTextH div 3)); sWText := 'This document is property of the WINSTECHNET And may not be modlfied, copled or distributed without prior consent of the WINSTECHNET'; png.Canvas.TextOut(nLeft, nTop, sWText); Dec(nTop, nTextH + (nTextH div 3)); sWText := '이 문서는 ㈜윈스테크넷의 자산입니다.'; png.Canvas.TextOut(nLeft, nTop, sWText); end; CUSTOMER_SKEC : begin var nSet, nFSize, nTextS1, nTextS2: Integer; if nW < nH then nSet := png.Width else nSet := png.Height; png.Canvas.Font.Name := '돋음'; png.Canvas.Font.Color := $00AEAEAE; if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - nW) div 2 else nLeft := 0; sWText := sBottomText + ' 이 문서는 SK ecoplant 의 보안정책 및 관련 법령에 의해 보호를 받는 정보자산으로 승인 없는 열람, 복사, 수정, 배포를 금지합니다.'; nTextS1 := 40; while True do begin SetImgFontSize(nTextS1); if png.Canvas.TextWidth(sWText) >= nSet then // 부서명이 들어간 후 2000에서 변경 begin Dec(nTextS1); SetImgFontSize(nTextS1); break; end; Inc(nTextS1); end; nTop := png.Canvas.TextHeight(sWText) div 2; sWText := 'This document is the informational asset protected by SK ecoplant security and law. Unauthorized access, copy, revision, distribution are strictly prohibited'; SetImgFontSize(40); nTextS2 := png.Canvas.Font.Size; while True do begin if png.Canvas.TextWidth(sWText) >= nSet then // 부서명이 들어간 후 2000에서 변경 begin Dec(nTextS2); png.Canvas.Font.Size := nTextS2; break; end; Inc(nTextS2); png.Canvas.Font.Size := nTextS2; end; if nW < nH then begin if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := ((png.Width - ((png.Width - nW) div 2)) div 2) - (png.Canvas.TextWidth(sWText) div 2) else nLeft := (png.Width div 2) - (png.Canvas.TextWidth(sWText) div 2); end else begin if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := (png.Width - nW) div 2 else nLeft := 0; end; var nTextH: Integer := png.Canvas.TextHeight(sWText); Inc(nTop, nTextH + Round(nTextH / 5)); png.Canvas.TextOut(nLeft, nTop, sWText); // 상단 둘째줄 var nnn: Integer := nLeft + png.Canvas.TextWidth(sWText); sWText := sBottomText; nTop := png.Canvas.TextHeight(sWText) div 2; png.Canvas.TextOut(nLeft, nTop, sWText); // 상단 첫째줄 왼쪽 var nBottom: Integer := png.Height - (png.Canvas.TextHeight(sWText) div 2) - (nTextH + Round(nTextH / 5)) - nTextH; png.Canvas.TextOut(nLeft, nBottom, sWText); // 하단 첫째줄 왼쪽 var nLeft2: Integer; sWText := '이 문서는 SK ecoplant 의 보안정책 및 관련 법령에 의해 보호를 받는 정보자산으로 승인 없는 열람, 복사, 수정, 배포를 금지합니다.'; if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft2 := (nnn - ((nnn - nW) div 2)) - png.Canvas.TextWidth(sBottomText) else nLeft2 := nnn - png.Canvas.TextWidth(sWText); png.Canvas.TextOut(nLeft2, nTop, sWText); // 상단 첫째줄 오른쪽 png.Canvas.TextOut(nLeft2, nBottom, sWText); // 하단 첫째줄 오른쪽 sWText := 'This document is the informational asset protected by SK ecoplant security and law. Unauthorized access, copy, revision, distribution are strictly prohibited'; Inc(nBottom, nTextH + Round(nTextH / 5)); png.Canvas.TextOut(nLeft, nBottom, sWText); // 하단 둘째줄 end; CUSTOMER_SANKYO : begin png.Canvas.Font.Color := clGray; // 좌측 상단 sWText := sBottomText; if (png.Width > nW) and (WInfo.sPdfPath = '') then png.Canvas.TextOut((png.Width - nW) div 2, 0, sWText) else png.Canvas.TextOut(0, 0, sWText); // 가운데 하단 sWText := '본 문서는 한국다이이찌산쿄의 정보자산이며, 본 문서의 무단 유출/복사/도용 시 당사 사규와 관련 법규에 의해 제재 받을 수 있습니다.'; if (png.Width > nW) and (WInfo.sPdfPath = '') then nLeft := ((png.Width - ((png.Width - nW) div 2)) div 2) - (png.Canvas.TextWidth(sWText) div 2) else nLeft := (png.Width div 2) - (png.Canvas.TextWidth(sWText) div 2); png.Canvas.TextOut(nLeft, nTop, sWText); end; CUSTOMER_SERVE1 : begin if bmpWaterP = nil then begin var bmp: TBitmap; Guard(bmp, TBitmap.Create); var sImgPath: String := GetRunExePathDir + DIR_CONF + 'CI.bmp'; if FileExists(sImgPath) then begin try bmp.Canvas.Font.Assign(png.Canvas.Font); bmp.Canvas.Font.Name := 'Tahoma'; // 맑은 고딕'; bmp.Canvas.Font.Size := GetDPI_Size(60); bmp.Canvas.Font.Style := bmp.Canvas.Font.Style + [fsBold]; bmp.PixelFormat := pf4bit; // 이거 켜면 흑백 출력시 안됨 24_0807 15:52:56 kku bmp.LoadFromFile(sImgPath); // LogToReg('BW-01', BooleanToStr(gAppHook.Helper.CurAppType = catWebb, 'YES', 'NO')); bmp.TransparentColor := clWhite; bmp.Transparent := true; var nBW: Integer; if bmp.Canvas.TextWidth(sBottomText) > bmp.Width then nBW := bmp.Canvas.TextWidth(sBottomText) else nBW := bmp.Width; bmpWaterP := TBitmap.Create; bmpWaterP.Canvas.Font.Assign(bmp.Canvas.Font); bmpWaterP.PixelFormat := pf4bit; bmpWaterP.SetSize(nBW + 10, bmp.Canvas.TextHeight(sBottomText) + bmp.Height + 40); bmpWaterP.Canvas.Brush.Color := clWhite; bmpWaterP.Canvas.Brush.Style := bsSolid; bmpWaterP.Canvas.TextOut(0, bmpWaterP.Height - bmp.Canvas.TextHeight(sBottomText), sBottomText); if bmpWaterP.Width > bmp.Width then bmpWaterP.Canvas.Draw(bmpWaterP.Width - (bmpWaterP.Width div 2) - (bmp.Width div 2), 0, bmp) else bmpWaterP.Canvas.Draw(0, 0, bmp); RotateBitmap_PlgBlt(bmpWaterP, -0.6, true, clWhite); ScalePercentBmp(bmpWaterP, 140); except // .. end; end; end; if bmpWaterP <> nil then begin var cTrMatrix: TColorMatrix; ZeroMemory(@cTrMatrix, SizeOf(cTrMatrix)); cTrMatrix := MakeColorMatrix(0.2, 0.2, 0.2, 0.12); // Dec(nW, nGapW); // Dec(nH, nGapH); var nX := (nW div 4) - (bmpWaterP.Width div 2); var nY := (nH div 4) - (bmpWaterP.Height div 2); DrawBitmapWaterEx(png.Canvas.Handle, nX, nY, bmpWaterP, @cTrMatrix); end; end; else begin png.Canvas.TextOut(nLeft, nTop, sBottomText); if CUSTOMER_TYPE <> CUSTOMER_SOLIDEO then begin // 프린터 문서 이름 추가 23_0826 15:51:34 kku if (png.Width > nW) and (WInfo.sPdfPath = '') then png.Canvas.TextOut((png.Width - nW) div 2, nTop, Format('%s', [WInfo.sDocName])) else png.Canvas.TextOut(0, nTop, Format('%s', [WInfo.sDocName])); end; end; end; end; end; // bmp.SaveToFile('C:\Users\kku\Desktop\새 폴더\test.bmp'); // png.SaveToFile('C:\Users\kku\Desktop\새 폴더\test.png'); // pngW.SaveToFile('C:\Users\kku\Desktop\새 폴더\test2.png'); // ZeroMemory(@pngRect, SizeOf(pngRect)); // pngRect.Right := png.Width; // nW; // pngRect.Bottom := png.Height; // nH; // Printer.Canvas.StretchDraw(pngRect, bmp); (* ImgEn.IO.Bitmap.Assign(png); var nLIdx := ImgEn.LayersAdd; ImgEn.Proc.Fill(TColor2TRGB(clWhite)); ImgEn.Proc.SetTransparentColors(TColor2TRGB(clWhite), TColor2TRGB(clWhite), 0); // ImgEn.Proc.TextOut(0, png.Height - (png.Height div 3) - 200, // Format('%s %s' + #13#10 + 'ToCSG - BSOne', [GetHostIp, GetComName]), F, 40); if png.Width > png.Height then ImgEn.Proc.TextOut(300 {600}, png.Height - (png.Height div 3) - 200, //400, Format('%s %s' + #13#10 + 'ToCSG - BSOne', [GetHostIp, GetComName]), F, 20) else ImgEn.Proc.TextOut(0, png.Height - (png.Height div 3) - 100, //200, Format('%s %s' + #13#10 + 'ToCSG - BSOne', [GetHostIp, GetComName]), F, 40); // ImgEn.Proc.TextOut(500, png.Height - (png.Height div 3) - 700, Format('%s %s' + #13#10 + 'ToCSG - BSOne', [GetHostIp, GetComName]), F, 25); // ImgEn.Proc.TextOut(500, png.Height - ((png.Height div 3) * 2) - 700, Format('%s %s' + #13#10 + 'ToCSG - BSOne', [GetHostIp, GetComName]), F, 25); // ImgEn.Proc.TextOut(500, png.Height - 700, Format('%s %s' + #13#10 + 'ToCSG - BSOne', [GetHostIp, GetComName]), F, 25); ImgEn.Layers[nLIdx].Transparency := 100; ImgEn.LayersMerge(0, 1); ImgEn.Update; *) if not PWC.bActive then // 워터마크 설정을 사용하면 아래 무시 25_0728 14:38:41 kku case CUSTOMER_TYPE of // CUSTOMER_DEV, CUSTOMER_ALADIN : begin if png.Width < png.Height then SetImgFontSize(png.Width div 40) else SetImgFontSize(png.Height div 40); // png.Canvas.Font.Name := '돋음'; // 폰트 지정하면 출력 안되는 현상이 있다? 24_0509 13:17:25 kku png.Canvas.Font.Style := png.Canvas.Font.Style + [fsBold]; var sText: String := GetEmpNo + '/' + GetIpAddr + '/' + FormatDateTime('yyyy-mm-dd', Now); if png.Width < png.Height then sText := sText + WORD_GAP + sText + WORD_GAP + sText else sText := sText + WORD_GAP + sText + WORD_GAP + sText + WORD_GAP + sText; var bmpT: TBitmap; Guard(bmpT, TBitmap.Create); bmpT.PixelFormat := pf4bit; bmpT.SetSize(png.Canvas.TextWidth(sText), png.Canvas.TextHeight(sText)); bmpT.Canvas.Font := png.Canvas.Font; bmpT.Canvas.Font.Color := clSilver; bmpT.Canvas.TextOut(0, 0, sText); bmpT.TransparentColor := clWhite; bmpT.Transparent := true; // bmpT.SaveToFile('c:\1.bmp'); RotateBitmap_PlgBlt(bmpT, -0.45, true, clWhite); var cTrMatrix: TColorMatrix; ZeroMemory(@cTrMatrix, SizeOf(cTrMatrix)); // 회색 cTrMatrix[0][0] := 0.299; cTrMatrix[0][1] := 0.299; cTrMatrix[0][2] := 0.299; cTrMatrix[1][0] := 0.587; cTrMatrix[1][1] := 0.587; cTrMatrix[1][2] := 0.587; cTrMatrix[2][0] := 0.114; cTrMatrix[2][1] := 0.114; cTrMatrix[2][2] := 0.114; cTrMatrix[3][3] := 0.242; // 투명도 1.0 ~ 2.22 cTrMatrix[4][4] := 1.0; var nHH := png.Height div 2; var nGapH: Integer := bmpT.Height; var c: Integer := (nGapH div 2) * -1; while c < nHH + nGapH do begin DrawBitmapWaterEx(png.Canvas.Handle, 0, c, bmpT, @cTrMatrix); Inc(c, Round(nGapH / 1.5)); end; end; CUSTOMER_KBIZ : begin SetBkMode(png.Canvas.Handle, TRANSPARENT); SetImgFontSize(54); png.Canvas.Font.Color := clSilver; if (png.Height > nH) and (WInfo.sPdfPath = '') then // 이거 왜 이렇게 했는지... 까먹음.. 24_0626 14:18:50 kku nTop := (png.Height - ((png.Height - nH) div 2)) - png.Canvas.TextHeight(sBottomText) else nTop := png.Height - png.Canvas.TextHeight(sBottomText); sBottomText := Format('%s %s', [GetEmpNo, FormatDateTime('yyyy-mm-dd hh:nn:ss', Now)]); if (png.Width > nW) and (WInfo.sPdfPath = '') then png.Canvas.TextOut((png.Width - nW) div 2, nTop, sBottomText) else png.Canvas.TextOut(0, nTop, sBottomText); if png.Width < png.Height then SetImgFontSize(png.Width div 18) else SetImgFontSize(png.Height div 18); png.Canvas.Font.Style := png.Canvas.Font.Style + [fsBold]; var sText: String := 'KBIZ'; var bmpW: TBitmap; Guard(bmpW, TBitmap.Create); bmpW.SetSize(png.Canvas.TextWidth(sText), png.Canvas.TextHeight(sText)); bmpW.Canvas.Font.Assign(png.Canvas.Font); bmpW.Canvas.Font.Color := clSilver; bmpW.Canvas.TextOut(0, 0, sText); bmpW.TransparentColor := clWhite; bmpW.Transparent := true; RotateBitmap_PlgBlt(bmpW, -0.8, true, clWhite); var cTrMatrix: TColorMatrix; ZeroMemory(@cTrMatrix, SizeOf(cTrMatrix)); // 회색 // cTrMatrix[0][0] := 0.299; // cTrMatrix[0][1] := 0.299; // cTrMatrix[0][2] := 0.299; // cTrMatrix[1][0] := 0.587; // cTrMatrix[1][1] := 0.587; // cTrMatrix[1][2] := 0.587; // cTrMatrix[2][0] := 0.114; // cTrMatrix[2][1] := 0.114; // cTrMatrix[2][2] := 0.114; // cTrMatrix[3][3] := 0.23; // 투명도 1.0 ~ 2.22 // cTrMatrix[4][4] := 1.0; cTrMatrix := MakeColorMatrix(0.2, 0.2, 0.2, 0.05); // 가운데 // var nX: Integer := png.Width - (png.Width div 2) - (bmpW.Width div 2); // var nY: Integer := png.Height - (png.Height div 2) - (bmpW.Height div 2); // DrawBitmapWaterEx(png.Canvas.Handle, nX, nY, bmpW, @cTrMatrix); // 왼쪽위 DrawBitmapWaterEx(png.Canvas.Handle, 0, 0, bmpW, @cTrMatrix); // 오른쪽아래 var nX: Integer := png.Width - bmpW.Width; var nY: Integer := png.Height - bmpW.Height; DrawBitmapWaterEx(png.Canvas.Handle, nX, nY, bmpW, @cTrMatrix); end; CUSTOMER_JUVIS : begin if png.Width < png.Height then SetImgFontSize(png.Width div 9) else SetImgFontSize(png.Height div 9); // png.Canvas.Font.Name := '돋음'; // 폰트 지정하면 출력 안되는 현상이 있다? 24_0509 13:17:25 kku png.Canvas.Font.Style := png.Canvas.Font.Style + [fsBold]; // var sText: String := '쥬비스 다이어트'; var sText: String := 'JUVIS DIET'; var bmpW: TBitmap; Guard(bmpW, TBitmap.Create); bmpW.SetSize(png.Canvas.TextWidth(sText), png.Canvas.TextHeight(sText)); bmpW.Canvas.Font := png.Canvas.Font; bmpW.Canvas.Font.Color := clSilver; bmpW.Canvas.TextOut(0, 0, sText); bmpW.TransparentColor := clWhite; bmpW.Transparent := true; RotateBitmap_PlgBlt(bmpW, -0.8, true, clWhite); var cTrMatrix: TColorMatrix; ZeroMemory(@cTrMatrix, SizeOf(cTrMatrix)); // 회색 cTrMatrix[0][0] := 0.299; cTrMatrix[0][1] := 0.299; cTrMatrix[0][2] := 0.299; cTrMatrix[1][0] := 0.587; cTrMatrix[1][1] := 0.587; cTrMatrix[1][2] := 0.587; cTrMatrix[2][0] := 0.114; cTrMatrix[2][1] := 0.114; cTrMatrix[2][2] := 0.114; cTrMatrix[3][3] := 0.22; // 투명도 1.0 ~ 2.22 cTrMatrix[4][4] := 1.0; var nX: Integer := png.Width - (png.Width div 2) - (bmpW.Width div 2); var nY: Integer := png.Height - (png.Height div 2) - (bmpW.Height div 2); DrawBitmapWaterEx(png.Canvas.Handle, nX, nY, bmpW, @cTrMatrix); end; // CUSTOMER_DEMO, CUSTOMER_WELFND, CUSTOMER_WELFNI, CUSTOMER_SHCI, CUSTOMER_SHSC, CUSTOMER_KORENTAL, CUSTOMER_WINSTN, CUSTOMER_SKEC, CUSTOMER_SANKYO : begin Result := false; var sImgPath: String := GetRunExePathDir + DIR_CONF + 'CI.bmp'; if FileExists(sImgPath) then begin try var bmpW: TBitmap; Guard(bmpW, TBitmap.Create); bmpW.LoadFromFile(sImgPath); bmpW.PixelFormat := pf4bit; bmpW.TransparentColor := clWhite; bmpW.Transparent := true; if CUSTOMER_TYPE = CUSTOMER_SKEC then ScalePercentBmp(bmpW, GetDPI_Size(120)) else ScalePercentBmp(bmpW, GetDPI_Size(300)); var cTrMatrix: TColorMatrix := MakeColorMatrix(0.2, 0.2, 0.2, 0.05); var nX: Integer := png.Width - (png.Width div 2) - (bmpW.Width div 2); var nY: Integer := png.Height - (png.Height div 2) - (bmpW.Height div 2); DrawBitmapWaterEx(png.Canvas.Handle, nX, nY, bmpW, @cTrMatrix); except // .. end; end; end; CUSTOMER_GEC : begin if bmpWaterP = nil then begin var sImgPath: String := GetRunExePathDir + DIR_CONF + 'HWMJ.dat'; if FileExists(sImgPath) then begin var sText: String := ''; if GetDeptName <> '' then sText := GetDeptName + '/' + GetEmpNo + '/' + GetIpAddr + '/' + FormatDateTime('yyyy-mm-dd', Now) else sText := GetEmpNo + '/' + GetIpAddr + '/' + FormatDateTime('yyyy-mm-dd', Now); var nFontSize: Integer := png.Canvas.Font.Size; while True do begin if nFontSize > 200 then break; if png.Canvas.TextHeight(sText) > 180 then // 부서명이 들어간 후 2000에서 변경 begin Dec(nFontSize); break; end; Inc(nFontSize); png.Canvas.Font.Size := nFontSize; end; var jpg: TJPEGImage; jpg := TJPEGImage.Create; jpg.LoadFromFile(sImgPath); var bmpImg: TBitmap; bmpImg := TBitmap.Create; bmpImg.Assign(jpg); jpg.Free; // Free bmpImg.Canvas.Font.Assign(png.Canvas.Font); bmpImg.Canvas.Font.Color := clSilver; bmpImg.Canvas.Font.Size := nFontSize - (nFontSize div 2); bmpImg.Canvas.Font.Style := bmpImg.Canvas.Font.Style + [fsBold]; //--- // sOut := '정보보호부문/2323308/10.177.15.123/2023-12-31'; // HEC 새로운 요구사항 반영 23_1121 10:22:09 kku // bmpImg.Canvas.Font.Size := bmpImg.Canvas.Font.Size + 14; // ScalePercentBmp(bmpImg, 120); //--- var nWW := bmpImg.Canvas.TextWidth(sText); if bmpImg.Width > nWW then nWW := bmpImg.Width; var nHH := bmpImg.Height + bmpImg.Canvas.TextHeight(sText); bmpWaterP := TBitmap.Create; bmpWaterP.Canvas.Font.Assign(bmpImg.Canvas.Font); bmpWaterP.PixelFormat := pf4bit; bmpWaterP.SetSize(nWW, nHH); bmpWaterP.Canvas.Brush.Color := clWhite; bmpWaterP.Canvas.Brush.Style := bsSolid; bmpWaterP.Canvas.FillRect(Rect(0, 0, bmpWaterP.Width, bmpWaterP.Height)); bmpWaterP.Canvas.Draw((nWW div 2) - (bmpImg.Width div 2), 0, bmpImg); bmpWaterP.Canvas.TextOut(0, bmpImg.Height, sText); bmpImg.Free; // Free RotateBitmap_PlgBlt(bmpWaterP, -0.7, true, clWhite); var ii: Integer; var jj: Integer; for ii := 0 to bmpWaterP.Width - 1 do for jj := 0 to bmpWaterP.Height - 1 do if bmpWaterP.Canvas.Pixels[ii, jj] <> clWhite then bmpWaterP.Canvas.Pixels[ii, jj] := clGray; // ScalePercentBmp(_bmpWaterP, 60); // ScalePercentBmp(_bmpWaterP, 130); // 늘리는거 쓰면 이미지가 빈값이 되는 문제가 있음 24_0514 08:30:40 kku bmpWaterP.TransparentColor := clWhite; bmpWaterP.Transparent := true; end; end; if bmpWaterP <> nil then begin // 추가 24_0626 17:31:52 kku var cTrMatrix: TColorMatrix; ZeroMemory(@cTrMatrix, SizeOf(cTrMatrix)); // 회색 cTrMatrix[0][0] := 0.299; cTrMatrix[0][1] := 0.299; cTrMatrix[0][2] := 0.299; cTrMatrix[1][0] := 0.587; cTrMatrix[1][1] := 0.587; cTrMatrix[1][2] := 0.587; cTrMatrix[2][0] := 0.114; cTrMatrix[2][1] := 0.114; cTrMatrix[2][2] := 0.114; cTrMatrix[3][3] := 0.22; // 투명도 1.0 ~ 2.22 cTrMatrix[4][4] := 1.0; var nIW: Integer := png.Width; var nIH: Integer := png.Height; var nX := (nIW div 2) - (bmpWaterP.Width div 2); var nY := (nIH div 2) - (nIH div 3); DrawBitmapWaterEx(png.Canvas.Handle, nX, nY, bmpWaterP, @cTrMatrix); nY := (nIH div 2) + (nIH div 10); DrawBitmapWaterEx(png.Canvas.Handle, nX, nY, bmpWaterP, @cTrMatrix); // bmpWaterP.SaveToFile('c:\0.bmp'); // png.SaveToFile('c:\1.png'); SetBkMode(png.Canvas.Handle, TRANSPARENT); png.Canvas.Font.Color := clGray; SetImgFontSize(Round(bmpWaterP.Canvas.Font.Size * 1.3)); sBottomText := GetLabelName; // '대외비(Restricted)'; if sBottomText <> '' then begin nLeft := png.Width - png.Canvas.TextWidth(sBottomText); nTop := 0; png.Canvas.TextOut(nLeft, nTop, sBottomText); end; sBottomText := 'Security Starts with Small Habits'; nLeft := png.Width - png.Canvas.TextWidth(sBottomText); nTop := png.Height - png.Canvas.TextHeight(sBottomText); png.Canvas.TextOut(nLeft, nTop, sBottomText); SetImgFontSize(bmpWaterP.Canvas.Font.Size div 2); sBottomText := 'This document or drawing is the property of Hyundai Engineering. Any reproduction or distribution of the materials without permission of Hyundai engineering is strictly prohibited.'; nLeft := 0; nTop := png.Height - png.Canvas.TextHeight(sBottomText); png.Canvas.TextOut(0, nTop, sBottomText); // png.SaveToFile('c:\2.png'); end; end; else Result := false; end; // 용지를 출력 옵션대로 변경하기 때문에 다시 원래대로 안돌려도 된다 25_0904 10:09:55 kku // if bRotate then // begin // nTmp := nW; // nW := nH; // nH := nTmp; // RotatePng(png, -90); // end; if Result then begin StretchBlt(aDest, 0, 0, nW, nH, png.Canvas.Handle, 0, 0, png.Width, png.Height, SRCCOPY); end; except on E: Exception do begin Result := false; ETgException.TraceException(E, 'Fail .. ProcessWatermarkToImage()'); end; end; end; end.