NonInventPurchasingSystem/CPRNIMS.Domain/UIServices/CaptCha/CaptchaService.cs
2026-01-20 07:44:30 +08:00

79 lines
2.5 KiB
C#

using CPRNIMS.Domain.UIContracts.CaptCha;
using System;
using System.Collections.Generic;
using System.Drawing.Imaging;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace CPRNIMS.Domain.UIServices.CaptCha
{
public class CaptchaService : ICaptchaService
{
private readonly Random _random = new Random();
public (string code, byte[] image) GenerateCaptcha()
{
// Generate random code
string captchaCode = GenerateRandomCode();
// Create image from code
using (var bitmap = new Bitmap(150, 50))
using (var graphics = Graphics.FromImage(bitmap))
using (var memoryStream = new MemoryStream())
{
graphics.Clear(Color.White);
// Add noise and pattern
AddNoise(graphics, bitmap.Width, bitmap.Height);
// Draw the text
using (var font = new Font("Arial", 20, FontStyle.Bold))
{
graphics.DrawString(captchaCode, font, Brushes.Black, 10, 10);
}
// Add some random lines for more security
AddRandomLines(graphics, bitmap.Width, bitmap.Height);
// Save to memory stream as PNG
bitmap.Save(memoryStream, ImageFormat.Png);
return (captchaCode, memoryStream.ToArray());
}
}
private string GenerateRandomCode()
{
// Generate a code of 6 characters (letters and numbers)
const string chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
return new string(Enumerable.Repeat(chars, 6)
.Select(s => s[_random.Next(s.Length)]).ToArray());
}
private void AddNoise(Graphics graphics, int width, int height)
{
// Add random pixels
for (int i = 0; i < 50; i++)
{
int x = _random.Next(width);
int y = _random.Next(height);
graphics.DrawRectangle(Pens.LightGray, x, y, 1, 1);
}
}
private void AddRandomLines(Graphics graphics, int width, int height)
{
// Add random lines
for (int i = 0; i < 5; i++)
{
int x1 = _random.Next(width);
int y1 = _random.Next(height);
int x2 = _random.Next(width);
int y2 = _random.Next(height);
graphics.DrawLine(Pens.Gray, x1, y1, x2, y2);
}
}
}
}