How to use Python to generate a bitmap with layer?

On 14/05/2015 at 15:10, xxxxxxxx wrote:

Hi,

I try to write an plugin that split a image into a image with layer.
Each color (material id's) get it own layer.
The layer are convert to use for alphamaps in c4d material.

I can initialize a bitmap from a file.
But it is BaseBitmap.

I try to use MultipassBitmap.
Now I can create a new empty layer.

But I cant set Pixel at the empty layer.

How can I set pixel to a layer?

  
import c4d   
import os   
from c4d import bitmaps, gui, storage   
  
  
def main() :   
  
    doc = c4d.documents.GetActiveDocument()   
    op = doc.GetActiveObject()   
    path = storage.LoadDialog(type=c4d.FILESELECTTYPE_IMAGES, title="Please Choose the PolyPaint Image")   
    if not path: return   
  
    # Create and initialize selected image   
    orig = bitmaps.BaseBitmap()   
    if orig.InitWith(path)[0] != c4d.IMAGERESULT_OK:   
        gui.MessageDialog("Cannot load image \"" + path + "\".")   
        return   
  
  
    # Get selected image infos   
    width, height = orig.GetSize()   
    bits = orig.GetBt()   
  
    # Create the copy and initialize it   
    copy = bitmaps.BaseBitmap()   
    copy.Init(width, height, bits)   
    multibmp = bitmaps.MultipassBitmap.AllocWrapper(copy)   
  
    layer_a = multibmp.AddLayer(multibmp.GetLayers(c4d.MPB_GETLAYERS_0),1)   
  
    # ColorPalette Variable vorbereiten   
    ColPal = [0,0]   
    cc = 0 # Zähler auf 0   
    while cc < 512: # ColorPalette 512 Einträge mit 0 füllen   
        ColPal.append(0)   
        cc = cc + 1   
          
    wy = 0   
    while wy < height: # Bildzeilen durchlaufen   
        wx = 0      
        while wx < width: # Bildpunkte der Zeile durchlaufen   
            readcol = orig.GetPixel(wx,wy) # Pixel als Farb-Vector auslesen   
            farbanzahl = 6               # In wie viele Farben aufteilen?   
            farbdivid = 256 * 3 / farbanzahl # Bit + Anzahl Farbkanäle geteilt durch die Farbanzahl = Divisor   
            # Farbkanäle runter rechnen   
            r=int(readcol[0]/farbdivid)   
            g=int(readcol[1]/farbdivid)   
            b=int(readcol[2]/farbdivid)   
            # reduzierte Farben in neue Bitmap eintragen   
            copy.SetPixel(wx,wy,r*farbdivid,g*farbdivid,b*farbdivid)   
            multibmp.SetPixel(wx,wy,r*farbdivid,g*farbdivid,b*farbdivid)   
            layer_a.SetPixel(wx,wy,r*farbdivid,g*farbdivid,b*farbdivid)   
               
            ColPal[r*g*b] = [r,g,b] # ColorPalette (512 mögliche Farben) mit Wert füllen   
  
            wx = wx +1 # Zeile +1   
        wy = wy + 1 # Spalte +1   
       
       
       
    bitmaps.ShowBitmap(orig) # Show original   
    bitmaps.ShowBitmap(copy) # Show copied image   
    bitmaps.ShowBitmap(multibmp) # Show copied image   
  
    # Einträge auswerten und anzeigen   
    ccc = 0   
    for element in ColPal:   
       if element > [0,0,0]:   
            print element   
            ccc = ccc + 1   
    print ccc   
       
    print layer_a   
    print multibmp   
  
if __name__=='__main__':   
    main()   

This is my code for loading an image.
Reduce the colors and write to a new bitmap.
And I create a multipass bitmap for test to create a layer.

Maybe, later I want to use OpenCV or PIL library for better convert the image.

Bernd

On 18/05/2015 at 02:51, xxxxxxxx wrote:

Hello,

it seems that a MultipassBitmap layer can only be accessed through GetPixelCnt() / SetPixelCnt(), you you have to setup a ByteSeq:

  
mp = c4d.bitmaps.MultipassBitmap(200,200,c4d.COLORMODE_RGB)  
  
newlayer = mp.AddLayer(None,c4d.COLORMODE_RGB)  
newlayer.SetParameter(c4d.MPBTYPE_NAME,"the new layer")  
  
sq = c4d.storage.ByteSeq(None, 3)  
  
for x in xrange(200) :  
     for y in xrange(200) :  
               
              # set the pixel to 255/128/0  
                
              sq[0] = chr(255)  
              sq[1] = chr(128)  
              sq[2] = chr(0)  
                
              newlayer.SetPixelCnt(x,y,1,sq.GetOffset(0),3,c4d.COLORMODE_RGB,c4d.PIXELCNT_0)  
  
saveImagePath = c4d.storage.SaveDialog(c4d.FILESELECTTYPE_IMAGES,"Save as TIFF")  
mp.Save(saveImagePath,c4d.FILTER_TIF,None,c4d.SAVEBIT_MULTILAYER)  

best wishes,
Sebastian

On 29/05/2015 at 07:43, xxxxxxxx wrote:

Hello Bernd,

was your question answered?

Best wishes,
Sebastian

On 04/06/2015 at 10:55, xxxxxxxx wrote:

Hi Sebastian 🙂

thank you after I try to develope the app I make a pause.
I have read you answer - very best thanks!!!

I will try it later 😉
Today I try another start to develope python script.

Maybe some days later I will answer the code can help, or not.
Thank you again, I don't forgot to post it later 😉

On 10/06/2015 at 16:52, xxxxxxxx wrote:

Looks good, but there is a problem:
if I save as tif it will be very good!!!
I open in Photoshop and there are the layers i can create now 🙂

But when I open the mp (bitmap) in the picture viewer it only show one layer!

  
  
mp = c4d.bitmaps.MultipassBitmap(200,200,c4d.COLORMODE_RGB|c4d.COLORMODE_ALPHA)   
newlayer = mp.AddLayer(None,c4d.COLORMODE_RGB)   
newlayer.SetParameter(c4d.MPBTYPE_NAME,"the new layer")   
       
sq = c4d.storage.ByteSeq(None, 3)   
  
for x in xrange(200) :   
    for y in xrange(200) :   
                 
    #set the pixel to 255/128/0   
                 
    sq[0] = chr(255)   
    sq[1] = chr(128)   
    sq[2] = chr(0)   
                 
# write pixel            newlayer.SetPixelCnt(x,y,1,sq.GetOffset(0),3,c4d.COLORMODE_RGB,c4d.PIXELCNT_0)   
  
  
  
# a second layer   
newlayerA = mp.AddLayer(None,c4d.COLORMODE_ALPHA)   
newlayerA.SetParameter(c4d.MPBTYPE_NAME,"the new layer2")   
       
sqA = c4d.storage.ByteSeq(None, 3)   
  
for x in xrange(200) :   
    for y in xrange(200) :   
                 
    #set the pixel to 255/128/0   
                 
    sqA[0] = chr(255)   
    sqA[1] = chr(128)   
    sqA[2] = chr(255)   
                 
            newlayerA.SetPixelCnt(x,y,1,sqA.GetOffset(0),3,c4d.COLORMODE_ALPHA,c4d.PIXELCNT_0)   
  
       
       
saveImagePath = c4d.storage.SaveDialog(c4d.FILESELECTTYPE_IMAGES,"Save as TIFF")   
mp.Save(saveImagePath,c4d.FILTER_TIF,None,c4d.SAVEBIT_MULTILAYER)   
bitmaps.ShowBitmap(mp)   

On 10/06/2015 at 17:05, xxxxxxxx wrote:

Photoshop:

Picture Viewer in C4D:

On 11/06/2015 at 01:05, xxxxxxxx wrote:

Hello,

a layer only appears in the Picture Viewer if the MPBTYPE_SHOW parameter is set to true. See also this thread: "Bake texture and MultipassBitMap".

Best wishes,
Sebastian

On 11/06/2015 at 03:29, xxxxxxxx wrote:

Thank you very much