Strona 1 z 1
Wypełnienie komórki kolorem na podstawie parametrów RGB.
: czw lis 26, 2015 11:39 am
autor: Julius_PL
Witam,
potrzebuję wypełnić kolorem komórki np w kolumnie D na podstawie danych RGB z kolumn A, B, C.
Przeszukałem, googlowałem i nie znalazłem.
Jest kilka przykładów gdzie zwracana jest wartość rgb, albo kolorowanie przy użyciu stylów, ale mnie chodzi o konkretny kolor RGB, pewnie przy użyciu makra.
Będę wdzięczny za ew. pomoc czy wskazówki.
Re: Wypełnienie komórki kolorem na podstawie parametrów RGB.
: czw lis 26, 2015 7:42 pm
autor: Julius_PL
Witam ponownie.
Zamiast szukać na szybko napisałem jak poniżej.
Na razie zaspokaja to moje potrzeby.
Może komuś się przyda.
Kod: Zaznacz cały
Sub BackColorRGB
oDocument=ThisComponent 'wyróżnienie aktywnego dok. (=>Selection)
oSheet=oDocument.Sheets.getByName("Arkusz1") 'wyróżnienie arkusza nr1
for i=1 to 100 ' dla 100 wierszy
oCell=oSheet.getCellByPosition(3,i)
oCell.CellBackColor = RGB(oSheet.getCellByPosition(0,i).getValue(), oSheet.getCellByPosition(1,i).getValue(),oSheet.getCellByPosition(2,i).getValue())
next i
End Sub
Pozdrawiam.
Re: Wypełnienie komórki kolorem na podstawie parametrów RGB.
: czw sty 21, 2016 4:34 pm
autor: qdq
Dzięki. Przyda się.
Można użyć jako bogatszą alternatywę dla formatowania warunkowego.
Re: Wypełnienie komórki kolorem na podstawie parametrów RGB.
: czw mar 03, 2016 4:51 pm
autor: qdq
Rozbudowałem powyższe makro, tak, żeby kolorowało komórki zaznaczonego zakresu od czerwonego do zielonego w odniesieniu do średniej, minimum i maksimum z danej kolumny. Przydatne, żeby szybko ocenić trendy bez rysowania wykresów.
Niestety makro wykonuje się bardzo powoli. Czy ktoś z większym doświadczeniem miałby ochotę rzucić okiem i dać kilka wskazówek jak je zoptymalizować?
Kod: Zaznacz cały
Sub RGB_kolumny
oRange=ThisComponent.getCurrentSelection()
for i = 0 to oRange.getColumns.getCount - 1
' zliczanie średniej, maxa i mina
min=0
max=0
suma=0
sred=0
licz=0
for j = 0 to oRange.getRows.getCount - 1
oCell=oRange.getCellByPosition(i,j)
suma = suma + oCell.value
If max < oCell.value Then max = oCell.value
If min > oCell.value Then min = oCell.value
if oCell.string <> "" then licz = licz + 1
next j
sred = suma/licz
for j = 0 to oRange.getRows.getCount - 1
oCell=oRange.getCellByPosition(i,j)
war = oCell.value
r=255
b=255
g=255
if sred = 0 then sred = 0.001
if min = 0 then min = -0.001
if max = 0 then max = 0.001
if war <= sred then g = g - 200 * (war-sred)/(min-sred)
if war <= sred then b = b - 255 * (war-sred)/(min-sred)
if war > sred then r = r - 255 * (war-sred)/(max-sred)
if war > sred then b = b - 200 * (war-sred)/(max-sred)
if r > 255 then r = 255
if r < 0 then r = 0
if g > 255 then g = 255
if g < 0 then g = 0
if b > 255 then b = 255
if b < 0 then b = 0
oCell.CellBackColor = RGB(r,g,b)
if oCell.value = 0 then oCell.CellBackColor = RGB(230,230,230)
if oCell.string = "" then oCell.CellBackColor = RGB(230,230,230)
if oCell.value = min then oCell.CellBackColor = RGB(250,0,0)
if oCell.value = max then oCell.CellBackColor = RGB(0,250,250)
next j
next i
end sub
Re: Wypełnienie komórki kolorem na podstawie parametrów RGB.
: czw mar 03, 2016 5:08 pm
autor: Jan_J
Wszystkie operacje powtarzasz wewnątrz podwójnej pętli. Na dodatek (chyba) źle, bo jeżeli pętla wylicza średnią, to zanim nie skończy, nie nie znasz ostatecznego wyniku. W takim razie nie powinno się go używać w tej samej pętli do obliczenia koloru. Chyba że chodzi właśnie o kolorowanie według naszej przyrastającej wiedzy o średniej; bywają takie zadania.
Optimum imho jest takie:
[*]pierwszy blok liczy statystyki z danych: min, max, średnią. Możesz to robić gotowymi funkcjami albo własną pętlą. Funkcjami będzie szybciej. W pseudokodzie
min = max = srednia = wartość pierwszej komórki
w pętli po komórkach
w = wartość bieżącej komórki # ważne żeby nie pobierać danej wiele razy; to trwa
if w < min: min = w else if w > max: max = w endif; srednia = srednia + w
koniec pętli (podwójnej)
srednia = srednia / liczba komórek w obszarze
modyfikacja min i maks, tak by nie dzielić przez 0 w przypadku, kiedy wszystkie wartości są jednakowe
[*]drugi blok przygotowuje tablicę kolorów o odpowiedniej długości
alokacja tablicy kolory o długości nk
dla każdego i od 0 do nk-1: kolory[nk] = rgb(coś tutaj, żeby umieć obliczyć wartość koloru na podstawie numeru)
w innych miejscach nie używamy funkcji rgb, tylko tablicy wynikowej
[*]w bloku trzecim przechodzisz jeszcze raz po obszarze i przypisujesz każdej komórce kolor
wynikający z jej wartości. W pseudokodzie:
w pętli po wszystkich komórkach (podwójnej)
w = wartość komórki
k = numer pozycyjny wartości koloru na podstawie nk i położenia w względem min, maks, średnia
(najlepiej prostą proporcją, można wyszukiwaniem binarnym, if-ami jest najwolniej)
pod kolor komórki podłóż kolory[k]
koniec pętli
OK, zdaje sę że chcesz to robić osobno w wierszach, więc część zastrzeżeń jest nieważna.
Ale unikaj i tak: wielokrotnego odwoływania się do właściwości komórki; obliczania wewnątrz pętli rzeczy, które za każdym razem wychodzą takie same.
Re: Wypełnienie komórki kolorem na podstawie parametrów RGB.
: czw mar 03, 2016 6:23 pm
autor: belstar
Możesz wyeliminować ciągłe powtarzanie pobierania danych, przez pobranie całego bloku za jednym zamachem (tablica - getDataArray()) i pętle wykonać na danych w pamięci, to samo dotyczy się kolorów, jakaś deklaracja tablicy.
I jeszcze by się zdało jakąś obsługę błędów zaimplementować, bo jak zaznaczę większy zakres jak potrzeba to występuje wyjątek.