把图片列表合成一个GIF动画图片

13年前
  1. import os   
  2. from PIL import Image   
  3. import images2gif   
  4.   
  5. #type 合成GIF分类    
  6. #0:图片缩放到最大宽度*最大高度(长方形)、并粘贴到最大宽度*最大高度(长方形)的白色背景图片中、居中后合成   
  7. #1:图片缩放到最大长度(正方形)、并粘贴到最大长度(正方形)的白色背景图片中、居中后合成   
  8. #2:图片不缩放、并粘贴到最大宽度*最大高度(长方形)的白色背景图片中、居中后合成   
  9. #3:图片不缩放、并粘贴到最大长度(正方形)的白色背景图片中、居中后合成   
  10. #4:原图直接合成(按宽度排序、不缩放也不粘贴到新的白色背景图片中)   
  11. #5:原图直接合成(按高度排序、不缩放也不粘贴到新的白色背景图片中)   
  12. def GetGifAnimationFromImages(targetGifFilePath, srcImageFilePaths, type = 0):   
  13.     #用来合成的图片   
  14.     images = []   
  15.        
  16.     #取得所有图片中最大长度(宽度、高度)   
  17.     maxWidthAndHeight = 1  
  18.     #最大宽度和高度   
  19.     maxWidth = 1  
  20.     maxHeight = 1  
  21.     #取得图片按宽度从大到小排序的路径顺序   
  22.     widthAndFilePaths = []   
  23.     #取得图片按高度从大到小排序的路径顺序   
  24.     heightAndFilePaths = []   
  25.        
  26.     for imageFilePath in srcImageFilePaths:   
  27.         fp = open(imageFilePath, "rb")   
  28.         width,height = Image.open(fp).size   
  29.         widthAndFilePaths.append((width, imageFilePath))   
  30.         heightAndFilePaths.append((height, imageFilePath))   
  31.         maxWidth = max(maxWidth, width)   
  32.         maxHeight = max(maxHeight, height)   
  33.         fp.close()   
  34.   
  35.     maxWidthAndHeight = max(maxWidthAndHeight, maxWidth, maxHeight)   
  36.            
  37.     #降序排列   
  38.     widthAndFilePaths.sort(key=lambda item: item[0], reverse=True)   
  39.     heightAndFilePaths.sort(key=lambda item: item[0], reverse=True)   
  40.        
  41.     if type == 4 or type == 5:   
  42.         #原图直接合成(按宽度排序)   
  43.         if type == 4:   
  44.             for widthAndFilePath in widthAndFilePaths:   
  45.                 img = Image.open(widthAndFilePath[1])   
  46.                 images.append(img)   
  47.         #原图直接合成(按高度排序)   
  48.         if type == 5:   
  49.             for heightAndFilePath in heightAndFilePaths:   
  50.                 img = Image.open(heightAndFilePath[1])   
  51.                 images.append(img)   
  52.     else:   
  53.         for imageFilePath in srcImageFilePaths:   
  54.             fp = open(imageFilePath, "rb")   
  55.             img = Image.open(fp)   
  56.             width,height = img.size   
  57.             #生成空的白色背景图片   
  58.             if type == 0 or type == 2:     
  59.                 #长方形   
  60.                 imgResizeAndCenter = Image.new("RGB", [maxWidth,maxHeight], (255,255,255))   
  61.             elif type == 1 or type == 3:   
  62.                 #正方形   
  63.                 imgResizeAndCenter = Image.new("RGB", [maxWidthAndHeight,maxWidthAndHeight], (255,255,255))   
  64.   
  65.             if type == 0:   
  66.                 #宽度/最大宽度>=高度/最大高度,使用小的缩放比例   
  67.                 if maxWidth / width >= maxHeight / height:   
  68.                     resizeImg = img.resize((width * maxHeight / height, maxHeight),Image.ANTIALIAS)   
  69.                     imgResizeAndCenter.paste(resizeImg, ((maxWidth - width * maxHeight / height)/ 2,0))   
  70.                 else:   
  71.                     resizeImg = img.resize((maxWidth, height * maxWidth / width),Image.ANTIALIAS)   
  72.                     imgResizeAndCenter.paste(resizeImg, (0,(maxHeight - height * maxWidth / width)/ 2))   
  73.             if type == 1:   
  74.                 #宽度>=高度,按宽度缩放到最大长度   
  75.                 if width >= height:   
  76.                     resizeImg = img.resize((maxWidthAndHeight, height * maxWidthAndHeight / width),Image.ANTIALIAS)   
  77.                     imgResizeAndCenter.paste(resizeImg, (0,(maxWidthAndHeight - height * maxWidthAndHeight / width)/ 2))   
  78.                 else:   
  79.                     resizeImg = img.resize((width * maxWidthAndHeight / height, maxWidthAndHeight),Image.ANTIALIAS)   
  80.                     imgResizeAndCenter.paste(resizeImg, ((maxWidthAndHeight - width * maxWidthAndHeight / height)/ 20))   
  81.             elif type == 2:   
  82.                 imgResizeAndCenter.paste(img, ((maxWidth - width) / 2,(maxHeight - height) / 2))   
  83.             elif type == 3:   
  84.                 imgResizeAndCenter.paste(img, ((maxWidthAndHeight - width) / 2,(maxWidthAndHeight - height) / 2))   
  85.                    
  86.     #        #保存缩放居中后的图片   
  87.     #        imgResizeAndCenter.convert("RGB").save(os.path.dirname(imageFilePath) + os.sep + "ResizeAndCenter" + os.path.basename(imageFilePath), 'jpeg')   
  88.             images.append(imgResizeAndCenter)   
  89.             fp.close()   
  90.            
  91.     images2gif.writeGif(targetGifFilePath, images, duration=1, nq=0.1)   
  92.   
  93. #取得目录下面的文件列表   
  94. def GetDirImageList(dir_proc, recusive = True):   
  95.     resultList = []   
  96.     for file in os.listdir(dir_proc):   
  97.         if os.path.isdir(os.path.join(dir_proc, file)):   
  98.             if (recusive):   
  99.                 resultList.append(GetDirImageList(os.path.join(dir_proc, file), recusive))   
  100.             continue  
  101.   
  102.         resultList.append(os.path.join(dir_proc, file))   
  103.            
  104.     return resultList   
  105.   
  106. if __name__ == "__main__":   
  107.     GetGifAnimationFromImages(r"D:\hecheng.gif", [r"D:\a.jpg", r"D:\b.jpg", r"D:\c.jpg"])   
  108.     GetGifAnimationFromImages(r"D:\hecheng1.gif", [r"D:\a.jpg", r"D:\b.jpg", r"D:\b.jpg", r"D:\c.jpg"], 1)   
  109.     GetGifAnimationFromImages(r"D:\hecheng2.gif", [r"D:\a.jpg", r"D:\b.jpg", r"D:\c.jpg"], 2)   
  110.     GetGifAnimationFromImages(r"D:\hecheng3.gif", [r"D:\a.jpg", r"D:\b.jpg", r"D:\c.jpg"], 3)   
  111.     GetGifAnimationFromImages(r"D:\hecheng4.gif", [r"D:\a.jpg", r"D:\b.jpg", r"D:\c.jpg"], 4)   
  112.     GetGifAnimationFromImages(r"D:\hecheng5.gif", [r"D:\a.jpg", r"D:\b.jpg", r"D:\c.jpg"], 5)   
  113.        
  114.     GetGifAnimationFromImages(r"D:\hechengTest.gif", GetDirImageList(r"D:\GifMarker"), type = 4