Zmenšení obrázku v ASP.NET (vhodné například pro náhledy v galeriích (tzv. thumbnaily nebo miniatury))
- Vložil Trupík 3/24/2006 2:10:23 PM
-
Článek o
zmenšování obrázků v PHP
si už pár lidí přečetlo, takže předpokládám,
že je to užitečná technika. V tomto článku vám chci předvést, jak se ta samá
věc dá udělat v ASP.NET . Výsledkem článku tedy opět bude funkce použitelná
k vytváření náhledů (thumbnailů, miniatur) pro obrázky například na webových
galeriích nebo inzertních stránkách.
Proč se thumbnaily hodí jsem již popisoval v již zmíněném článku o zmenšování
obrázků v PHP. Ve zkratce proto, aby si návštěvník nemusel stahovat celý velký
obrázek jen proto, aby viděl jeho malý náhled. Proto je dobré mít na serveru
kromě vlastních obrázků jejich zmenšené kopie. Tyto kopie si můžete vytvořit
ručně nebo pro tuto práci použít ASP.NET.
PHP pro práci s obrázky používá knihovnu gd2, ASP.NET funkce a třídy ze jmenného
prostoru System.Drawing a System.Drawing.Imaging.
Vlastní technologie pro práci s obrázky se jmenuje .NET GDI+ a nahrazuje
GDI (Graphics Device Interface) - starší API pro práci se základní grafikou
ve Windows. S tímto označením
se můžete setkat v nápovědě MSDN, třídy a metody ale tento název zdá se mi neobsahují.
(To jen kdybyste chtěli někde hledat další informace - GDI+ je to klíčové slovo,
se kterým začít).
Vlastní proces zmenšení obrázku je jednoduchý:
// pro snadnejsi zapis pouzijeme
// namespaces pro praci s GDI+
using System.Drawing;
using System.Drawing.Imaging;
public void MakeThumbs(
string FilePath, // cesta k obrazku
string CopyPath, // cesta k ulozeni zmenseneho obrazku
int MaxWidth, // maximalni sirka zmenseneho obrazku
int MaxHeight) // maximalni vyska zmenseneho obrazku
{
float pw, ph, p;
// jako jednotky velikosti budeme pouzivat pixely
GraphicsUnit units
= System.Drawing.GraphicsUnit.Pixel;
// otevreme obrazek a vytvorime
// jemu odpovidajici graficky objekt bitmap
Bitmap b =
new System.Drawing.Bitmap(FilePath);
// zjistime povodni velikost obrazku v pixelech
RectangleF r = b.GetBounds(ref units);
// vytvorime objekt Size, do ktereho ulozime
// vypocitanou velikost zmenseneho obrazku
Size NewSize = new System.Drawing.Size();
// pokud je predana nula do parametru MaxWidth nebo MaxHeight,
// omezeni se netyka tohoto rozmeru
if (MaxWidth == 0)
MaxWidth = (int)r.Width;
if (MaxHeight == 0)
MaxHeight = (int)r.Height;
// vypocitame pomery zmenseni vysky a sirky
pw = r.Width / MaxWidth;
ph = r.Height / MaxHeight;
// a vetsi pomer pouzijeme jako vlastni pomer zmenseni
if (pw > ph)
p = pw;
else
p = ph;
// toto zabrani zvetseni obrazku (kdyby pomer zmenseni vysel
// mensi nez jedna
if (p < 1)
p = 1;
// do NewSize ulozime novou vysku a sirku po zmenseni
NewSize.Width = (int)(r.Width / p);
NewSize.Height = (int)(r.Height / p);
// vytvorime novou bitmapu, jako vzorovy obrazek predame puvodni
// obrazek a do konstruktoru tez predavame objekt NewSize,
// takto vytvorena bitmapa bude obsahovat zmenseny obrazek.
Bitmap b2 = new System.Drawing.Bitmap(b, NewSize);
// nyni by jiz stacilo zavolat b2.Save(CopyPath) a
// bylo by hotovo, ale takovymto ulozenim by se ulozil
// obrazek po ztratove kompresi, ktera je defaultne
// nastavena na dost tvrdou hodnotu, takze je lepsi pouzit
// pretizenou metodu Save a predat vlastni hodnotu komprese
// potrebujeme vlastni Encoder - ten bude mit po
// vytvoreni jeden parametr - stupen komprese
Encoder qualityEncoder = Encoder.Quality;
// hodnota 100 je prave komprese, muzete zadat cislo
// od 0 do 100, 100 je nejmensi komprese
EncoderParameter ratio =
new EncoderParameter(qualityEncoder, 100L);
EncoderParameters codecParams = new EncoderParameters(1);
codecParams.Param[0] = ratio;
string mimeType = "image/jpeg";
// pomocnou funkci GetEncoderInfo zjistime to nutne pro vytvoreni
// encoderu pro obrazky jpeg
ImageCodecInfo jpegCodecInfo = GetEncoderInfo(mimeType);
// nyni jiz obrazek muzeme ulozit, krome cilove cesty metoda Save
// dostava take informace o codecu a parametry codecu
b2.Save(CopyPath, jpegCodecInfo, codecParams);
// objekty GDI+ je dobre uvolnovat
// hned pote, co je jiz nepotrebujeme
b.Dispose();
b2.Dispose();
}
// pomocna funkce pro nastaveni encoderu
public ImageCodecInfo GetEncoderInfo(string mimeType)
{
int j;
ImageCodecInfo[] encoders;
encoders = ImageCodecInfo.GetImageEncoders();
for (j = 0; j < encoders.Length; ++j)
{
if (encoders[j].MimeType == mimeType)
return encoders[j];
}
return null;
}
Ohodnoťte prosím užitečnost článku