Hỏi về thuộc tính BackColor của Command Button (Control ToolBox)

Liên hệ QC

ndu96081631

Huyền thoại GPE
Thành viên BQT
Super Moderator
Tham gia
5/6/08
Bài viết
30,703
Được thích
53,952
Trong 1 sheet có khá nhiều Command Button (Cmd), tôi dùng vòng lập duyệt qua các Cmd này và thay đổi 1 số thuộc tính của nó!
Ví dụ: tôi dùng code này để thay đổi độ dài, rộng:
PHP:
Sub ChangeObj()
  Dim Obj As OLEObject
  For Each Obj In ActiveSheet.OLEObjects
   Obj.Height = 50
   Obj.Width = 100
  Next
End Sub
Code chạy không có vấn đề! Nhưng tôi không tài nào tìm được code gì nói về việc thay đổi thuộc tính BackColor của Cmd cả
Mong các bạn chỉ giúp!
 

File đính kèm

Trời ạ, chơi trò sắp xếp lại --=0, đúng là củ chuối thật, nhưng mà cái yêu cầu này còn củ chuối hơn, tạm thời chưa nghĩ ra cách nào, thôi để tìm hiểu sau vậy -+*/.
 
Upvote 0
Trời ạ, chơi trò sắp xếp lại --=0, đúng là củ chuối thật, nhưng mà cái yêu cầu này còn củ chuối hơn, tạm thời chưa nghĩ ra cách nào, thôi để tìm hiểu sau vậy -+*/.
Đành vậy! Nhưng cái quan trọng ở đây là tìm hiểu xem Excel đã sắp xếp bảng màu ấy dựa trên tiêu chí nào (chẳng lẽ sắp tùy tiện)
Tôi còn có 1 yêu cầu "củ chuối" không kém:
- Khi ta dùng For Each thì để ý rằng vòng lập duyệt theo tên Object (chính xác là số nằm sau tên) chứ không theo thứ tự của vị trí... Vậy nếu tôi muốn bắt buộc For phải quét theo vị trí của Object thì làm thế nào? Tức tô màu từ phải sang trái, từ trên xuống dưới
Tuy rằng "củ chuối" thật nhưng tôi biết có nhiều người cần vụ này... Vì quá trình vẽ object, rồi xóa, rồi lại vẽ... vô tình đã làm cho tên và vị trí lộn xộn hết... Ví dụ: Cmd01 thì nằm cuối cùng, Cmd05 nằm ở giữa và Cmd11 nằm đầu tiên...
vân vân.. và vân vân...
Các cao thủ thử nghĩ xem!
 
Lần chỉnh sửa cuối:
Upvote 0
Đành vậy! Nhưng cái quan trọng ở đây là tìm hiểu xem Excel đã sắp xếp bảng màu ấy dựa trên tiêu chí nào (chẳng lẽ sắp tùy tiện)
Tôi còn có 1 yêu cầu "củ chuối" không kém:
- Khi ta dùng For Each thì để ý rằng vòng lập duyệt theo tên Object (chính xác là số nằm sau tên) chứ không theo thứ tự của vị trí... Vậy nếu tôi muốn bắt buộc For phải quét theo vị trí của Object thì làm thế nào? Tức tô màu từ phải sang trái, từ trên xuống dưới
Tuy rằng "củ chuối" thật nhưng tôi biết có nhiều người cần vụ này... Vì quá trình vẽ object, rồi xóa, rồi lại vẽ... vô tình đã làm cho tên và vị trí lộn xộn hết... Ví dụ: Cmd01 thì nằm cuối cùng, Cmd05 nằm ở giữa và Cmd11 nằm đầu tiên...
vân vân.. và vân vân...
Các cao thủ thử nghĩ xem!

Lồng vào một vòng lặp nữa xác định theo Left và Top bác ạ.

Như vậy cũng hơi . . mệt!

Hoặc chạy một vòng lặp, cho tất cả vị trí của các Command vào 1 mảng, sắp xếp lại theo : Left --> Top --> Ten
Sau đó căn cứ vào mảng này để gọi Command ra

Thân!
 
Upvote 0
Đành vậy! Nhưng cái quan trọng ở đây là tìm hiểu xem Excel đã sắp xếp bảng màu ấy dựa trên tiêu chí nào (chẳng lẽ sắp tùy tiện)
Tôi còn có 1 yêu cầu "củ chuối" không kém:
- Khi ta dùng For Each thì để ý rằng vòng lập duyệt theo tên Object (chính xác là số nằm sau tên) chứ không theo thứ tự của vị trí... Vậy nếu tôi muốn bắt buộc For phải quét theo vị trí của Object thì làm thế nào? Tức tô màu từ phải sang trái, từ trên xuống dưới
Tuy rằng "củ chuối" thật nhưng tôi biết có nhiều người cần vụ này... Vì quá trình vẽ object, rồi xóa, rồi lại vẽ... vô tình đã làm cho tên và vị trí lộn xộn hết... Ví dụ: Cmd01 thì nằm cuối cùng, Cmd05 nằm ở giữa và Cmd11 nằm đầu tiên...
vân vân.. và vân vân...
Các cao thủ thử nghĩ xem!
- Về cái thứ tự bảng màu tôi đang nghĩ có thể nó sắp theo thứ tự mã màu RGB, vì ta thấy nó bắt đầu bằng màu ĐEN có mã là RGB(0, 0, 0), giá trị nhỏ nhất. Kết thúc bằng màu TRẮNG có mã là RGB(255, 255, 255), giá trị lớn nhất. Vấn đề là tôi chưa rõ trong cái Pallet màu của excel thì nó được sắp theo thứ tự từ trên xuống dưới, hay từ trái qua phải, hay theo đường chéo dần cho đến cuối.
- Về cái yêu cầu "chủ chuối" thứ 2 này thì tôi nghĩ nó không củ "chuối lắm" :-=. Bạn có thể dùng giải pháp là sét đến Control nào thì di chuyển nó về đúng với vị trí của nó rồi hãy tô màu. Mà để di chuyển nó về đúng vị trí của nó thì đã có thuật toán rồi, bạn tham khảo thử file này nhé, bạn tha hồ thay đổi vị trí các Control, đổi tên, xóa đi tạo lại ..., sau khi chạy Macro thì các Control được tô màu không hề thay đổi.
 

File đính kèm

Upvote 0
- Về cái yêu cầu "chủ chuối" thứ 2 này thì tôi nghĩ nó không củ "chuối lắm" :-=. Bạn có thể dùng giải pháp là sét đến Control nào thì di chuyển nó về đúng với vị trí của nó rồi hãy tô màu. Mà để di chuyển nó về đúng vị trí của nó thì đã có thuật toán rồi, bạn tham khảo thử file này nhé, bạn tha hồ thay đổi vị trí các Control, đổi tên, xóa đi tạo lại ..., sau khi chạy Macro thì các Control được tô màu không hề thay đổi.

Ở đây nói là vị trí mới bạn ạ, tức là từ trên xuống dưới, từ phải qua trái thì các màu theo quy định.

Code của bạn làm cho các CM trở hết lại vị trí ban đầu (mà vị trí này lại phụ thuộc vào màu sắc của các CM)

Như vậy khi di chuyển thì các CM không còn giữ màu cũ nữa mà phụ thuộc vào cái CM trước đó màu gì ??

Và bạn nên phân biệt giữa Command Button, với CheckBox; TextBox; OptionButton; ListBox; ComboBox; ToggleButton . . .

Gộp chung tất cả vào Shape thì không được tổng quát.

Và bạn hãy thử Code trên với >57 CM xem thế nào ?? Nó chồng lên nhau ngay.

Thân!
 
Upvote 0
Xin cho hỏi có thể căn cứ vào thuộc tính Object.LeftObject.Top của object trên sheet để sắp xếp thứ tự mã màu cho các Object được không?
 
Upvote 0
Xem ra vụ điều khiển các Object Control Toolbox này quả thật không đơn giãn! Rất nhiều cách... Cái khó khăn lớn nhất là các thuộc tính của chúng không dể dàng hiện ra sau khi ta gõ dấu chấm
Về việc set màu theo vị trị, theo tôi thì không nên trả nó về vị trí ban đầu mà nên set màu cho nó theo vị trí mới....
Xin cho hỏi có thể căn cứ vào thuộc tính Object.LeftObject.Top của object trên sheet để sắp xếp thứ tự mã màu cho các Object được không?
Hướng mà tôi đang nghĩ đến là hướng này đây! Cũng giống như Mr OkeBab nói... Tôi đang nghĩ phải dùng vòng lập nữa để lấy vị trí của nó cho vào 1 mãng... Tiếp theo sẽ set màu theo các số từ nhỏ đến lớn (giống như trong công thức ta dùng hàm SMALL vậy)
Sẳn đây cho hỏi: trong VBA có hàm nào tương đương với SMALL và LARGE không?
Mong các cao thủ chỉ giáo thêm!
(càng học càng ngu!)
 
Lần chỉnh sửa cuối:
Upvote 0
Ở đây nói là vị trí mới bạn ạ, tức là từ trên xuống dưới, từ phải qua trái thì các màu theo quy định.

Code của bạn làm cho các CM trở hết lại vị trí ban đầu (mà vị trí này lại phụ thuộc vào màu sắc của các CM)

Như vậy khi di chuyển thì các CM không còn giữ màu cũ nữa mà phụ thuộc vào cái CM trước đó màu gì ??

Và bạn nên phân biệt giữa Command Button, với CheckBox; TextBox; OptionButton; ListBox; ComboBox; ToggleButton . . .

Gộp chung tất cả vào Shape thì không được tổng quát.

Và bạn hãy thử Code trên với >57 CM xem thế nào ?? Nó chồng lên nhau ngay.

Thân!
- Như trên tôi có nói là màu sẽ phụ thuộc vào vị trí chứ ko phải vị trí phụ thuộc vào màu, nên khi di chuyển các CM rồi chạy lại ta vẫn có bảng màu không thay đổi.
- Vì tôi đang đi theo cái yêu cầu cũ là xử lý cho Command button, còn việc phân biệt thì có thể phân biệt rất dễ thông qua tiền tố của tên Control, giả sử cái tiến tố mặc định của nó là .
- Với CM>57 sẽ bị chồng lên cũng là do xuất phát từ cái yêu cầu là 56 cái button, nên tôi đã gộp cái màu với số thứ tự của CM, mà màu ở đây tôi MOD cho 56 nên số thứ tự CM>57 sẽ bị lặp. Cái này có thể sửa lại bằng cách thêm 1 biến thứ tự tăng dần như biến i sau đây là OK.
Mã:
Sub ChangeObj()
  Dim Obj As Shape
  Dim iColor As Long
[COLOR=Red]  Dim i As Long
[/COLOR]  For Each Obj In ActiveSheet.Shapes
[COLOR=Red]    If Left(Obj.Name, 13) = "CommandButton" Then ' Command button
[/COLOR]        Obj.Height = iHeight
        Obj.Width = iWidth
        Obj.Top = ([COLOR=Red]i[/COLOR] \ iCols) * iHeight + iTop
        Obj.Left = ([COLOR=Red]i[/COLOR] Mod iCols) * iWidth + iLeft
[COLOR=Red]        i = i + 1
[/COLOR]        iColor = ((iColor) Mod 56) + 1
        Obj.OLEFormat.Object.Object.BackColor = ActiveWorkbook.Colors(iColor)
[COLOR=Red]    End If
[/COLOR]  Next
End Sub
Giờ thì bạn có thể thêm bao nhiêu CM tùy ý, ta sẽ luôn có 1 bảng màu giống nhau sau mỗi lần chạy(>56 thì sẽ lặp lại)
 
Upvote 0
- Như trên tôi có nói là màu sẽ phụ thuộc vào vị trí chứ ko phải vị trí phụ thuộc vào màu, nên khi di chuyển các CM rồi chạy lại ta vẫn có bảng màu không thay đổi.

Như vậy là một CM sẽ luôn có 1 màu cố định phải không bạn ???

Bài toán đặt ra : Nếu CM1 thay đổi chỗ cho CM20 thì như vậy màu của chúng sẽ thay đổi cho nhau.

Và một điều nữa là khi người dùng di chuyển vị trí các CM thì bạn lại cho nó trở về vị trí cũ, vấn đề vẫn giữ nguyên vị trí mới này bạn ạ. Và sau đó dựa vào vị trí mới này để set màu

Còn nếu làm như trên (1 CM là cố định màu) thì ta cũng có thể tạo ra 1 Function trả về màu của CM. Ứng với mỗi 1 CM có một màu cố định. Chỉ cần Select Case là được (tuy có hơi nhiều). Khi cần thì chỉ cần gọi ra là xong.

- Vì tôi đang đi theo cái yêu cầu cũ là xử lý cho Command button, còn việc phân biệt thì có thể phân biệt rất dễ thông qua tiền tố của tên Control, giả sử cái tiến tố mặc định của nó là .

Là gì vậy bạn ?? Bạn định căn cứ vào tên để phân biệt với 1 tiền tố VD như là CM*** ???


Thân!
 
Upvote 0
Như vậy là một CM sẽ luôn có 1 màu cố định phải không bạn ???
Bài toán đặt ra : Nếu CM1 thay đổi chỗ cho CM20 thì như vậy màu của chúng sẽ thay đổi cho nhau.
Và một điều nữa là khi người dùng di chuyển vị trí các CM thì bạn lại cho nó trở về vị trí cũ, vấn đề vẫn giữ nguyên vị trí mới này bạn ạ. Và sau đó dựa vào vị trí mới này để set màu
Còn nếu làm như trên (1 CM là cố định màu) thì ta cũng có thể tạo ra 1 Function trả về màu của CM. Ứng với mỗi 1 CM có một màu cố định. Chỉ cần Select Case là được (tuy có hơi nhiều). Khi cần thì chỉ cần gọi ra là xong.
Cái này thì có lẽ phải hỏi lại ndu về cái yêu cầu, vì hình như tôi và bạn đang hiểu 2 vấn đề khác nhau. Tôi thì hiểu là ndu đang muốn có 1 cái bảng màu với thứ tự các màu là không thay đổi qua mỗi lần chạy mà không phụ thuộc vào tên cũng như thứ tự tạo ra các CM. Cái cách cũ của ndu ndu tự sắp xếp các CM thành bảng màu, và nếu ta đổi vị trí 2 CM cho nhau thì bảng màu cũng bị thay đổi màu 2 vị trí đó, hoặc giả sử tôi xóa CM đầu tiên đi(màu đen) và thêm mới 1 CM mới rồi lại đặt đúng vào vị trí đầu tiên đó, thì vị trí đầu tiên sau khi chạy sẽ là màu trắng, các màu tiếp theo trong bảng màu sẽ bị dịch đi 1 màu.
Nếu đúng ý của ndu như vậy thì cách của tôi là OK rồi. Còn khi cần lấy màu thì ta dựa vào màu của CM đó luôn chứ đâu cần vòng lặp. Còn muốn lấy màu theo vị trí thì khi đó người ta dùng mảng Control chứ không dùng các Control độc lập đâu. Tuy nhiên trong trường hợp độc lập này ta vẫn có thể lấy màu theo vị trí được, bằng cách dựa theo Top và Left giống như ý kiến của ca_di, vì từ code ta đã lấy Top và Left của CM từ vị trí của nó thì từ Top và Left ta cũng có thể trả về vị trí của nó được thôi.
Là gì vậy bạn ?? Bạn định căn cứ vào tên để phân biệt với 1 tiền tố VD như là CM*** ???
Cái này thì đúng rồi, tôi định nói là CommandButton mà quên chưa paste vào//////. Giải pháp này tôi nghĩ là ko có vấn đề gì.
 
Upvote 0
Tôi thì hiểu là ndu đang muốn có 1 cái bảng màu với thứ tự các màu là không thay đổi qua mỗi lần chạy mà không phụ thuộc vào tên cũng như thứ tự tạo ra các CM.
Cái này thì đúng rồi, tôi định nói là CommandButton mà quên chưa paste vào//////. Giải pháp này tôi nghĩ là ko có vấn đề gì.

Mình lại hiểu rằng : Cứ khi vị trí thay đổi thì khi set lại màu sẽ tuần tự theo bảng mã màu, tuy nhiên bảng mã màu này sẽ ấn định lần lượt lên các CM theo đúng vị trí mới của các CM. sự lần lượt này có thể sẽ là : Từ trái qua phải, từ trên xuống dưới. Vị trí mới của các CM sẽ được giữ nguyên

Bạn thử set màu theo tuần tự các CM trong File dưới xem sao nhé : (Mình lấy VD File của bạn)

Bạn nhớ chạy OBDaoViTri để chúng thay đổi vị trí nhé. Và ở vị trí mới này, bạn hãy giữ nguyên, không được để chúng xê dịch, sau đó Set màu tuần tự lên đó.

Dĩ nhiên là mình làm được điều này (theo như trình bày ở trên), tuy nhiên mình muốn mọi người thử sức với bài toán mở rộng này xem sao.


Về tiền tố : Bạn phải nói rõ ràng hơn. Bạn dựa vào thuộc tính Name cũng là một giải pháp tốt. Tuy nhiên dựa vào proID sẽ tốt hơn nhiều.

Thân!
 

File đính kèm

Lần chỉnh sửa cuối:
Upvote 0
Mình lại hiểu rằng : Cứ khi vị trí thay đổi thì khi set lại màu sẽ tuần tự theo bảng mã màu, tuy nhiên bảng mã màu này sẽ ấn định lần lượt lên các CM theo đúng vị trí mới của các CM. sự lần lượt này có thể sẽ là : Từ trái qua phải, từ trên xuống dưới. Vị trí mới của các CM sẽ được giữ nguyên
!
Chính xác là tôi cần y chang như Mr OkeBab nói... Tùy tôi muốn kéo Cmd này đi đâu cũng được, và set lại màu theo vị trí mới này, theo thứ tự từ trái sang phải, từ trên xuống
 
Upvote 0
Như vậy bài toán này thức chất là, duyệt qua các CM trên Form và tô màu theo thứ tự từ trên xuống dưới, từ trái qua phải theo thứ tự ColorIndex của bảng màu đúng ko?Tiện đây cũng cho hỏi luôn là các CM có nằm theo kiểu matrix không(matrix có thể rỗng 1 số ô như ví dụ của okebab), nghĩa là 2 ô bất kỳ có cột hoặc là trùng nhau, hoặc là không trùng nhau, không có trường hợp giao nhau.
 
Lần chỉnh sửa cuối:
Upvote 0
rollover79 đã viết:
Như vậy bài toán này thức chất là, duyệt qua các CM trên Form và tô màu theo thứ tự từ trên xuống dưới, từ trái qua phải theo thứ tự ColorIndex của bảng màu đúng ko?
Chính xác là từ trái qua phải rồi mới từ trên xuống dưới... Thứ tự màu thì giống với thứ tự màu do Excel sắp sẳn (xem thứ tự màu khi bấm vào nút Fill Color)
rollover79 đã viết:
Tiện đây cũng cho hỏi luôn là các CM có nằm theo kiểu matrix không(matrix có thể rỗng 1 số ô như ví dụ của okebab), nghĩa là 2 ô bất kỳ có cột hoặc là trùng nhau, hoặc là không trùng nhau, không có trường hợp giao nhau.
Nằm theo matrix, không chồng nhau... nhưng cũng không chính xác 100% (vì xếp bằng tay mà) ----> Nói chung tôi sẽ cố sắp chúng như 1 khối vuông cho sư phụ thuận tiện viết code
Nói thêm:
- Trong file chỉ có Command Button nên không cần đặt điều kiện loại trừ các Object khác
- Số lượng Command Button tối đa chỉ 56 nút hoặc ít hơn
Nhờ sư phụ giúp dùm vụ này, nhân tiện để học hỏi luôn về các phương thức điều kiển Object (vụ này tôi còn quá kém)
Chân thành cãm ơn!
 
Upvote 0
Vậy bạn tham khảo thử file này xem nhé. Trong code có 3 cái Sub:
- ResetObject: sub này sẽ có nhiệm vụ sắp xếp các CM thành 1 mảng chuẩn gồm 8 cột(số dòng thì phụ thuộc vào số lượng CM). Trong sub này tôi cũng fill luôn cái Caption của các CM theo thứ tự từ 1 đến hết.
- SwapCM: sub này sẽ hỗ trợ bạn đổi chỗ 2 CM bất kỳ, cách này thì sẽ đảm bảo được vị trí đẹp mà chuẩn, dĩ nhiên bạn cũng có thể tự thay đổi bằng tay.
- FillColor: Tô màu cho các CM theo đúng thứ tự bảng màu(dĩ nhiên là thứ tự này vẫn chuối như cách của bạn:-=), và khi tô màu thì không di chuyển vị trí các CM, không tin bạn có thể lấy Caption của các CM để kiểm chứng |||||. Nó sẽ tô màu theo thứ tự vị trí của các CM, bạn có thể thử di chuyển bằng tay các CM thì nó vẫn tô theo đúng quy luật trên.
Hy vọng lần này sẽ đáp ứng đúng yêu cầu của bạn!
 

File đính kèm

Upvote 0
Web KT

Bài viết mới nhất

Back
Top Bottom