Come salvare un file con estensione gif con una nuova tabella di colori utilizzando GDI +

Traduzione articoli Traduzione articoli
Identificativo articolo: 315780 - Visualizza i prodotti a cui si riferisce l?articolo.
Espandi tutto | Chiudi tutto

In questa pagina

Sommario

Per la una versione di Microsoft Visual C# .NET di questo articolo, vedere 319061.
Per la una versione di Microsoft Visual Basic .NET di questo articolo, vedere 319591.
GIF (CompuServe Graphics Interchange Format) Ŕ stato progettato con un massimo di 256 colori sono disposti in una tabella dei colori. Per apportare modifiche comuni a un file di immagine GIF, Ŕ necessario modificare una tabella di colori personalizzata. Tuttavia, quando GDI + consente di modificare un oggetto immagine e quindi viene richiesto di salvare l'immagine con il codificatore GIF, il file GIF risultante contiene una tabella dei colori mezzitoni.

Per salvare un' immagine con una tabella di colori personalizzata utilizzando il codificatore GIF, Ŕ necessario utilizzare una copia a 256 colori dell' immagine , GDI + non modificato.

Informazioni

Il file di immagine GIF Ŕ possibile esprimere un massimo di 256 colori. PoichÚ colore Ŕ una risorsa scarsa nel file con estensione gif, l'ottimizzazione di tali colori Ŕ un'attivitÓ pi¨ comunemente richiesta. Per applicare una tabella di colori ottimizzato, Ŕ necessario impostare di qualsiasi tabella arbitrario colore personalizzato in un file GIF.

Una volta GDI + modifica un' immagine e quindi si scrive un'immagine in un file utilizzando il codificatore GIF, GDI + scrive il file utilizzando una tavolozza dei mezzi toni a cui bit dell'oggetto immagine Ŕ stato ridotto del colore. GDI + esegue una conversione di colori da 32 bit per pixel (32 BPP) quando scrive l'immagine nel file di quanto tutte le modifiche apportate all'immagine vengono eseguite con il motore di grafica a 32 BPP GDI +.

Sebbene GDI + supporta la creazione di immagini e bitmap di diversi formati pixel e pertanto Ŕ possibile caricare un'immagine GIF, l'utilizzo del motore di grafico a 32 BPP richiede la conversione a 32 BPP, quando modificate da GDI +. Tuttavia, un'immagine o bitmap che Ŕ non modificato da GDI + mantiene il formato pixel originale ed Ŕ possibile scrivere un file utilizzando il metodo Save con il codificatore appropriato. Questa proprietÓ costituisce la base per una tecnica che possibile salvare un' immagine in un file GIF di una tabella di colori personalizzata.

╚ possibile scrivere un non modificato bitmap con il codificatore GIF e conservare la tabella di colori di bitmap ; pertanto, Ŕ possibile utilizzare questo metodo per salvare un file di GIF con una nuova tabella dei colori.

Il metodo consiste nel copiare i dati dell'immagine da un oggetto immagine originale a un oggetto temporaneo di bitmap . Questo temporaneo bitmap viene creata come un a 8 BPP indicizzato bitmap , che rappresenta il formato di pixel viene utilizzato per salvare un file GIF. La tabella di colori di bitmap Ŕ impostata utilizzando il metodo SetPalette , e quindi viene copiata la definizione di immagine temporaneo bitmap . Dopo aver creato il temporaneo bitmap con una definizione di duplicati, Ŕ possibile utilizzare il metodo Salva per salvarlo con il codificatore GIF, che mantiene la tabella dei colori a 8 BPP.

Per scrivere un'immagine GIF in un file con una tabella di colori personalizzata, attenersi alla seguente procedura:
  1. Creare un oggetto bitmap duplicato della stessa dimensione dell'immagine di origine.
  2. Impostare il sommario di colori personalizzata per l'oggetto bitmap tabella il colore desiderato.
  3. Utilizzare il metodo LockBits per ottenere l'accesso in scrittura i bit di immagine della copia.
  4. Creare una definizione di immagine nella copia scrivendo gli indici di colore alla memoria ottenuto da LockBits duplicare i pixel nell'immagine originale.
  5. Utilizzare UnLockBits per rilasciare i bit di immagine.
  6. Utilizzare la copia di bitmap con la tabella colori personalizzata per salvare l' immagine in un file utilizzando Salva e il codificatore GIF.
  7. Rilasciare la copia di bitmap dell' immagine .

Utilizzando il codice di esempio

Il codice di esempio in questo articolo viene illustrato come utilizzare Bitmap.Save per scrivere un file GIF con una tabella colori personalizzata della dimensione arbitrari. Il codice non Ŕ ottimizzato per le prestazioni poichÚ lo scopo Ŕ per solo la dimostrazione. Le opportunitÓ migliore per l'ottimizzazione sono in pixel l'elaborazione di cicli. GetPixel Ŕ un'utile astrazione del formato pixel, ma Ŕ molto lento. Il codice di esempio sarebbe molto pi¨ veloce se si utilizza LockBits per accedere direttamente il formato pixel. Per aumentare la velocitÓ, non utilizzare il metodo GetPixel e l'astrazione della classe di colore . Per migliorare le prestazioni, Ŕ necessario riscrivere la conversione di gradazioni di grigio mediante operazioni matematiche integer, anzichÚ a virgola mobile.

La funzione di esempio accetta i seguenti cinque parametri:
  • Qualsiasi oggetto GDI + l' immagine .
  • Il nome di file per il file di destinazione.
  • Identificatore di classe (CLSID) del codificatore GIF.
  • Il numero di colori per il file GIF.
  • Flag che indica se Ŕ necessario un colore trasparente.
Per ulteriori informazioni sulla funzione GDI + GetEncoderClsid e per scaricare il codice di esempio, vedere la documentazione della Guida di MSDN sul collegamento riportato di seguito:

Platform SDK: GDI + - Image::Save (nomefile, clsidEncoder, encoderParams)
http://msdn.microsoft.com/en-us/library/ms533843.aspx
La funzione crea prima un oggetto bitmap che ha il formato di pixel di PixelFormat8BPPIndexed perchÚ questo Ŕ l'oggetto che viene salvato in creare il file di GIF con nColors e quindi viene creata una tavolozza dei colori con i colori personalizzati. Il file GIF Ottiene le dimensioni e voci specifiche per la tabella dei colori da ColorPalette dell'oggetto bitmap . Il codice di esempio consente di creare una scala di grigi a scopo dimostrativo perchÚ tale algoritmo Ŕ semplice estendere su vari formati di tabella di colori.

Per creare il file GIF, Ŕ necessario inizializzare l'oggetto bitmap a 8 BPP con la definizione di immagine deve essere scritto nel file. Nel codice di esempio, Ŕ utilizzata per una serie di cicli centrale colore convertire l'immagine in ingresso allo spazio colore TV essenzialmente bianco e nero.

A scopo dimostrativo, i pixel di immagine di origine sono accessibili per mezzo del metodo GetPixel di un oggetto bitmap che rappresenta una copia dell'immagine di origine. PerchÚ la classe Image non implementa il metodo GetPixel , viene creata una copia di bitmap .

╚ possibile utilizzare altre tecniche per accedere ai pixel, come l'accesso diretto per i pixel utilizzando il metodo LockBits o il interoperabilitÓ con Sezioni DIB GDI di Windows . Quando Ŕ possibile utilizzare la funzione BitBlt per copiare una bitmap da un HDC GDI + a un controller di dominio memoria GDI DIB sezione, le funzioni GBitBlt utilizza le funzionalitÓ di colore corrispondente di GDI.

Dopo aver creato la copia di bitmap , Ŕ possibile utilizzare il metodo Save con il CLSID GIF fornito per scrivere l'immagine bitmap nel file di destinazione.

File GIF con meno di 256 colori

Il codec GIF in GDI + versione 1.0 consente di codificare solo GDI + immagini che sono 8 BPP. Tutti i formati immagine vengono convertiti prima della codifica. Questo codice utilizza il formato di bitmap a 8 BPP per scrivere i file GIF con meno di 256 colori, perchÚ il codec GIF riconosce oggetti di bitmap a 8 BPP che contengono meno di 256 colori, la proprietÓ ColorPalette.Count .

Per ulteriori informazioni sui formati di pixel GIF codec, vedere la sezione "References" di questo articolo.

Il codice del ciclo di elaborazione che consente di copiare le definizioni di pixel dell'immagine in bitmap a 8 BPP prende in considerazione le dimensioni della tavolozza quando il codice calcola il valore di indice di un pixel. Il codec GIF limita la dimensione della tavolozza e limita la definizione di immagine per valori di indice che sono compatibili con le dimensioni della tavolozza (vale a dire la potenziale GIF colore tabella) e pertanto Ŕ possibile creare GIF con colori di meno di 256.

Trasparenza GIF

Nel codice di esempio, la routine di creazione ColorPalette imposta il primo movimento sia il colore trasparente GIF per illustrare l'utilizzo della funzionalitÓ di trasparenza. Il codice viene eseguita impostando il componente Alpha della voce del colore su ZERO. Il codice di esempio in questo articolo Ŕ solo a scopo dimostrativo, di conseguenza, il colore di trasparenza una scelta arbitraria e pu˛ avere risultati imprevisti che dipendono interamente l'immagine di origine.

Il codificatore GIF identifica il primo colore nel, ColorPalette , ha un valore alfa pari a ZERO come colore trasparente. Questo significa che il colore trasparente non necessario per la prima voce il ColorPalette . Pu˛ essere uno qualsiasi dei 256 colori possibili nella tavolozza, a condizione che tutte le voci precedenti contengono componenti di Alpha con valori diversi da zero. Tutte le voci successive con i valori alfa componente ZERO vengono ignorate. Le voci tutti i componenti alfa diverso da zero sono considerate opache.

Nota : quando si utilizza questo codice per sovrascrivere un file esistente, potrebbe essere visualizzato un problema con la dimensione del file risultante. Questo si verifica a causa di un bug in GDI + versione 1.0 non tronca il file.

Per ulteriori informazioni sulle dimensioni del file immagine, vedere la sezione "References" di questo articolo. Ma l'articolo di riferimento non esiste viene illustrato l'utilizzo della classe bitmap nello spazio dei nomi System.Drawing di .NET Framework, l'argomento sono valide per GDI + poichÚ System.Drawing viene implementato da GDI +.

Il numero di licenze GIF/LZW

Microsoft ha ottenuto una licenza di Unisys per utilizzare il formato di file GIF e altre tecnologie LZW sono coperti da Stati Uniti proprietÓ Unisys e brevetti esterne in un numero di prodotti Microsoft. Tuttavia, questa licenza non Ŕ esteso agli sviluppatori di terze parti che utilizzano prodotti di sviluppo Microsoft o strumenti per lo sviluppo di applicazioni. Gli sviluppatori di terze parti, Ŕ necessario determinare se Ŕ necessario ottenere una licenza di Unisys per utilizzare il formato GIF o le tecnologie LZW.

Per ulteriori informazioni sulle licenze LZW e GIF, fare clic sul numero dell'articolo della Microsoft Knowledge Base riportato di seguito:
193543INFORMAZIONI: Unisys GIF e informazioni di licenza LZW Technology

Codice di esempio

Status SaveGIFWithNewColorTable(
  Image *pImage,
  const WCHAR* filename,
  const CLSID* clsidEncoder,
  DWORD nColors,
  BOOL fTransparent
)
{
    Status stat = GenericError;

    // GIF codec supports 256 colors maximum.
    if (nColors > 256)
        nColors = 256;
    if (nColors < 2)
        nColors = 2;

    // Make a new 8-BPP pixel indexed bitmap that is the same size as the source image.
    DWORD   dwWidth = pImage->GetWidth();
    DWORD   dwHeight = pImage->GetHeight();

    // Always use PixelFormat8BPPIndexed, because that is the color table
    // based interface to the GIF codec.
    Bitmap  bitmap(dwWidth, dwHeight, PixelFormat8BppIndexed); 

    stat = bitmap.GetLastStatus();

    if (stat != Ok)
        return stat;        // No point in continuing.

    // Allocate the new color table.
    DWORD   dwSizeColorPalette;
    dwSizeColorPalette = sizeof(ColorPalette);      // Size of core structure.
    dwSizeColorPalette += sizeof(ARGB)*(nColors-1);   // The other entries.

    // Allocate some raw space to back the ColorPalette structure pointer.
    ColorPalette *ppal = (ColorPalette *)new BYTE[dwSizeColorPalette];
    if (ppal == NULL) return OutOfMemory;

    ZeroMemory(ppal, dwSizeColorPalette);

    // Initialize a new color table with entries that are determined by
    // some optimal palette finding algorithm; for demonstration 
    // purposes, just do a grayscale. 
    if (fTransparent)
        ppal->Flags = PaletteFlagsHasAlpha;
    else
        ppal->Flags = 0; 
    ppal->Flags |= PaletteFlagsGrayScale;
    ppal->Count = nColors;
    for (UINT i = 0; i < nColors; i++)
    {
        int Alpha = 0xFF;       // Colors are opaque by default.
        int Intensity = i*0xFF/(nColors-1); // even distribution 

        // The GIF encoder makes the first entry in the palette with a
        // zero alpha the "transparent" color in the GIF.
        // For demonstration purposes, the first one is picked arbitrarily.

        if ( i == 0 && fTransparent) // Make this color index...
            Alpha = 0;          // Transparent
        
        // Create a gray scale for demonstration purposes.
        // Otherwise, use your favorite color reduction algorithm
        // and an optimum palette for that algorithm generated here.
        // For example, a color histogram, or a median cut palette.
        ppal->Entries[i] = Color::MakeARGB( Alpha, 
                                            Intensity, 
                                            Intensity, 
                                            Intensity );
    }

    // Set the palette into the new Bitmap object.
    bitmap.SetPalette(ppal);


    // Use GetPixel below to pull out the color data of Image.
    // Because GetPixel isn't defined on an Image, make a copy in a Bitmap 
    // instead. Make a new Bitmap that is the same size of the image that
    // you want to export. Otherwise, you might try to interpret the native 
    // pixel format of the image by using a LockBits call.
    // Use PixelFormat32BppARGB so that you can wrap a Graphics around it.
    Bitmap BmpCopy(dwWidth, dwHeight, PixelFormat32BppARGB); 
    stat = BmpCopy.GetLastStatus();
    if (stat == Ok)
    {
        Graphics g(&BmpCopy);

        // Transfer the Image to the Bitmap.
        stat = g.DrawImage(pImage, 0, 0, dwWidth, dwHeight);

        // g goes out of scope here and cleans up.
    }

    if (stat != Ok)
    {
        delete [] (LPBYTE) ppal;
        ppal = NULL;
        return stat;
    }

    // Lock the whole of the bitmap for writing.
    BitmapData  bitmapData;
    Rect        rect(0, 0, dwWidth, dwHeight);

    stat = bitmap.LockBits(
      &rect,
      ImageLockModeWrite,
      PixelFormat8BppIndexed,
      &bitmapData);

    if (stat == Ok)
    {
        // Write to the temporary buffer provided by LockBits.
        // Copy the pixels from the source image in this loop.
        // Because you want an index, convert RGB to the appropriate
        // palette index here.
        BYTE *pixels;
        if (bitmapData.Stride > 0)
            pixels = (BYTE*) bitmapData.Scan0;
        else
            // If the Stride is negative, Scan0 points to the last             // scanline in the buffer.
            // To normalize the loop, obtain the start of the buffer,
            // which is located (Height-1) scanlines previous.
            pixels = (BYTE*) bitmapData.Scan0 + bitmapData.Stride*(dwHeight-1);
        UINT stride = abs(bitmapData.Stride);

        // Top-down and bottom-up is not relevant to this algorithm.

        for(UINT row = 0; row < dwHeight; ++row)
        {
          for(UINT col = 0; col < dwWidth; ++col)
          {
              // Map palette indexes for a grayscale.
              // If you use some other technique to color convert,
              // put your favorite color reduction algorithm here.
              Color     pixel;
              UINT      i8BppPixel = row * stride + col;

              BmpCopy.GetPixel(col, row, &pixel);

              // Use luminance/chrominance conversion to get grayscale.
              // Basically, turn the image into black and white TV: YCrCb.
              // You do not have to to calculate Cr or Cb because you 
              // throw away the color anyway.
              // Y = Red * 0.299 + Green * 0.587 + Blue * 0.114

              // This expression is best as integer math for performance,
              // however, because GetPixel listed earlier is the slowest 
              // part of this loop, the expression is left as 
              // floating point for clarity.
              double luminance = (pixel.GetRed() * 0.299) +
                                (pixel.GetGreen() * 0.587) +
                                (pixel.GetBlue() * 0.114);

              // Gray scale is an intensity map from black to white.
              // Compute the index to the gray scale entry that  
              // approximates the luminance, and then round the index.      
              // Also, constrain the index choices by the number of colors to do
              pixels[i8BppPixel] = (BYTE)(luminance * (nColors-1)/255 +0.5);
          }
        }
    // To commit the changes, unlock the portion of the bitmap.  
        stat = bitmap.UnlockBits(&bitmapData);
    }

    // If destination work was successful, see whether the source was successful.
    if (stat == Ok) stat = BmpCopy.GetLastStatus();

    // See whether the code has been successful to this point.
    if (stat == Ok)
    {
    // Write it out to the disk.
        stat =  bitmap.Save(filename, clsidEncoder, NULL);
    }

    // Clean up after yourself.
    delete [] (LPBYTE) ppal;
    ppal = NULL;
    // BmpCopy goes away on its own when it falls out of scope.

    return stat;
}
				

Informazioni su codice di esempio

Microsoft fornisce esempi di programmazione a scopo puramente illustrativo, senza alcuna garanzia di qualsiasi tipo, sia espressa che implicita, ivi incluse, senza limitazioni, le garanzie implicite di commerciabilitÓ o idoneitÓ per uno scopo particolare. In questo articolo si presume che l'utente conosca il linguaggio di programmazione in questione e gli strumenti utilizzati per creare ed eseguire il debug delle procedure. Gli addetti al Supporto Microsoft possono spiegare la funzionalitÓ di una particolare procedura, ma non possono modificare questi esempi per fornire ulteriori funzionalitÓ o realizzare procedure per soddisfare esigenze specifiche.
Se si dispone di esperienza di programmazione limitata, Ŕ possibile che desideri contattare un Microsoft Certified Partner o servizi di consulenza Microsoft. Per ulteriori informazioni, visitare questi siti Web di Microsoft:

Microsoft Certified Partner - https://partner.microsoft.com/global/30000104

Microsoft Advisory Services - http://support.microsoft.com/gp/advisoryservice

Per ulteriori informazioni sulle opzioni di supporto disponibili e su come contattare Microsoft, visitare il seguente sito: http://support.microsoft.com/default.aspx?scid=fh;EN-US;CNTACTMS

Riferimenti

Per ulteriori informazioni sui formati di pixel GIF codec, fare clic sul numero dell'articolo della Microsoft Knowledge Base riportato di seguito:
318343INFORMAZIONI: File GDI + GIF vengono salvati con il formato a 8 BPP
Per ulteriori informazioni sulle dimensioni del file immagine, fare clic sul numero dell'articolo della Microsoft Knowledge Base riportato di seguito:
312119PRB: Salva metodo della classe di bitmap non troncamento dimensioni file
Anche se l'articolo che viene fatto riferimento in questo collegamento viene illustrato l'utilizzo della classe bitmap nello spazio dei nomi System.Drawing di .NET Framework, l'argomento relativo a GDI + poichÚ System.Drawing viene implementato da GDI +.

Glossario

BPP
bit per pixel - il numero di bit utilizzata per rappresentare il valore di colore di ogni pixel in un'immagine digitalizzata, descrive il layout fisico della definizione del ogni pixel colore di un'immagine. I formati di pixel pi¨ comuni e in genere riferimento includono 32 BPP, 24 BPP, 16 BPP, 8 BPP, 4 BPP, 1 BPP.
8 BPP
Il formato di pixel di immagine espresso come otto bit contenuti in un byte. Il valore di byte viene utilizzato come indice in una tabella dei colori che contiene le effettive definizioni di colore (RGB) di rosso, verde e blu. PoichÚ l'indice Ŕ un byte nella dimensione, la tabella dei colori Ŕ limitata a 256 colori.
GIF
Gli elementi grafici GIF - un formato di file di immagine streamable che Ŕ stato creato da CompuServe.
RGB
Rosso, verde e blu - ogni genere espresso come un byte e in un gruppo di 3 byte di colore.

ProprietÓ

Identificativo articolo: 315780 - Ultima modifica: lunedý 12 febbraio 2007 - Revisione: 3.5
Le informazioni in questo articolo si applicano a:
  • Microsoft GDI+ 1.0
  • Microsoft Windows XP Professional
  • the operating system: Microsoft Windows XP 64-Bit Edition
Chiavi:á
kbmt kbdswgdi2003swept kbbitmap kbgdiplus kbhowto KB315780 KbMtit
Traduzione automatica articoli
Il presente articolo Ŕ stato tradotto tramite il software di traduzione automatica di Microsoft e non da una persona. Microsoft offre sia articoli tradotti da persone fisiche sia articoli tradotti automaticamente da un software, in modo da rendere disponibili tutti gli articoli presenti nella nostra Knowledge Base nella lingua madre dell?utente. Tuttavia, un articolo tradotto in modo automatico non Ŕ sempre perfetto. Potrebbe contenere errori di sintassi, di grammatica o di utilizzo dei vocaboli, pi¨ o meno allo stesso modo di come una persona straniera potrebbe commettere degli errori parlando una lingua che non Ŕ la sua. Microsoft non Ŕ responsabile di alcuna imprecisione, errore o danno cagionato da qualsiasi traduzione non corretta dei contenuti o dell?utilizzo degli stessi fatto dai propri clienti. Microsoft, inoltre, aggiorna frequentemente il software di traduzione automatica.
Clicca qui per visualizzare la versione originale in inglese dell?articolo: 315780
LE INFORMAZIONI CONTENUTE NELLA MICROSOFT KNOWLEDGE BASE SONO FORNITE SENZA GARANZIA DI ALCUN TIPO, IMPLICITA OD ESPLICITA, COMPRESA QUELLA RIGUARDO ALLA COMMERCIALIZZAZIONE E/O COMPATIBILITA' IN IMPIEGHI PARTICOLARI. L'UTENTE SI ASSUME L'INTERA RESPONSABILITA' PER L'UTILIZZO DI QUESTE INFORMAZIONI. IN NESSUN CASO MICROSOFT CORPORATION E I SUOI FORNITORI SI RENDONO RESPONSABILI PER DANNI DIRETTI, INDIRETTI O ACCIDENTALI CHE POSSANO PROVOCARE PERDITA DI DENARO O DI DATI, ANCHE SE MICROSOFT O I SUOI FORNITORI FOSSERO STATI AVVISATI. IL DOCUMENTO PUO' ESSERE COPIATO E DISTRIBUITO ALLE SEGUENTI CONDIZIONI: 1) IL TESTO DEVE ESSERE COPIATO INTEGRALMENTE E TUTTE LE PAGINE DEVONO ESSERE INCLUSE. 2) I PROGRAMMI SE PRESENTI, DEVONO ESSERE COPIATI SENZA MODIFICHE, 3) IL DOCUMENTO DEVE ESSERE DISTRIBUITO INTERAMENTE IN OGNI SUA PARTE. 4) IL DOCUMENTO NON PUO' ESSERE DISTRIBUITO A SCOPO DI LUCRO.

Invia suggerimenti

 

Contact us for more help

Contact us for more help
Connect with Answer Desk for expert help.
Get more support from smallbusiness.support.microsoft.com