如题,我根据资料写出的程序如下,自己加了trackbar调整,但拖动滑块时容易把图像调花,怎么才能平滑调整呢?请高手指点。代码如下:procedure HSLtoRGB(H, S, L: Integer; var R, G, B: Integer);
//hsl颜色空间到rgb空间的转换
var //类似于返回多个值的函数
Sat, Lum: Double;
begin
R := 0;
G := 0;
B := 0;
if (H < 360) and (H >= 0) and (S <= 100) and (S >= 0) and (L <= 100) and (L
>=
0) then
begin
if H <= 60 then
begin
R := 255;
G := Round((255 / 60) * H);
B := 0;
end
else if H <= 120 then
begin
R := Round(255 - (255 / 60) * (H - 60));
G := 255;
B := 0;
end
else if H <= 180 then
begin
R := 0;
G := 255;
B := Round((255 / 60) * (H - 120));
end
else if H <= 240 then
begin
R := 0;
G := Round(255 - (255 / 60) * (H - 180));
B := 255;
end
else if H <= 300 then
begin
R := Round((255 / 60) * (H - 240));
G := 0;
B := 255;
end
else if H < 360 then
begin
R := 255;
G := 0;
B := Round(255 - (255 / 60) * (H - 300));
end; Sat := Abs((S - 100) / 100);
R := Round(R - ((R - 128) * Sat));
G := Round(G - ((G - 128) * Sat));
B := Round(B - ((B - 128) * Sat)); Lum := (L - 50) / 50;
if Lum > 0 then
begin
R := Round(R + ((255 - R) * Lum));
G := Round(G + ((255 - G) * Lum));
B := Round(B + ((255 - B) * Lum));
end
else if Lum < 0 then
begin
R := Round(R + (R * Lum));
G := Round(G + (G * Lum));
B := Round(B + (B * Lum));
end;
end;
end;procedure RGBtoHSL(R, G, B: Integer; var H, S, L: Integer);
// RGB空间到HSL空间的转换
var
Delta: Double;
CMax, CMin: Double;
Red, Green, Blue, Hue, Sat, Lum: Double;
begin
Red := R / 255;
Green := G / 255;
Blue := B / 255;
CMax := Max(Red, Max(Green, Blue));
CMin := Min(Red, Min(Green, Blue));
Lum := (CMax + CMin) / 2;
if CMax = CMin then
begin
Sat := 0;
Hue := 0;
end
else
begin
if Lum < 0.5 then
Sat := (CMax - CMin) / (CMax + CMin)
else
Sat := (cmax - cmin) / (2 - cmax - cmin);
delta := CMax - CMin;
if Red = CMax then
Hue := (Green - Blue) / Delta
else if Green = CMax then
Hue := 2 + (Blue - Red) / Delta
else
Hue := 4.0 + (Red - Green) / Delta;
Hue := Hue / 6;
if Hue < 0 then
Hue := Hue + 1;
end;
H := Round(Hue * 360);
S := Round(Sat * 100);
L := Round(Lum * 100);
end;
//亮度调节
procedure TFormMain.TrackBarBrightnessChange(Sender: TObject);
var
bmp: TBITMAP;
x, y, ScanlineBytes,i,DeltaP: integer;
p: prgbtriplearray;
RVALUE, bvalue, gvalue: integer;
hVALUE, sVALUE, lVALUE: integer;
begin
self.DoubleBuffered := true;
//设置双缓冲
if imgCarPhoto.Picture.Graphic <> nil then
else
begin
TrackBarBrightness.Position:=50;
OriginalBrightnessPosition:=TrackBarBrightness.Position;
Label6.Caption:='亮度 ' + IntToStr(OriginalBrightnessPosition);
exit;
end; bmp := TBITMAP.Create;
bmp.Assign(imgCarPhoto.Picture.Bitmap);
//加载位图
bmp.PixelFormat := pf24bit;
//指定为24位
p := bmp.ScanLine[0];
ScanlineBytes := integer(bmp.ScanLine[1]) - integer(bmp.ScanLine[0]);
//获取两行间距,此法只需执行Scanline两次,速度快,是优化的 i:=TrackBarBrightness.Position;
DeltaP:=i - OriginalBrightnessPosition;
OriginalBrightnessPosition:=i;
Label6.Caption:='亮度 ' + IntToStr(i); for y := 0 to bmp.Height - 1 do
begin
for x := 0 to bmp.Width - 1 do
begin
//获取RGB的三个分量值,并进行赋值
RVALUE := p[x].rgbtRed;
gVALUE := p[x].rgbtGreen;
bVALUE := p[x].rgbtBlue;
// 调用前面的RGB转HSL过程,获取HSL三个分量值
RGBtoHSL(RVALUE, gVALUE, bVALUE, hVALUE, sVALUE, lVALUE);
//饱和度值进行线性调节。
lVALUE := lVALUE + DeltaP;
lVALUE := min(100, lVALUE);
lVALUE := max(0, lVALUE);
//下面两行是饱和度度减小操作
//SVALUE := SVALUE - 5;
//调用前面的HSL空间转RGB颜色空间的过程,获得RGB三个分量
HSLtorgb(hVALUE, sVALUE, lVALUE, rVALUE, gVALUE, bVALUE);
p[x].rgbtRed := RVALUE;
p[x].rgbtGreen := gVALUE;
p[x].rgbtBlue := bVALUE;
end;
inc(integer(p), ScanlineBytes) //指针递增
end;
imgCarPhoto.Picture.Bitmap.Assign(bmp);
Bmp.Free;
end;
//对比度调节
procedure TFormMain.TrackBarContrastChange(Sender: TObject);
var
p: PByteArray;
x, y, i, DeltaP: Integer;
Bmp: TBitmap;
begin
self.DoubleBuffered := true;
//设置双缓冲
if imgCarPhoto.Picture.Graphic <> nil then
else
begin
TrackBarContrast.Position:=128;
OriginalContrastPosition:=TrackBarContrast.Position;
Label5.Caption:='对比度 ' + IntToStr(OriginalContrastPosition);
exit;
end; Bmp := TBitmap.Create;
Bmp.Assign(ImgCarPhoto.Picture.Bitmap);
Bmp.PixelFormat := pf24Bit; i:=TrackBarContrast.Position;
DeltaP:=i - OriginalContrastPosition;
OriginalContrastPosition:=i;
Label5.Caption:='对比度 ' + IntToStr(i);
for y := 0 to Bmp.Height - 1 do
begin
p := Bmp.scanline[y];
for x := 0 to Bmp.Width - 1 do
begin
//确定阀值为128
if (p[x * 3] < 246) and (p[x * 3] > 128) and (p[x * 3 + 1] >
128)
and (p[x * 3 + 1] < 246)
and (p[x * 3 + 2] > 128) and (p[x * 3 + 2] < 246) then
begin
p[x * 3] := Min(246, Max(128, p[x * 3] + DeltaP));
p[x * 3 + 1] := Min(246, Max(128, p[x * 3 + 1] + DeltaP));
p[x * 3 + 2] := Min(246, Max(128, p[x * 3 + 2] + DeltaP));
end;
if (p[x * 3] > 10) and (p[x * 3] < 128) and (p[x * 3 + 1] >
10)
and (p[x *
3 + 1] < 128)
and (p[x * 3 + 2] > 10) and (p[x * 3 + 2] < 128) then
begin
p[x * 3] := Min(128, Max(10, p[x * 3] - DeltaP));
p[x * 3 + 1] := Min(128, Max(10, p[x * 3 + 1] - DeltaP));
p[x * 3 + 2] := Min(128, Max(10, p[x * 3 + 2] - DeltaP));
end;
end;
end;
ImgCarPhoto.Picture.Bitmap.Assign(Bmp);
Bmp.Free;
end;
//hsl颜色空间到rgb空间的转换
var //类似于返回多个值的函数
Sat, Lum: Double;
begin
R := 0;
G := 0;
B := 0;
if (H < 360) and (H >= 0) and (S <= 100) and (S >= 0) and (L <= 100) and (L
>=
0) then
begin
if H <= 60 then
begin
R := 255;
G := Round((255 / 60) * H);
B := 0;
end
else if H <= 120 then
begin
R := Round(255 - (255 / 60) * (H - 60));
G := 255;
B := 0;
end
else if H <= 180 then
begin
R := 0;
G := 255;
B := Round((255 / 60) * (H - 120));
end
else if H <= 240 then
begin
R := 0;
G := Round(255 - (255 / 60) * (H - 180));
B := 255;
end
else if H <= 300 then
begin
R := Round((255 / 60) * (H - 240));
G := 0;
B := 255;
end
else if H < 360 then
begin
R := 255;
G := 0;
B := Round(255 - (255 / 60) * (H - 300));
end; Sat := Abs((S - 100) / 100);
R := Round(R - ((R - 128) * Sat));
G := Round(G - ((G - 128) * Sat));
B := Round(B - ((B - 128) * Sat)); Lum := (L - 50) / 50;
if Lum > 0 then
begin
R := Round(R + ((255 - R) * Lum));
G := Round(G + ((255 - G) * Lum));
B := Round(B + ((255 - B) * Lum));
end
else if Lum < 0 then
begin
R := Round(R + (R * Lum));
G := Round(G + (G * Lum));
B := Round(B + (B * Lum));
end;
end;
end;procedure RGBtoHSL(R, G, B: Integer; var H, S, L: Integer);
// RGB空间到HSL空间的转换
var
Delta: Double;
CMax, CMin: Double;
Red, Green, Blue, Hue, Sat, Lum: Double;
begin
Red := R / 255;
Green := G / 255;
Blue := B / 255;
CMax := Max(Red, Max(Green, Blue));
CMin := Min(Red, Min(Green, Blue));
Lum := (CMax + CMin) / 2;
if CMax = CMin then
begin
Sat := 0;
Hue := 0;
end
else
begin
if Lum < 0.5 then
Sat := (CMax - CMin) / (CMax + CMin)
else
Sat := (cmax - cmin) / (2 - cmax - cmin);
delta := CMax - CMin;
if Red = CMax then
Hue := (Green - Blue) / Delta
else if Green = CMax then
Hue := 2 + (Blue - Red) / Delta
else
Hue := 4.0 + (Red - Green) / Delta;
Hue := Hue / 6;
if Hue < 0 then
Hue := Hue + 1;
end;
H := Round(Hue * 360);
S := Round(Sat * 100);
L := Round(Lum * 100);
end;
//亮度调节
procedure TFormMain.TrackBarBrightnessChange(Sender: TObject);
var
bmp: TBITMAP;
x, y, ScanlineBytes,i,DeltaP: integer;
p: prgbtriplearray;
RVALUE, bvalue, gvalue: integer;
hVALUE, sVALUE, lVALUE: integer;
begin
self.DoubleBuffered := true;
//设置双缓冲
if imgCarPhoto.Picture.Graphic <> nil then
else
begin
TrackBarBrightness.Position:=50;
OriginalBrightnessPosition:=TrackBarBrightness.Position;
Label6.Caption:='亮度 ' + IntToStr(OriginalBrightnessPosition);
exit;
end; bmp := TBITMAP.Create;
bmp.Assign(imgCarPhoto.Picture.Bitmap);
//加载位图
bmp.PixelFormat := pf24bit;
//指定为24位
p := bmp.ScanLine[0];
ScanlineBytes := integer(bmp.ScanLine[1]) - integer(bmp.ScanLine[0]);
//获取两行间距,此法只需执行Scanline两次,速度快,是优化的 i:=TrackBarBrightness.Position;
DeltaP:=i - OriginalBrightnessPosition;
OriginalBrightnessPosition:=i;
Label6.Caption:='亮度 ' + IntToStr(i); for y := 0 to bmp.Height - 1 do
begin
for x := 0 to bmp.Width - 1 do
begin
//获取RGB的三个分量值,并进行赋值
RVALUE := p[x].rgbtRed;
gVALUE := p[x].rgbtGreen;
bVALUE := p[x].rgbtBlue;
// 调用前面的RGB转HSL过程,获取HSL三个分量值
RGBtoHSL(RVALUE, gVALUE, bVALUE, hVALUE, sVALUE, lVALUE);
//饱和度值进行线性调节。
lVALUE := lVALUE + DeltaP;
lVALUE := min(100, lVALUE);
lVALUE := max(0, lVALUE);
//下面两行是饱和度度减小操作
//SVALUE := SVALUE - 5;
//调用前面的HSL空间转RGB颜色空间的过程,获得RGB三个分量
HSLtorgb(hVALUE, sVALUE, lVALUE, rVALUE, gVALUE, bVALUE);
p[x].rgbtRed := RVALUE;
p[x].rgbtGreen := gVALUE;
p[x].rgbtBlue := bVALUE;
end;
inc(integer(p), ScanlineBytes) //指针递增
end;
imgCarPhoto.Picture.Bitmap.Assign(bmp);
Bmp.Free;
end;
//对比度调节
procedure TFormMain.TrackBarContrastChange(Sender: TObject);
var
p: PByteArray;
x, y, i, DeltaP: Integer;
Bmp: TBitmap;
begin
self.DoubleBuffered := true;
//设置双缓冲
if imgCarPhoto.Picture.Graphic <> nil then
else
begin
TrackBarContrast.Position:=128;
OriginalContrastPosition:=TrackBarContrast.Position;
Label5.Caption:='对比度 ' + IntToStr(OriginalContrastPosition);
exit;
end; Bmp := TBitmap.Create;
Bmp.Assign(ImgCarPhoto.Picture.Bitmap);
Bmp.PixelFormat := pf24Bit; i:=TrackBarContrast.Position;
DeltaP:=i - OriginalContrastPosition;
OriginalContrastPosition:=i;
Label5.Caption:='对比度 ' + IntToStr(i);
for y := 0 to Bmp.Height - 1 do
begin
p := Bmp.scanline[y];
for x := 0 to Bmp.Width - 1 do
begin
//确定阀值为128
if (p[x * 3] < 246) and (p[x * 3] > 128) and (p[x * 3 + 1] >
128)
and (p[x * 3 + 1] < 246)
and (p[x * 3 + 2] > 128) and (p[x * 3 + 2] < 246) then
begin
p[x * 3] := Min(246, Max(128, p[x * 3] + DeltaP));
p[x * 3 + 1] := Min(246, Max(128, p[x * 3 + 1] + DeltaP));
p[x * 3 + 2] := Min(246, Max(128, p[x * 3 + 2] + DeltaP));
end;
if (p[x * 3] > 10) and (p[x * 3] < 128) and (p[x * 3 + 1] >
10)
and (p[x *
3 + 1] < 128)
and (p[x * 3 + 2] > 10) and (p[x * 3 + 2] < 128) then
begin
p[x * 3] := Min(128, Max(10, p[x * 3] - DeltaP));
p[x * 3 + 1] := Min(128, Max(10, p[x * 3 + 1] - DeltaP));
p[x * 3 + 2] := Min(128, Max(10, p[x * 3 + 2] - DeltaP));
end;
end;
end;
ImgCarPhoto.Picture.Bitmap.Assign(Bmp);
Bmp.Free;
end;
解决方案 »
- 十万火急啊 怎么取网页中指定标签中的,每个标签的内容。。。
- edit与数据库表里的一个字段判断代码该如何写?
- dephid的CheckBox取值问题
- 小弟有一个问题,现在有一个PageControl控件,有多个页面,现在我右击某一页,选种该页,请问如何做呢?在线等待.
- cxGrid主从表结构,但是如果数据比较多,我用全部展开会很慢。如何解决?
- 关于DELPHI 子窗口的问题
- 送分(QReport 显示问题)
- 一个修改的问题,请赐教!
- 关于在线程中使用回调函数以及C++静态成员的问题
- 关于toolbar的显示和关闭的问题,答对一定给分
- opendoc这个函数怎么写
- 具有WS_EX_NOACTIVATE风格的窗口在AttachThreadInput后失去焦点,怎么办?
var
p: PByteArray;
x, y, i, DeltaP: Integer;
Bmp: TBitmap;
begin
self.DoubleBuffered := true;
//设置双缓冲
if imgCarPhoto.Picture.Graphic <> nil then
else
begin
TrackBarContrast.Position:=128;
OriginalContrastPosition:=TrackBarContrast.Position;
Label5.Caption:='对比度 ' + IntToStr(OriginalContrastPosition);
exit;
end; Bmp := TBitmap.Create;
Bmp.Assign(ImgCarPhoto.Picture.Bitmap);
//这张肯定不是原图
Bmp.PixelFormat := pf24Bit; i:=TrackBarContrast.Position;
DeltaP:=i - OriginalContrastPosition;
OriginalContrastPosition:=i;
Label5.Caption:='对比度 ' + IntToStr(i);
for y := 0 to Bmp.Height - 1 do
begin
p := Bmp.scanline[y];
for x := 0 to Bmp.Width - 1 do
begin
//确定阀值为128
if (p[x * 3] < 246) and (p[x * 3] > 128) and (p[x * 3 + 1] >
128)
and (p[x * 3 + 1] < 246)
and (p[x * 3 + 2] > 128) and (p[x * 3 + 2] < 246) then
begin
p[x * 3] := Min(246, Max(128, p[x * 3] + DeltaP));
p[x * 3 + 1] := Min(246, Max(128, p[x * 3 + 1] + DeltaP));
p[x * 3 + 2] := Min(246, Max(128, p[x * 3 + 2] + DeltaP));
end;
if (p[x * 3] > 10) and (p[x * 3] < 128) and (p[x * 3 + 1] >
10)
and (p[x *
3 + 1] < 128)
and (p[x * 3 + 2] > 10) and (p[x * 3 + 2] < 128) then
begin
p[x * 3] := Min(128, Max(10, p[x * 3] - DeltaP));
p[x * 3 + 1] := Min(128, Max(10, p[x * 3 + 1] - DeltaP));
p[x * 3 + 2] := Min(128, Max(10, p[x * 3 + 2] - DeltaP));
end;
end;
end;
ImgCarPhoto.Picture.Bitmap.Assign(Bmp);
//你调整之后把结果图覆盖掉了,怎么会是原图!!!
Bmp.Free;
end;
你应该先备份一张原图,然后每次调用时,bmp.assign(原始图)而不是ImgCarPhoto.Picture.Bitmap这个