Kendin Yap: Ev Multimedya Sistemi için Evrensel Ambilight - Atmosvet

  • 11.05.2019

Ekran çerçevesi etrafında dinamik arka aydınlatmaya sahip TV'ler, Philips'in tescilli yongalarından biridir. Ve diğerlerinden farklı olarak, işe yarıyor. Ancak her şeyin bir bedeli vardır ve Ambilight ve sürükleyici varlığı olan TV'ler diğer birçok modelden daha pahalıdır.

Rus geliştiriciler, herhangi bir üreticinin monitörlerini dinamik arka aydınlatma ile donatacak bir yöntem önerdiler. Bunu yapmak için cihazı bir servis merkezine götürmeniz bile gerekmez: sadece biraz zamana ve azim gerekir.

Genel olarak, böyle bir arka ışık, radyo bileşenleri olarak satın alınabilir ve bağımsız olarak yapılandırılabilir. Ancak, uygulamanın gösterdiği gibi, bu, PaintPack'in hazır seçenekleriyle neredeyse karşılaştırılabilir.

İki ana model mevcuttur: monitör versiyonu (30 LED) ve TV versiyonu (60 LED). Ayrıca çok basit bir tane var - 10 LED için, ancak yalnızca en küçük monitörler için uygundur.

TV versiyonu harici bir güç kaynağı ile donatılmıştır. Ayrıca, daha fazla sayıda LED lehine konuşur, bu da daha büyük bir aydınlatma alanı sağlar (başka bir deyişle, daha geniş ve daha yüksek parlar). Bu seçenekler herhangi bir nedenle uygun değilse, geliştiricilerle iletişime geçebilirsiniz: küçük bir ek ücret karşılığında değiştirilmiş bir sürüm sunacaklar.

mindrunway.ru

Aslında PaintPack, çıkarılabilir LED şeritlerin her iki taraftan bağlandığı küçük bir kasadır. Dolgulu kutu, bir PC'ye bağlanmak için göstergeler ve bir güç konektörünün yanı sıra microUSB'yi taşır. Ayrıca iki cihazı zincirleme bağlamak için bir ana konektör (tescilli) vardır.

Cihaz gövdesi TV'nin veya monitörün arkasında bulunur. Daha sonra talimatlara uygun olarak LED şeritler döşenir, elektrik bağlanır ve büyücülük başlar. PaintPack'i USB aracılığıyla bir bilgisayara bağlarken, sürücülerin yüklenmesi ve aygıtın birlikte verilen programda yapılandırılması gerekir.


mysku.ru

Ayar, AmbiBox paketi kullanılarak yapılır. "Akıllı arka ışık" menüsüne gitmek, bir ekran yakalama yöntemi ve programda sunulan çalışma modlarından birini seçmek gerekir:

  1. Statik arka plan - herhangi bir renk ayarlanabilir, LED ışıması düzenlenir.
  2. Renkli müzik - arka ışık, müziğin sesiyle birlikte zamanında yanıp sönecektir. Arka ışık rengi yeşil-sarı olarak ayarlanmıştır.
  3. Dinamik arka plan - bir rengin diğerine düzgün akışı.
  4. Ekran yakalama, ana çalışma modudur.

Bu modda, izlenen filmlerden ve oyunlardan renk yakalamak mümkündür. Arka ışık rengi, ekrandaki görüntüye göre üst, alt ve yan bölgelere (her biri ayrı ayrı) bölünmüş olarak değişecektir.

PaintPack, resmi Philips muadilinden biraz daha yavaştır. Ancak maliyet farkı ve herhangi bir cihazı yükseltme olasılığı göz önüne alındığında, seçim açıktır.

Bu eğitimde, Arduino Nano'yu kullanarak kendi DIY TV ortamımızı nasıl oluşturacağımızı öğreneceğiz.

Ambilight Arduino'nun yalnızca Bambilight yazılımını çalıştıran bir bilgisayarda çalışacağını unutmayın (kütüphaneyi GitHub'dan indirin).

Aşağıdaki bileşenlere ihtiyacınız olacak:

  • Bireysel Adreslenebilir RGB LED Şerit
  • Küçük geliştirme kurulu
  • Çoklu kablolar
  • 12V DC güç adaptörü
  • Çift taraflı bant
  • 4-5 Zımba
  • Teller için plastiği sıkılaştırır (bağlar)

Adım 2. LED şeridi test etme

İlk önce bandı TV'nize takarsanız, bu hoş olmayacak, ancak daha sonra bir LED'in çalışmadığını ve bandı çıkarmanız ve baştan başlamanız gerektiğini fark edeceksiniz.

Bu nedenle, LED şeridinize geçici kabloları lehimlemek ve Arduino, güç adaptörü ve .ino dosyası ile test etmek iyi bir fikirdir (sonraki adımlarda indirilebilir). Arduino'nuza .ino yükleyin. Burada henüz bir şey yapılandırmanıza gerek yok. LED şerit renklerinden bazılarının değiştiğini görmelisiniz.

Adım 3. Bağlantı şeması

Bu adımda yukarıdaki görseli kullanarak LED şeridi bağlayabilirsiniz.

LED şeridimiz, 3 LED'i ayrı ayrı sürmek için IC WS2811'i kullanır.

Adım 4. Ambilight'ı monitörünüze / TV'nize yükleme

Arduino Embilight LED şeridini monitörünüzün veya TV'nizin arkasına yapıştırmadan önce yüzeyi elinizden geldiğince temizlediğinizden emin olun. Tozdan kurtulmak için lifli bir bez kullanmak daha iyidir.

Yüzeyin temiz olduğundan emin olduktan sonra, LED şeridini monitörünüzün yanında tutarak ve boyutuna göre keserek uzunluğunu ölçebilirsiniz. Karşı taraftaki şeridin aynı uzunlukta olduğundan emin olun.

Tüm parçaları istediğiniz boyutta kestikten sonra monitörünüzün arkasına takabilirsiniz. Yapıştırıcı genellikle en iyi seçenek olmadığından, bazı çift taraflı bant parçaları kullanmanızı öneririz.

Önemli!

LED şeritlerindeki okların monitörünüzün çevresini gösterdiğinden emin olun! Değilse, baştan başlamak zorunda kalacaksınız!

Bantlar yerleştirildikten sonra bunları monitörün arkasına takabilirsiniz. USB kablosunu daha sonra bilgisayarınıza bağlamanız gerekeceğinden, uygun bir yere kurmayı unutmayın.

Adım 5. Tüm elektroniklerin lehimlenmesi

LED şeridi lehimlemek için bükülmüş ve uygun boyuta kesilmiş birkaç zımba kullandık. Sonra onları birbirine bağlamak için LED şeritlere lehimledim. Kısa devreleri önlemek için bazı yalıtkanlar kullanabilirsiniz, ancak bizim durumumuzda buna ihtiyacımız yoktu. Biraz daha iyi görünmesi için ataşlara siyah bir renk vermek için fosforlu kalem kullandık.

Şimdi, yukarıdaki adımdakiyle aynı devreyi kullanarak LED şeridi Arduino'ya bağlayın. USB kablosunu bağlayın, FastLED kitaplığını kurun (GitHub'dan indirin) ve bir sonraki adımdaki kodu Arduino'nuza yükleyin. Ve sonra, tüm kablolamayı yaptığımız gibi, güç adaptörünü bağlamanız yeterlidir.

Adım 6. Arduino Ambilight taslağı

Aşağıda Arduino Ambilight vurgulamamızın kodunu indirebilir veya kopyalayabilirsiniz.

#include "FastLED.h" #define NUM_LEDS 38 #define LED_DATA_PIN 3 #define NUM_BYTES (NUM_LEDS * 3) // 3 renk #define PARLAKLIK 100 #define UPDATES_PER_SECOND 100 #define TIMEOUT_ 3000 modedefine MODEint MODE_ANIMATION; bayt MESSAGE_PREAMBLE = (0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09); uint8_t PREAMBLE_LENGTH = 10; uint8_t current_preamble_position = 0; imzasız uzun last_serial_available = -1L; uint8_t led_counter = 0; uint8_t byte_counter = 0; CRGB ledleri; bayt arabelleği; // Dolgu animasyon öznitelikleri CRGBPalette16 currentPalette = RainbowColors_p; TBlendType currentBlending = LINEARBLEND; uint8_t startIndex = 0; void setup () (Serial.begin (115200); FastLED.clear (true); FastLED.addLeds (led'ler, NUM_LEDS); FastLED.setBrightness (PARLAKLIK); ) void loop () (anahtar (mod) (durum MODE_ANIMATION: fillLEDsFromPaletteColors (); break; case MODE_AMBILIGHT: processIncomingData (); break;)) void processIncomingData () (if (waitForPreamble (TIMEOUT)) (Serial.readBytes (buffer, NUM_BYTES); / * (int i = 0; i için DEBUG)< NUM_BYTES; i++) { Serial.write((char)buffer[i]); } */ while (byte_counter < NUM_BYTES) { byte green = buffer; byte blue = buffer; byte red = buffer; leds = CRGB(red, green, blue); } FastLED.show(); byte_counter = 0; led_counter = 0; } else { mode = MODE_ANIMATION; } } bool waitForPreamble(int timeout) { last_serial_available = millis(); while (current_preamble_position < PREAMBLE_LENGTH) { if (Serial.available() >0) (last_serial_available = millis (); if (Serial.read () == MESSAGE_PREAMBLE) (current_preamble_position ++;) else (current_preamble_position = 0;)) if (milis () - last_serial_available> zaman aşımı) (yanlış döndür;)) current_preamble_position = 0; true döndür; ) void fillLEDsFromPaletteColors () (startIndex ++; // hız uint8_t colorIndex = startIndex; for (int i = 0; i< NUM_LEDS; i++) { leds[i] = ColorFromPalette(currentPalette, colorIndex, BRIGHTNESS, currentBlending); colorIndex += 3; } FastLED.delay(1000 / UPDATES_PER_SECOND); if (Serial.available() >0) (mod = MODE_AMBILIGHT;))

Adım 7. Yazılım yapılandırması

.ino dosyasını açın ve aşağıdaki satırları durumunuza göre düzenleyin:

#define NUM_LEDS 38 // LED sayısı #define PARLAK 100 // parlaklık

Şimdi taslağı Arduino'ya yükleyin. Daha önce Bambilight kitaplığını indirmiş olmanız gerekirken, indirmediyseniz şimdi GitHub üzerinden kitaplığı indirebilirsiniz.

Şurada bulunan Bambilight.exe'yi açın:

[Bambilight klasörünü kaydettiğiniz konum] \ Bambilight-master \ Bambilight-master \ Binary

Şimdi her şeyi beğeninize göre ayarlayın ve aşağıdaki gibi bir test videosu kullanarak test edin:

Sonuçtan memnun kaldığınızda Bambilight programını küçültebilirsiniz.

Genel olarak, Arduino'yu kullanarak kendi ellerinizle yaptığınız TV için ambilight'ın bu sonucunu almalısınız. Patlamış mısır, pepsi alın ve sonucun tadını çıkarın.

İyi günler.

İlk yazım için en başarılı el işlerimden birini seçtim: Philips'ten Ambilight'ın HDMI-passthrough analogu, bundan sonra bu kompozisyona "Atmosvet" adını vereceğim.

Tanıtım
İnternette, bir PC'den bir resim görüntülerseniz, bir monitör / TV için Ambilight'ın nasıl yapılacağına dair hazır / açık kaynaklı çözümler ve makaleler bulmak çok zor değil. Ancak multimedya sistemimde, bir PC'den TV'de bir resim görüntülemek, kullanım süresinin sadece %5'ini alıyor, oyun konsollarından daha fazla zaman oynuyorum, bu da kendime ait bir şey bulmam gerektiği anlamına geliyor.
İlk veri:
  • 60" Plazma TV
  • Asrock Vision 3D 137B tabanlı HTPC
  • Xbox 360
Çoğu cihaz, içeriği oynatırken bile oynatmak için HDCP kullanır.
Gereklilik:
TV'ye bağlı tüm cihazlar için Atmosvet için merkezi destek sağlamak gerekir.
uygulama
4.5m led şeridi tv'ye nasıl taktığımı ve arduino ile ne yapılması gerektiğini anlatmayacağım, taban olarak kullanabilirsiniz.

Tek uyarı:
Ekranın altında garip bir titreme olduğunu fark ettim, ilk başta sinyalde bir hata yaptım, deflikeri yeniden seçtim, resmin yeniden boyutlandırılmasını değiştirdim ve bir çok şey kazdım, daha iyi oldu, ancak titreme Yardım etmedi. gözlemlemeye başladım. Titremenin yalnızca kasetin sonunda ve ardından parlak sahnelerde olduğu ortaya çıktı. Bir multimetre alarak, bandın başındaki, ortasındaki ve sonundaki voltajı ölçtüm ve titremenin nedenini tahmin ettim: bandın başında 4,9V idi (evet, Çin güç kaynağı ünitesi bir voltaj veriyor. sapma, bu önemli değil), ortada 4.5 4.22'nin sonunda - Voltaj düşüşü çok önemli , sorunu basitçe çözmem gerekiyordu - bandın ortasına güç kaynağı ünitesinden gücü getirdim, koydum TV'nin arkasındaki kablo. Anında yardımcı oldu, herhangi bir titreme tamamen durdu.

Web kamerası ile fotoğraf çekme
Fikri çalıştırmak ve görselleştirmesi için ilk test sürümü, bir web kamerası aracılığıyla bir görüntü yakalanarak seçildi) şuna benziyordu:

Düşük renksel geriverim ve yüksek gecikme, bu uygulamanın hiçbir şekilde kullanılamayacağını gösterdi.

HDMI aracılığıyla resim çekme

Olası seçenekleri araştırma sürecinde, en güvenilir ve bütçesel olarak aşağıdaki şema seçildi:

  • Tüm cihazlardan gelen sinyal, HDCP'yi destekleyen 5'i 1 arada bir HDMI anahtarına beslenir
  • Çıkış sinyali, yalnızca HDCP'yi desteklemekle kalmayıp aynı zamanda çıkışta da kapatan 1'si 2 çıkışlı bir HDMI ayırıcıya beslenir (Çinlilere teşekkürler).
  • Çıkış sinyallerinden biri TV'ye gidiyor
  • Başka bir çıkış sinyali, HDMI'dan AV'ye dönüştürücüye gider
  • S-Video sinyali ICONBIT'ten yakalama kutusuna gidiyor
  • Yakalama kutusu, TV'deki Arduino teyp denetleyicisine bağlı olan USB üzerinden her zaman çalışan HTCP'ye bağlanır.

Başlangıçta vahşi ve koltuk değneği gibi görünüyor, ancak:

  • İşe yarıyor.
  • Her şeyi özetleyerek, Çin'den sipariş vermek bana 3-4 bin rubleye mal oldu.

Neden bir HDMI yakalama kartı kullanmadım? Çok basit: En ucuz ve en uygun fiyatlı seçenek Blackmagic Intensity Shuttle'dır, ancak 1080p / 60fps sinyallerle çalışamaz, yalnızca 1080p / 30fps sinyallerle çalışamaz - bu kabul edilemez çünkü Resmi çekebilmek için kare hızını düşürmek istemedim. + bu işin maliyeti yaklaşık 10 bin. ruble. - sonuç bilinmiyorsa ucuz değildir.

HDMI'yi S-videoya dönüştürmedeki kayıp, 46x26 LED arka ışık çözünürlüğünde renk yakalamak için önemsizdir.

Başlangıçta, S-video çekmek için EasyCap kullanmayı denedim (birçok Çince varyasyonu var), ancak sonuç olarak, orada kullanılan çip son derece zayıf ve openCV kullanarak onunla çalışamazsınız.

Tek dezavantajı, S-Video çıkış sinyalinin kenarlarda siyah bantlar içermesi, gerçek içeriği kesmesi (yaklaşık %2-5), bu bantları kaldırmak için çıkış görüntüsünü yakalama kartından kırptım, görüntünün kaybı bu alanlarda pratikte sonucu etkilemedi.

Yazılım
Bu benim için en ilginç kısımdı, çünkü Demir parçalarıyla ortalıkta dolaşmayı pek sevmiyorum.

Görüntüyü yakalamak için openCV'yi ve özellikle onun .NET sarmalayıcı emgu CV'sini kullandım.

Ayrıca renk listesini kontrolöre göndermeden önce birkaç farklı görüntü işleme ve görüntü hazırlama tekniği uygulamaya karar verdim.

Çerçeve işleme
1. Yakalanan bir kareyi alma
2. Siyah çubukları hariç tutmak için çerçeveyi kırpın
Burada her şey basit:
frame.ROI = yeni Dikdörtgen (8, 8, çerçeve.Genişlik - 8, çerçeve.Yükseklik - 18 - 8);
Üstten 8 piksel, sağdan 8 piksel ve alttan 18 piksel kırpın. (Solda şerit yok)
3. Çerçeveyi arka ışık çözünürlüğüne göre yeniden boyutlandırın, yanımızda sağlıklı bir resim taşımamıza gerek yok
Karmaşık bir şey de yok, bunu openCV araçlarını kullanarak yapıyoruz:
frame.Resize (LedWidth - 2 * LedSideOverEdge,
LedHeight - LedBottomOverEdge - LedTopOverEdge,
INTER.CV_INTER_LINEAR);
Dikkatli okuyucu değişkenlerin bolluğunu fark edecektir. Gerçek şu ki, TV çerçevem ​​yeterince büyük, yanlarda 1 LED, üstte 1 ve altta 3 LED kaplıyor, bu nedenle yeniden boyutlandırma ekranın tam karşısındaki LED'lerde yapılıyor ve köşeleri daha sonra tamamlıyoruz. Yeniden boyutlandırırken, LED'lerin piksellerinin sahip olması gereken ortalama renkleri elde ederiz.
4. Kesilen çerçeveden LED'lerin haritalanmasını gerçekleştiriyoruz
Pekala, burada da her şey basit, aptalca her iki taraftan geçiyoruz ve sırayla 136 değer dizisini LED'lerin rengiyle dolduruyoruz. Öyle oldu ki, şu anda, diğer tüm işlemlerin bir dizi LED ile gerçekleştirilmesi, işlenmesi daha zor olan bir çerçeveden daha kolaydır. Ayrıca gelecek için, bir "derinlik" yakalama parametresi ekledim (LED renginin ortalamasını almak için ekranın kenarından piksel sayısı), ancak son kurulumda, onsuz daha iyi çıktı.
5. Renk düzeltmesi yapın (beyaz dengesi / renk dengesi)
TV'nin arkasındaki duvarlar ahşaptan yapılmış, ahşap sarı, bu yüzden sarılığı telafi etmeniz gerekiyor.
var blue = 255.0f / (255.0f + blueLevelFloat) * pixelBuffer [k];
var green = 255.0f / (255.0f + greenLevelFloat) * pixelBuffer;
var red = 255.0f / (255.0f + redLevelFloat) * pixelBuffer;
Genel olarak, başlangıçta renk dengesini bazı açık kaynak düzenleyicilerin kaynaklarından aldım, ancak beyaz değişmedi (beyaz beyaz kaldı), formülleri biraz değiştirdim, kendimi mühürledim ve doğru olanı elde ettim: eğer seviye renk bileşeni negatiftir (nasıl olduğunu açıklayacağım - bu renk eksik), sonra yoğunluğunu ekliyoruz ve tam tersi. Duvarlarım için işe yaradı: RGB (-30.5.85).

Renk düzeltmede, her bir bileşenden sadece 13 çıkararak siyah seviyelendirme (siyah RGB'de 13,13,13 civarında gelir) da yapıyorum.

6. Desatürasyon gerçekleştirin (görüntünün doygunluğunu azaltın)
Son kurulumda desatürasyon kullanmıyorum, ancak bir noktada gerekli olabilir, aslında renkleri Philips ambilight gibi daha "pastel" yapar. Kodu vermeyeceğim, sadece RGB -> HSL'den dönüştürüyoruz, Doygunluk bileşenini azaltıyoruz ve RGB'ye geri dönüyoruz.
7. Deflicker
Giriş görüntüsü "titreşiyor" - bu, sanırım, bir analog sinyale dönüşümün bir sonucudur. Önce kendim çözmeye çalıştım, sonra VirtualDub'da kullanılan Defliker filtresinin kaynak koduna baktım, C# ile yeniden yazdım (C++'daydı), çalışmadığını anladım çünkü öyle bir izlenim ki kareler arasında titreme ile savaşıyor, sonunda çözümümü birleştirdim ve bu defliker garip bir şey aldı, ancak beklenenden daha iyi çalışıyor. İlk defliker yalnızca tüm çerçevenin yoğunluğu ile çalıştı, her LED'e ayrı ayrı ihtiyacım var. Orijinal defliker yoğunluktaki değişimi bir toplam olarak karşılaştırdı, renk vektörünün uzunluğunu karşılaştırmayı daha çok seviyorum, Orijinal defliker önceki kareye kıyasla yoğunluktaki değişimin deltasını karşılaştırdı, bu uymuyor ve yeniden yaptım önceki karelerin penceresindeki yoğunluğun ortalama değerine. Ve diğer birçok küçük şey, bunun sonucunda ilk saptırıcıdan çok az şey kaldı.
Ana fikir: önceki karelerin ortalama yoğunluğuna bağlı olarak, yoğunluğu belirli bir eşikten yüksek değilse mevcut kareyi değiştirin (son kurulumda bu eşiği 25'im var), eşik aşılırsa, o zaman pencere değiştirmeden sıfırlayın.
Deflicker kodum biraz değiştirildi (bağlam dışı okunabilirlik için):
Array.Copy (_leds, _ledsOld, _leds.Length); for (var i = 0; i< _leds.Length; i++) { double lumSum = 0; // Calculate the luminance of the current led. lumSum += _leds[i].R*_leds[i].R; lumSum += _leds[i].G*_leds[i].G; lumSum += _leds[i].B*_leds[i].B; lumSum = Math.Sqrt(lumSum); // Do led processing var avgLum = 0.0; for (var j = 0; j < LedLumWindow; j++) { avgLum += _lumData; } var avg = avgLum/LedLumWindow; var ledChange = false; if (_strengthcutoff < 256 && _lumData != 256 && Math.Abs((int) lumSum - avg) >= _strengthcutoff) (_lumData = 256; ledChange = true;) // Mevcut led için ayar faktörünü hesaplayın. var ölçek = 1.0; int r, g, b; if (ledChange) (for (var j = 0; j< LedLumWindow; j++) { _lumData = (int) lumSum; } } else { for (var j = 0; j < LedLumWindow - 1; j++) { _lumData = _lumData; } _lumData = (int) lumSum; if (lumSum >0) (ölçek = 1.0f / ((ort + lumSum) / 2); var filt = 0.0f; for (var j = 0; j< LedLumWindow; j++) { filt += (float) _lumData/LedLumWindow; } scale *= filt; } // Adjust the current Led. r = _leds[i].R; g = _leds[i].G; b = _leds[i].B; // save source values var sr = r; var sg = g; var sb = b; var max = r; if (g >maks) maks = g; if (b> maks) maks = b; çift ​​s; if (ölçek * maks> 255) s = 255.0 / maks; başka s = ölçek; r = (int) (s * r); g = (int) (s * g); b = (int) (s * b); // çift k'yi vurgula; if (sr> _lv) (k = (sr - _lv) / (çift) (255 - _lv); r = (int) ((k * sr) + ((1.0 - k) * r));) if ( sg> _lv) (k = (sg - _lv) / (çift) (255 - _lv); g = (int) ((k * sg) + ((1.0 - k) * g));) if (sb> _lv) (k = (sb - _lv) / (çift) (255 - _lv); b = (int) ((k * sb) + ((1.0 - k) * b));) _leds [i] = Renkli .Argb'den (r, g, b); ) / * Geçici yumuşama aşaması. * / if (ledChange || _softening == 0) devam ediyor; var diffR = Math.Abs ​​​​(_leds [i] .R - _ledsOld [i] .R); var diffG = Math.Abs ​​​​(_leds [i] .G - _ledsOld [i] .G); var diffB = Math.Abs ​​​​(_leds [i] .B - _ledsOld [i] .B); r = _led'ler [i].R; g = _led'ler [i] .G; b = _led'ler [i] .B; int toplamı; if (fark R< _softening) { if (diffR >(_yumuşatma >> 1)) (toplam = _leds [i] .R + _leds [i] .R + _ledsEski [i] .R; r = toplam / 3;)) if (diffG< _softening) { if (diffG >(_yumuşatma >> 1)) (toplam = _leds [i] .G + _leds [i] .G + _ledsEski [i] .G; g = toplam / 3;)) if (diffB< _softening) { if (diffB >(_softening >> 1)) (toplam = _led'ler [i] .B + _led'ler [i] .B + _led'lerEski [i] .B; b = toplam / 3;)) _led'ler [i] = Color.FromArgb (r, g, b); )
_led'ler Renk sınıfının LED'lerinin bir dizisi olsun, _ledsOld - dönüşümden önceki çerçeve değerleri, LedLumWindow - önceki çerçevelerin penceresinin genişliği, yoğunluktaki ortalama değişikliği tahmin etmek için, son kurulumda 100'lük bir pencerem vardı. , bu da 30 fps'de 3 saniyeye eşittir. _lumData - önceki karelerin yoğunluk değerinin bir dizisi.

Sonunda, bu mekanizma resme beklenmedik hoş sonuçlar bile verdi, görsel olarak nasıl algılandığını tarif etmek zor, ancak dinamik kontrast gibi gerektiğinde daha koyu ve gerektiğinde daha parlak hale getiriyor. Sonuç olarak, defliker'ın amacı, yalnızca titremeyi ortadan kaldırmak değil, aynı zamanda hem bileşenler açısından hem de pencere içinde zaman açısından çıktı rengini genel olarak dengelemek için geniş oldu.

8. Komşular tarafından yumuşatma LED'leri.
Genel olarak, son kurulumda, kenar yumuşatmayı pek sevmedim ve kapattım, ancak bazı durumlarda işe yarayabilir. Burada her bir LED'in renginin komşularına göre ortalamasını alıyoruz.
var smothDiameter = 2 * _smoothRadius + 1; Array.Copy (_leds, _ledsOld, _leds.Length); for (var i = 0; i< _ledsOld.Length; i++) { var r = 0; var g = 0; var b = 0; for (var rad = -_smoothRadius; rad <= _smoothRadius; rad++) { var pos = i + rad; if (pos < 0) { pos = _ledsOld.Length + pos; } else if (pos >_ledsOld.Length - 1) (konum = konum - _ledsOld.Length;) r + = _ledsOld.R; g + = _ledsOld.G; b + = _ledsOld.B; ) _leds [i] = Color.FromArgb (r / smothDiameter, g / smothDiameter, b / smothDiameter); )
9. Geçerli durumu, gönderen paketin yakalayıp arka ışık denetleyicisine göndermesi için kaydedin.
Çerçeveleri işleme ve denetleyiciye paket gönderme sürecini kasıtlı olarak böldüm: paketler belirli bir aralıkta bir kez gönderilir (benim için 40ms), böylece arduino bir öncekini işlemek için şarkı söyler, çünkü 30ms'den daha sık boğulur, bu yüzden kare hızı yakalamaya doğrudan bağımlı olmadığımız ve bu sürece müdahale etmediğimiz ortaya çıktı (ve bir paket göndermek de zaman kaybettiriyor).
arduino hakkında biraz
Seride Arduino'ya ağır bir paket alıp gönderemezsiniz, çünkü varsayılan HardwareSerial arabelleğinin ötesine geçecek ve sonunu kaybedeceksiniz.
Çözüm oldukça basit: HardwareSerial arabelleğinin boyutunu, gönderilen paketin tamamına bir dizi renk sığdırmak için yeterli bir boyuta ayarladık, benim için 410.
kullanıcı arayüzü
Yazılımın kendisi bir win hizmeti olarak uygulandı, tüm parametreleri yapılandırmak + etkinleştirmek / devre dışı bırakmak için hizmette WebService aracılığıyla hizmete bağlanan bir Web UI yaptım. Mobil ekrandaki son arayüz şöyle görünür:
Sonuç
Sonuç olarak, sonuç tüm beklentileri karşıladı ve şimdi konsollarda oyun oynarken oyunun atmosferine daha da fazla daldım.

Çalışmanın genel bir sonucu olarak, düzenime göre atmosferin çalışmasıyla bir video kaydettim:

Test konusu 1: Pasifik Kıyıları, Şanghay savaş sahnesi, bu film test ve gösterim, birçok parlak sahne ve flaş, yıldırım çarpması vb. için iyidir.:

Test örneği 2: YouTube'dan birleştirilmiş MLP'den bazı videolar, parlak renklere sahip sahneleri (çizgileri beğendim) ve hızlı değişen sahneleri (görünümün sonunda, efektlerin etkilerini görebilirsiniz) test etmek için çok uygundur. gecikme, yalnızca videoda görünür, Gerçek görüntülemede bu fark edilmediğinde, videodaki gecikmeyi ölçmeye çalıştım - 10-20ms çıktı):

Ve son olarak, HTPC'den gelen kaynakların tüketimine dikkat çekmekte fayda var:
HTPC i3'te ASRock Vision 3D var, atmosfer hizmeti %5-10 CPU ve 32MB RAM tüketiyor.

İlginiz için teşekkür ederim, umarım makalem birine yardımcı olur.

  • öğretici

Piksel arka aydınlatmasını gösteren videolar oldukça etkileyici görünüyor - çok renkli flaşlar, dinamik yansımalar harika görünüyor ve diğer benzer arka aydınlatma türlerine kıyasla daha hareketli görünüyor.
Arduino kullanarak kontrollü ışıklarla çalışma isteği beni böyle bir sistem kurmaya yöneltti. Görünüşe göre, bu, toplamda sadece birkaç saatin harcandığı oldukça basit bir olaydır (aslında, yapının kendisi 10 dakikadır, gerisi yazılımdır). Montaj ve programlama sürecinin detaylarını bu yazıda anlatacağım. Yazılım, sonuçlar ve demo ektedir.

donanım parçası

Böyle bir arka ışık için aşağıdaki öğelere ve cihazlara ihtiyacımız var:

Diyagram (bu gurur verici kelime iki ürünü dört telli bağlamak için uygunsa) şekilde gösterilmiştir:

Montaj işlemi son derece basittir. Bunu ayrıntılı olarak açıklamanın bir anlamı yok (aynı nedenle, bitmiş "ürünün" fotoğrafları yok - İnternette dört telli çok sayıda arduin var).

  1. Her şeyi şemada gösterildiği gibi lehimleyin.
  2. Kabloları arduino'ya bağlayın, arduino'nun kendisini PC'ye bağlayın, güç kaynağını bağlayın.
  3. Krokiyi Arduino'ya dökün (aşağıya bakın), yürütülebilir dosyayı bilgisayarda çalıştırın (yazılımın bağlantıları da aşağıya bakın), programda istediğiniz COM bağlantı noktasını kurun.
    Windows Vista / 7 kullanıyorsanız - Aero'yu devre dışı bıraktığınızdan emin olun. Aksi takdirde, çalışma hızı basitçe içler acısı, anladığım kadarıyla Aero açıkken düşük ekran yakalama hızı sorununa bir çözüm yok.
  4. Her şeyin çalıştığından emin olun, kapatın.
    Yazılımın çalıştığı belirtilmelidir. yalnızca 32 bit renkte... Bu kolayca düzeltilebilir ama bence böyle bir düzenlemenin pek bir anlamı yok.
  5. Bandı monitöre takın. Bandı çevre çevresinde sol alt köşeden saat yönünde başlatmanız gerekir (LN-> LV-> PV-> PN-> LN). Hiçbir şeyi kesmenize gerek yok, bant neredeyse her yerde iyi bükülüyor, bu yüzden herhangi bir sorun olmamalı. Sabitlemek için çift taraflı bant kullandım - bant çok hafif ve bu fazlasıyla yeterli.
Bu, montajı tamamlar. Dikey ve yatay olarak piksel sayısını hesaplamak ve ayarlamak için kalır ve videoları izleyebilir, oynatabilir vb. ve sevinin.

Yazılım bölümü

Yazılım bölümü iki bileşenden oluşur:
  • Arduino için eskiz;
  • PC için kontrol programı.
Arduino için eskiz
Arduino'da aşağıdaki kodu doldurmanız gerekiyor. SmallUART kitaplığı kullanılır (ancak, özellikle olağanüstü bir şey yapmaz, isterseniz standart araçlarla yapabilirsiniz).
/ *** PİKSEL IŞIK İÇİN ARDUINO KODU *** / #include #Dahil etmek imzasız uzun lastTime; // Zaman şeridi son kez güncellendi const unsigned long fadeTimeout = 3000; /////////////////////////////////////////// // //////// // geçersiz kurulum () (UART_Init (115200); SPI.begin (); SPI.setBitOrder (MSBFIRST); SPI.setDataMode (SPI_MODE0); SPI.setClockDivider (SPI_CLOCK_DIV8); blackoutAll () ; gecikme (1); son Zaman = milis ();) ///////////////////////////// //// //////////////////// // void döngüsü () (uint8_t verisi; UART_SendByte ("R"); // Bayt "Biz" hazırız "bool geçerli = false; veri = uartRead (geçerli); if (geçerli) (uint16_t pix_num = veri * 3; // (uint16_t i = 0; i) için toplam izleyen bayt< pix_num; i++) { data = uartRead(valid); if (!valid) break; SPI.transfer(data); // Transfer byte to SPI } lastTime = millis(); } if (millis() - lastTime >fadeTimeout) blackoutAll (); ) ////////////////////////////////////////// // ///////// // Mümkün olan tüm 256 led'i kapatın void blackoutAll () ((int16_t i = 0; i için)< 768; i++) SPI.transfer(0); //погасить все пикселы ленты } //////////////////////////////////////////////////////////// // Read byte with timeout unsigned char uartRead(bool& valid) { uint8_t res = 0; valid = false; for (uint8_t i = 0; i < 255; ++i) { // Max timeout 256*10 if(UART_ReadByte(res)) { valid = true; break; } delayMicroseconds(10); } return res; }

Burada her şey son derece basit:

  1. Arka ışık verilerini almaya hazır olduğumuza dair bir sinyal gönderiyoruz;
  2. Kısa bir süre için veri bekliyoruz;
  3. Veri geldiyse, bu verinin ilk baytı servis verilen diyotların sayısıdır. İzlenecek bayt sayısını bulmak için 3 (RGB) ile çarpın;
  4. Alınan verileri kasete iletiyoruz;
  5. Feed'in son güncellemesinin zaman damgasını güncelleriz (bu, feed'in tüm piksellerinin zaman aşımına uğraması ve boş bırakılması için gereklidir).
bilgisayar programı
Bunun için hazır çözümler var gibi görünüyor, ancak gördüklerim kategorik olarak hoşuma gitmedi ve genel olarak sportmenlik dışı, Arduino'nun kullanılması boşuna. Bu nedenle, bir sandviçi çiğnerken, ekranın alanlarını yakalamak, işlemek ve gerekli verileri teybe aktarmak için sol ayakla bir program yazılmıştır. Sakatat içeren programın tamamı github.com/sergrt/pixie adresindeki github'da mevcuttur (kod için tekme atmayın).
Qt 5.0.1 kullanılır - ilgi uğruna, bu özel sürümde bulunan hiçbir özel şey dahil değildir, bu nedenle oldukça iyi çalışır ve son 4 düzenleme yeni sınıflar kullanılarak yapılmıştır, bu nedenle artık kaynak kodu ile uyumlu değil 4. sürüm Eğlencemin çoğunu Windows altında yaptığım için proje bunun için yapıldı - Visual Studio 2012, GDI veya DirectX yakalama. Dürüst olmak gerekirse, Qt Creator için .pro dosyaları oluşturmaya çalıştım, ancak yeni VS Qt Eklentisi ile bu işlem çok can sıkıcı, sonuç olarak bu dosyalar hemen çalışmadı, anlamadım. Ancak her şey linux altında sorunsuz bir şekilde derlenebilir, bkz. UPD #3.
Program ayarları
Ana ayar, LED'lerin sayısını dikey ve yatay olarak belirlemek ve ayrıca yakalanan alanların boyutunu ayarlamaktır. Benim 22" dikey olarak 10 parça ve yatay olarak 17 parça sığdırır:


Çerçeve hızı sınırını yaklaşık 30 olarak ayarlamak mantıklıdır. Mümkün olan en yüksek hızda çalışmak için "0" değeri kullanılır.

Ayrıca Arduino ile iletişim için bağlantı noktasını ve baud hızını doğru bir şekilde belirtmeniz gerekir. Varsayılan çizim hızı 115200'dür:

Parlaklığı, tetik eşiğini ve sınırlayıcıyı ayarlamak için ayrı bir "İşleme" sekmesi yapılmıştır. Orada sunulan parametreler gerçek zamanlı olarak ayarlanır:

Programla çalışmanın rahatlığı için, başlangıçta yakalamayı otomatik olarak çalıştıracak şekilde yapılandırabilir ve ayrıca bildirim alanına simge durumuna küçültülmüş olarak başlatabilirsiniz.

İlgilenenler için yazılımın içi hakkında biraz
Ana fikir, belirli bir mekanizmaya göre alanları yakalayan, ayarlanabilir bir fps ile bir iş parçacığı başlatmak ve bu alanları işlemek ve ardından banda aktarmak için aktarmaktır. Alanlar ayarlara göre yakalanır (kimin aklına gelirdi), pikselin rengi, ekranın karşılık gelen alanının üç RGB kanalının basit ortalaması ile belirlenir. İsteğe bağlı olarak (önişlemci yönergeleri ile) Lab'de dönüştürmeyi ve kuvvetlerine göre ortalamayı etkinleştirebilirsiniz, ancak bu kod parçası hiçbir şekilde optimize edilmemiştir (İnternetten olduğu gibi), yavaşlar, bu nedenle devre dışı bırakılır. varsayılan. Ayrıca, Lab'in herhangi bir özel avantajı bu görev bağlamında fark edilmez, dolayısıyla bu üzülmek için bir neden değildir.
Alanlar dikey ve yatay olarak işlenir ve kasete sol alt köşeden başlayarak ve çevre boyunca saat yönünde (tıpkı montaj sırasında bandı monitöre sardığımız gibi) bir renk dizisi gönderilir.
DirectX'i hızda yakalamak, GDI'dan yakalamaya yaklaşık olarak eşittir, ilk durumda tüm ekran yakalanır ve ikincisinde - sadece gerekli parçalar. Muhtemelen burada bir miktar optimizasyon marjı vardır.
Memcpy'nin bol kullanımı, öncelikle işin hızıyla ilgilidir - diğer tüm yöntemler, bir dereceye kadar daha yavaş olduklarını göstermiştir.

Sonuçlar ve izlenimler

Şeridin büyük bir parlaklık marjı vardır, bu iyidir - diğer ışık kaynaklarıyla bile kullanabilirsiniz. Tamamen karanlıkta, kaydırıcıları hareket ettirmek ve daha yumuşak hale getirmek daha iyidir. Bandın kendisi bağımsız bir aydınlatma kaynağı olarak hizmet edebilir, sadece taslağı yeniden yapmanız gerekir.
Monitörün / TV'nin köşegeninin küçük bir önemi olmadığını düşünüyorum. Daha büyük daha iyi.
Ayrıca ekranı, LED'lerin yansıdığı yakınlarda hiçbir yüzey olmayacak şekilde kurmalısınız (benim durumumda bunlar hoparlörlerin yan yüzeyleridir) - bu özellikle kritik değildir, ancak keskin bir şekilde ayırt edilen piksellerin olması daha iyidir. hiç görünmüyor - aralarında adil bir mesafe olduğu için resmi en iyi şekilde etkilemiyor.

Neyi beğendik:
Böyle bir arka ışıkla video izlemek ve oyun oynamak, gözleri öznel olarak rahatlatır - monitör resmine sert odaklanma kaybolur. Parlaklık ile aşırıya kaçmazsanız, göz yorgunluğu hissi daha sonra gelir. Videoyu izlemek en azından olağandışıdır, bütünlük adına bunu uzaktan yapmak daha iyidir.

Neyi beğenmedi:
Arka ışık sisteminin kendisi hakkında özel bir şikayet yoktur, ancak daha önce de belirtildiği gibi, zevkin doygunluğu için doğru ortama ihtiyacınız vardır - parlama yüzeylerinin olmaması, ekranın arkasında tek tip bir renk arka planı vb. Çalışma sırasında, monitörümün tasarım zevklerinin bandın normal çalışmasına biraz müdahale ettiği ortaya çıktı - ön panel şeffaf plastikten yapılmış ve tüm çevre boyunca arka kapağın birkaç milimetre üzerinde, özellikle alttan çıkıntı yapıyor. Bu nedenle, bandın nispeten uzağa sabitlenmesine rağmen, bu panelin kenarlarında ayrı ayrı LED'ler görülebilir. Sanırım bununla çok az insan karşılaşacak, ama yine de bilginin önceden mevcut olmasına izin verin.

Aşağıda dinamik olarak nasıl göründüğünü gösteren bir video var. Operatör engellenen ufuk için özür diler.

Mayo incelemelerini biraz seyreltmek için size bir TV için dinamik arka aydınlatma oluşturma deneyimimden bahsedeceğim. muska habr yapmayı bırak
Ana bölüm arka ışık yine de bir LED şerit var, bu yüzden başlığa koymaya karar verdim. inşaatta biraz daha fazla bileşen olmasına rağmen.

Uzun zamandır Philips olmayan TV'nize arka ışığı vidalamak istediyseniz, ancak denemekten korktuysanız, deneyin. göründüğünden daha kolay.

Bir tohum için sonucun küçük bir videosu.


Şu anda - arka ışık daha da havalı çalışıyor - ayarlarda daha yüksek bir parlaklık ve daha yüksek bir yenileme hızı ayarladım, şimdi aksiyon filmlerinde veya bir kulüpteki sahnelerde (çerçevede flaş flaş olduğunda) - tüm duvar sadece ışıkla patlar

Nasıl yapıldığı oldukça basit:
+
+
+
Biraz cesaret =
Ambilight

Daha ayrıntılı olarak, noktadan noktaya:
1 Ahududu zaten o zaman vardı. Amazon'da aynı yerden aldım, ama bence rolün kökeni burada oynamıyor - yönetim kurulu birleşik ve tamamen her yerden satın alabilirsiniz - en önemli şey BU'yu almanızı önermem. Ek radyatörler olmadan maksimum frekansta belirli bir süre çalıştıktan sonra, podglyuchitsya'ya başladım. Aşırı ısınma için yazıyorum ama aptalca bir üretim hatası olabilir. Ahududu, güç kaynağına karşı son derece hassastır, bu nedenle hemen düşük dalgalanma seviyesine sahip normal bir PSU'yu stoklayın ... (ve yük altında batmamak için)
2 Gerçek bant. Nasıl çalışır bence videoda görmek oldukça güzel. bandın kendisinde özel bir şey yok - TV'nin tam olarak 3 tarafı için yeterli olacak şekilde parçaları kestim. Bükülme noktalarını tel parçalarıyla lehimledim (bağlantıyı başlangıçta konektörlerle yaptım, ancak tel parçalarının uzun süre dışarı çıkması çabucak çileden çıktı - her şeyi kestim ve küçük parçalar halinde lehimledim)
3 Ustaca program hiperion. Aptalların talimatlarına göre ahududulara yüklendi (işletim sistemim olarak multimedya OpenElec'im var). Hatta ilk seferde başardım. Çalışma sürecinde, ekranın kenarlarının renk verilerini aptalca yakalar, ortalamaları alır ve LED şeridine kontrol sinyalleri gönderir. Bant gökkuşağının tüm renkleriyle göz kırpıyor, seyirciler çok seviniyor. Çalışma sırasında, 30 gig ağırlığında fullHD oynatırken, yüzde başına ek yük %5-10'dur. Hız hiçbir şekilde etkilenmez.

Sonuç, en çılgın beklentilerin ötesinde:
Metre başına 30 tonluk LED yoğunluğu ile TV setinin arkasındaki tüm duvar (yaklaşık 10-15 santimetre uzaklaştırma) ekranın renkleriyle renklendirilmiştir. görsel olarak, sahne birbirinden ayrılıyor ... iyi, bu duvar olduğu kadar. iletimde gecikme yoktur. en azından gözle izlemek imkansız. her şey pürüzsüz ve net. Bir akıllı telefon için, arka ışığı salon moduna geçirebileceğiniz harika bir program var - istediğiniz rengi / parlaklığı ayarlayın veya önerilen desenlerden birini çalıştırın (koşan kırmızı ışık veya sadece bir gökkuşağı veya örnek renk geçişleri).
Çizgi film izlerken arka ışık kapatıldığında, kızı çileden çıkar ve her şeyi geri vermeyi talep eder.)))

Peki, MySKU politikasına uymak için ayrıntılar hakkında bir inceleme:
LED şerit - birçok kez gözden kaçmıştır. Ben de aynısını aldım. Çok iyi. kalite mükemmel. hafızanın hizmet edip etmediğini gösterir - 16 milyon ton. tam olarak sayılmazdı. ek güç kaynağı gerektirir - 5v 2A ünitede artı veya eksi asılı - 2 metre fazlasıyla yeterlidir. 3 için yeterli bence ama garanti veremem. Kontrol kontaklarını ahududu GPIO'ya getirdim.

Malinka tek kartlı bir bilgisayardır. Sadece tembeller gözden kaçmazdı. Hem Linux'un temellerine hakim olmak hem de minimalist ve esnek bir medya merkezi oluşturmak için harika bir şey. Benim için ideal bir seçenek olduğu ortaya çıktı: Bana sunulan herhangi bir içeriği kaydırıyor, bir alıcı olarak çalışıyor ve İnternet TV'yi gösteriyor, bir telefondan veya dizüstü bilgisayardan bir şey başlatmak istediğimde AirPlay sinyal alıcısı gibi davranıyor. Harika bir şey - 3 watt ve çok eğlenceli + kutudan çıktığı gibi HDMI CEC desteği - her şey TV'nin kendi uzaktan kumandasından kontrol ediliyor.

Ve son olarak, takip eden başka bir video:

Birkaç gün önce daha fazla demovidos yapmaya karar verdim - zaten yeni bir dairede.

duvarın rengi fıstık, ayarları değiştirmedim ve yapmayacağım. yani renkler biraz yeşil. Beğendim ama senin fikrin umurumda değil)

+69 almayı planlıyorum Favorilere ekle incelemeyi beğendim +16 +48