В Delphi написанный код:
result = (Image1.Canvas.Pixels[i, j] and $000000ff);
что это значит? И если возможно, пожалуйста, скажите, как я могу сделать такую же операцию в С#?
Отредактировано: Я не знаю, где проблема: я использую тот же алгоритм, но результат не эквивалентен или тот же .i думаю, что я не понимаю код delphi true!
Код Delphi:
procedure TForm1.Button1Click(Sender: TObject);
var
i,j:byte;
noise_mass: array [0..255,0..255] of byte;
BN,BST:real;
mu:real;
begin
mu:=0.75;
Randomize;
for i:=0 to 255 do
begin
for j:=0 to 255 do
begin
noise_mass[i,j]:=Random(255);
BN:=BN+sqr(noise_mass[i,j]);
BST:=BST+sqr(image1.Canvas.Pixels[i,j] and $000000ff);
end;
end;
for i:=0 to 255 do
begin
for j:=0 to 255 do
begin
image1.Canvas.Pixels[i,j]:=image1.Canvas.Pixels[i,j]+round(mu*noise_mass[i,j]*BST/BN);
end;
end;
end;
Код С#:
private Bitmap MakeNoise(Bitmap original)
{
double mu = 0.5;
Bitmap newBitmap = new Bitmap(256, 256);
double BN = 0, BST = 0;
byte[,] noise_mass = new byte[256, 256];
for (int i = 0; i <= 255; i++)
{
for (int j = 0; j <= 255; j++)
{
noise_mass[i, j] = (byte)(new System.Random(255)).Next();
BN = BN + Math.Pow(noise_mass[i, j], 2);
BST = BST + Math.Pow(original.GetPixel(i, j).R, 2);
}
}
for (int i = 0; i <= 255; i++)
{
for (int j = 0; j <= 255; j++)
{
int r = original.GetPixel(i, j).ToArgb() + (int)Math.Round(mu * noise_mass[i, j] * BST / BN);
Color c = Color.FromArgb(r);
newBitmap.SetPixel(i, j, c);
}
}
return newBitmap;
}
Нижний байт Значение Delphi TColor - это красный компонент. Если у вас есть System.Drawing.Bitmap, то то, что вы хотите, это следующее, которое использует Color, обладающая свойством для красной компоненты. Нет необходимости в каких-либо бит-трюках.
result = original.GetPixel(i, j).R;
Image1.Canvas.Pixels[i, j]
указывает цвет одного пикселя.&& $000000ff
сохраняет только R (ed) из значения RGB.В Delphi он предназначен для получения значения RED TColor. См. Некоторые цветовые константы в Графический блок:
(Более крупный список можно найти здесь).
Эти цвета имеют то же значение, что и родной ColorRef тип, используемый Windows, который имеет порядок в BGR (синий/зеленый/красный), или цвет системы (см. ниже). Обратите внимание, что .NET использует другой тип System.Drawing.Color: порядок - RGB (красный/зеленый/синий) и никаких системных цветов вообще.
Ваш код не будет работать для всех значений TColor, поскольку TColor может содержать два типа цветов:
Чтобы сделать сопоставление для всех возможных значений, вы должны использовать функцию ColorToRGB в графическом модуле (она преобразует системные цвета в правильные значения RGB).
В вашем конкретном случае это, вероятно, работает, потому что пиксели Canvas не могут содержать системные цвета, а только значения RGB.
Но: вы не должны использовать жестко закодированные литералы, такие как $000000FF, потому что трудно угадать их смысл.
Чтобы получить правильные значения красного/зеленого/синего, вы должны комбинировать функцию ColorToRGB с этими функциями в блоке Windows:
function GetRValue(rgb: DWORD): Byte; inline;
function GetGValue(rgb: DWORD): Byte; inline;
function GetBValue(rgb: DWORD): Byte; inline;
Итак, вы получили бы такую функцию, чтобы получить красную порцию универсальным способом в Delphi:
function GetRed(Color: TColor): Byte;
begin
Result := GetRValue(ColorToRGB(Color));
end;
Эта страница имеет хорошую ссылку на использование цвета в Delphi.
- Йерун
Пиксельные данные почти всегда ARGB в пространстве .NET. Учитывая, что у вас есть такие пиксельные координаты в массиве, вы могли:
UInt32 red = pixels[x+y*w] & 0xFFFF0000
& выполняет побитовое и. Первый FF должен содержать альфа-канал без изменений.
Next
, а не кRandom
.