2016-09-07 84 views
0

我正在實驗室工作,我們經常製作幹細胞的時間推移系列(每小時圖像)。目前的想法是把所有的幀放在一起,並製作一個視頻顯示這個增長的細胞(類似於這個youtube video)。使用OpenCV + Python可以做到簡單和酷炫。時間推移圖像的亮度/直方圖規範化

import numpy as np 
import os 
import cv2 

fourcc = cv2.VideoWriter_fourcc(*'XVID') 
out = cv2.VideoWriter('output.avi',fourcc, 20.0, (640,480)) 

timelapse_folder = '../myTimeLapse/' 

for file in os.listdir(timelapse_folder): 
    frame = cv2.imread(timelapse_folder+file, 0) 
    out.write(frame) 

out.release() 

但是我們有問題,所有的圖像而改變亮度一點點,所以我們得到了我們的視頻輸出一些閃爍。

我不能上傳視頻,但這裏有與GIMP生成以可視化的問題,一些簡單的例子:

這就是視頻我從幀

enter image description here

,這就是獲得我想要的視頻(將閃爍最小化,而不是將其完全刪除也很好)

enter image description here

有沒有辦法調整所有圖像(或可能在2個圖像之間)的直方圖或亮度,以消除使用OpenCV的閃爍?

感謝您的每一個想法或提示!

編輯:由安德魯的想法產生的GIF序列(回答以下)

enter image description here

+1

。假定所有的圖像是漂浮/整數的2D陣列,然後,你可以構造所有的圖像的3D陣列,然後針對最亮的'(max(np.average(arr,axis = 2)))'進行歸一化。然後你逐步完成並寫入視頻? – Andrew

+0

嘿我試過'max_avg = np.max(np.average(images,axis = 2))',然後在for frame中循環每幀frame =(frame/max_avg)* 255,但它並沒有消除閃爍。或者你的意思是另一種標準化? – Fabian

回答

1

如果您的數據是3D數組,則不需要循環執行此操作。有5個圖像,例如256 x 256,您應該可以構建一個數組,即arr.shape == (256, 256, 5)。我的最初評論有點不合時宜,但下面的例子應該這樣做。

target_array = [] 

for file in os.listdir(timelapse_folder): 
    frame = cv2.imread(timelapse_folder+file, 0) 
    if target_array:#Not entirely happy with this, but it should work 
     target_array = np.dstack((target_array, frame)) 
    elif not target_array: 
     target_array = np.asarray(frame) 
target_array = target_array/np.max(target_array) 
#target_array *= 255 #If you want an intensity value with a more common range here 
for idx in xrange(target_array.shape[2]): 
    out.write(target_array[:, :, idx]) 

編輯: 我用this page熨平一些扭結與尋址3D陣列

+0

如果您遇到閃爍問題,可以在每個數據片之間添加一個插值片這是兩幀之間的中途,這將減少表觀閃爍效應。不確定平滑功能是否可以工作,具體取決於有多少幀。 – Andrew

+0

嘿我試過你的解決方案做圖像之間的這種規範化和添加轉換(插值切片),現在看起來「確定」。標準化消除了一點閃爍,但是我對插值切片有一些問題,因爲這些單元有時不夠接近,所以看起來非常模糊。我會添加一個由你對我的問題的答案所產生的gif,但我會等待接受 - 也許任何人有另一個想法。否則,我會在幾天內接受。非常感謝。 – Fabian

+0

如果平滑度是優先級,您可以隨時添加多個插值切片,這可以在dstack期間完成,定義插值切片的數量,然後創建該數量的陣列。然後你可以選擇是線性還是對數步進(也許11個切片的正態分佈會給出最佳的平滑度?)。顯然,你的真實數據將超過11:1左右,但只要你對任何看到它的科學家坦誠相告,我就沒有看到任何問題。 – Andrew

0

是這些圖像RGB或灰度值?閱讀每一幀後,我只想執行你的循環正常化:

frame = frame/np.max(frame) 

在灰度值的話,那麼每個圖像應該有0和1,但是這取決於之間的值,你的圖像看起來怎麼樣,你也可以嘗試其他的歸,例如使用np.mediannp.mean而不是np.max

+0

我試過,但所有圖像之間的亮度差異仍然存在。我想我需要尊重像安德魯在他的評論中寫的所有圖像的平均值,但我不知道如何將每幀的平均值移動到所有幀的平均值。你懂我的意思嗎? – Fabian

+0

我想我得到你的問題。你有什麼樣的物體,你可以從背景中分離你的幀(例如,使用一個簡單的閾值)?這樣你就可以嘗試只調整所有幀的背景。例如:以任意幀的背景的平均值作爲參考,並移動所有其他幀,使其背景的平均值與參考相匹配。 –

+0

是否有簡單的numpy或cv2方法來移動這些幀值?細胞不是完全白色的,所以我認爲如果我只調整背景,我會得到閃爍的細胞(前景)。在較高匯合度的圖像(很多細胞)中,我無法區分背景,因爲只有閃爍的細胞真的很接近。 – Fabian