Draw a number with dropdown selection


#1

Hi all,

I need to draw a number of dropdown selected item in one of the 12 dotnet labels.
image

So, number 1 if it’s top dropdown and number 2 if it’s bottom one.

I can’t wrap my head around it, it seems. So I came here for help


#2

I don’t understand the question… try asking it differently. Where do you want to draw? In the top rectangular controls or in the dropdown controls?
Why is it necessary to ‘draw’? Does this control not support text?

… in general, are you asking how to organize the logic of the interface, or are you interested in the “drawing” technique?


#3

So, I have this 12 dotNet labels in the top which are support .text property.
Every rectangle is a specific map representation: first rectangle is Ambient Color, second is Diffuse Color and so on, from this list:
image

Also, I have these dropdown menus. Both menus have same list of maps (12)

I want to draw a number 1 in this second top rectangle if Diffuse Color is selected in the top dropdown
and I want to draw 2 in this third top rectangle if Specular Color is selected in the bottom dropdown.

There’s a case where the same map is selected in both dropdown menus, meaning both 1 and 2 should be drawn in the same rectangle - in this case I want to draw and x in this rectangle.


#4

so … as I can understand that you are asking how to organize the logic of the interface, right?
then you need to describe this logic completely…

my_material_ca = attributes my_material_ca attribid:#(122112, 121222)
(
	parameters params rollout:params
	(
		texture_states type:#inttab default:1 tabsize:12
		texture_one type:#integer default:1 ui:ui_texture_one
		texture_two type:#integer default:2 ui:ui_texture_two
		
		on texture_states set val index do
		(
			--this.params.changeTexturestate index:index state:val 
		)
		on texture_one set index do
		(
			this.params.changeTexturestate index:index state:1
		)
		on texture_two set index do
		(
			this.params.changeTexturestate index:index state:2
		)
	)
	rollout params "Parameters" width:191
	(
		local wb = 13
		local hb = 21
		local _s = 12
	
		local texture_types = #
		(
			"Ambient", 
			"Diffuse", 
			"Specular", 
			"Specular Level", 
			"Glossiness", 
			"Self-Illumination", 
			"Opacity", 
			"Filter", 
			"Bump", 
			"Reflection", 
			"Refraction", 
			"Displacement"
		)
		
		button bt01 "1" width:wb height:hb pos:[_s + 00*(wb + 1), 4]
		button bt02 "2" width:wb height:hb pos:[_s + 01*(wb + 1), 4]
		button bt03 "2" width:wb height:hb pos:[_s + 02*(wb + 1), 4]
		button bt04 "1" width:wb height:hb pos:[_s + 03*(wb + 1), 4]
		button bt05 "1" width:wb height:hb pos:[_s + 04*(wb + 1), 4]
		button bt06 "2" width:wb height:hb pos:[_s + 05*(wb + 1), 4]
		button bt07 "2" width:wb height:hb pos:[_s + 06*(wb + 1), 4]
		button bt08 "1" width:wb height:hb pos:[_s + 07*(wb + 1), 4]
		button bt09 "1" width:wb height:hb pos:[_s + 08*(wb + 1), 4]
		button bt10 "2" width:wb height:hb pos:[_s + 09*(wb + 1), 4]
		button bt11 "1" width:wb height:hb pos:[_s + 10*(wb + 1), 4]
		button bt12 "2" width:wb height:hb pos:[_s + 11*(wb + 1), 4]
		

		label lb_texture_one "Primary: " align:#right offset:[-25,12] across:2 
		dropdownlist ui_texture_one items:texture_types width:110 height:13 align:#left offset:[-25,10] 
		label lb_texture_two "Secondary: " align:#right offset:[-25,2] across:2 
		dropdownlist ui_texture_two items:texture_types width:110 height:13 align:#left offset:[-25,0] 
		
		local buttons = #(bt01, bt02, bt03, bt04, bt05, bt06, bt07, bt08, bt09, bt10, bt11, bt12)
		
		fn changeTextureState index:1 state: = 
		(
			if state != unsupplied then
			(
				texture_states[index] = state
			)
			else if index != unsupplied do
			(
				state = texture_states[index]
				if bit.get state 1 do texture_one = index
				if bit.get state 2 do texture_two = index
			)
			
			for k=1 to buttons.count do
			(
				tx = ""
				if k == texture_one then
				(
					tx = if k == texture_two then "x" else "1"
				)
				else 
				(
					tx = if k == texture_two then "2" else "" 
				)
				buttons[k].text = tx
			)
		)

		on bt01 pressed do undo "Toggle state" on changeTexturestate index:1
		on bt02 pressed do undo "Toggle state" on changeTexturestate index:2
		on bt03 pressed do undo "Toggle state" on changeTexturestate index:3
		on bt04 pressed do undo "Toggle state" on changeTexturestate index:4
		on bt05 pressed do undo "Toggle state" on changeTexturestate index:5
		on bt06 pressed do undo "Toggle state" on changeTexturestate index:6
		on bt07 pressed do undo "Toggle state" on changeTexturestate index:7
		on bt08 pressed do undo "Toggle state" on changeTexturestate index:8
		on bt09 pressed do undo "Toggle state" on changeTexturestate index:9
		on bt10 pressed do undo "Toggle state" on changeTexturestate index:10
		on bt11 pressed do undo "Toggle state" on changeTexturestate index:11
		on bt12 pressed do undo "Toggle state" on changeTexturestate index:12
		
		on params open do undo "Toggle state" on undo off
		(
			changeTexturestate()
		)
	)
)

ca = createinstance my_material_ca 
createdialog ca.params 

#5

It doesn’t make any sense to me, but it was good practice in logic… I hope it helps you somehow.


#6

Thank you, Denis. It is working as expected!
Now I’m trying to combine it with my script, which is huge and parameters is a new thing for me, so I don’t really know how it’s working. It’s almost working when merged, but I have an event in my script which is checking if anything is selected and if I do, it’s enabling some buttons in ui.

These are events on open and close:
fn event_on = (callbacks.addScript #selectionSetChanged “selection_checker()” id:#m3dLearnEvent)
fn event_off = (callbacks.removescripts #selectionSetChanged id:#m3dLearnEvent)

And here’s the function for the event:
fn selection_checker =
(
selArray = (selection as array)
if selArray.count == 1 do
(
::RipTools.selBySrc.enabled = true
)
)

I know this isn’t the right place to ask this question. Maybe you can explain how your script works?
I’m using the normal rollout:
try (
cui.UnRegisterDialogBar RipTools
destroyDialog :: RipTools
) catch ()

rollout RipTools “Ripping Tools”
(
button btn “BUTTON”
)

createDialog RipTools 140 750 1386 98 style:#(#style_sysmenu,#style_toolwindow)


#7

Let’s do things right… First, tell us what your tool should do.

To be honest, I don’t have the time or inclination to catch bugs in someone’s code. If you want to learn something, tell us about your tool idea and I will try to help you implement it step by step in a simple but professional way.

I hope this guide will be helpful to others as well.


#8

Thank you.

When I load a model in 3d max it may have diffuse map, specular, etc The number of maps occupied by textures may be different. Sometimes normal map texture is in diffuse map slot while diffuse texture is in normal map slot.

So, I came up with this simple swapper to swap diffuse and normal maps:

To quickly see which texture is applied to a diffuse map, for example, I’ve made this eye icon - hover it, and you’ll see texture preview.

At this point, everything is working pretty fine, and I don’t want to refactor it, at least for now.

Now I had an idea to show the list of available maps in material (standard material has 12 maps) as a list of rectangle in the very top and draw a number as you did in your script example.

Next I wanted to color a rectangle from the top if its corresponded map has a texture, for example, in green.

As you correctly noticed, I came here for logic because I’m lacking of knowledge for this task. What you’ve created is working damn good, but when I’m trying to merge your code with mine it crashes with errors in mine.

You use:

my_material_ca = attributes my_material_ca attribid:#(122112, 121222)
(
    -- some code
)
ca = createinstance my_material_ca
createdialog ca.RipTools

while I use:
rollout RipTools “Ripping Tools”
(
)
createDialog RipTools

So, here it is.


#9

Do you visually determine which texture is out of place and where it should actually be?


#10

I made a custom attribute example to demonstrate how paramblock can work with this UI. As you can see, all operations in my example are undoable. But… it seems like you don’t need it.
From your explanation, the tool you are working on don’t require a plugin implementation. It’s more like a utility, or more likely a standalone tool.


#11

This situation is rather specific and inherent in small, shall we say, spontaneous projects. In a serious project, a naming convention is used for texture names, so that it is easy to detect a mistake automatically and automatically fix it if necessary.


#12

It also makes your project special…because the standard material maps are kind of an anachronism. Not many users are still using it. Physical based materials (currently in use) have a different list of textures. So it would be right to make the UI design not so tied to a specific list of textures.


#13

Well since the mismatch could be random I visualize only a preview of an image in a map selected from dropdown menus.

it’s a next level for me. I will get there at some point for sure but right now I’m trying to solve problems gradually and don’t create new ones. The same way the MVP method works.

that’s right, I’m doing this tool the way it doesn’t break anything, just a swapper - user can swap maps back with another click.

My tool is standalone, yes.

I’m making this tool for fixing scenes from a friend of mine who is generating these scenes with his tools, so it’s more like a help tool for fixing broken scenes.


#14

So, let’s say we have a momentary and urgent project without the prospect of its further development in order to simplify the work with standard materials and bitmap textures. Should we follow this plan?


#15

What does this mean for us?

  • must be done quickly
  • should be simple to save debugging time
  • solve special cases, not general ones
  • the whole value of the project lies in the practice of writing scripts, training, user interface solutions. All this may be required in future projects.

#16

I think each person is able to evaluate the prospect of their project :slight_smile: The script I have is already working as it meant, but I would like to improve the visual feedback for some features. That’s why I came here.


#17

well… the main thing is that you like it


#18

Can you help me implement the part of your code in my(?):
rollout RipTools “Ripping Tools”
(
– some code
)
createDialog RipTools

I really want it to work now without me learning new things.

p.s.: I learn things anyway. For so many years the maxscript helped me learn c#, python, C++, autoit. That will not be possible without small victories since I’m not a programmer at all but an artist who want to automate things in work.


#19
try(destroydialog _params) catch()
rollout _params "Parameters" width:191
(
	local wb = 12
	local hb = 23
	local _x = 28
	local _y = 8

	local texture_states = #(1,1,1,1,1,1,1,1,1,1,1,1)
	local texture_one = 1
	local texture_two = 2	
	
	local texture_types = #
	(
		"Ambient", 
		"Diffuse", 
		"Specular", 
		"Specular Level", 
		"Glossiness", 
		"Self-Illumination", 
		"Opacity", 
		"Filter", 
		"Bump", 
		"Reflection", 
		"Refraction", 
		"Displacement",
		""
	)
	
	checkbutton info "?" width:wb height:hb pos:[4, _y] tooltip:"Show States" highlightcolor:brown enabled:on

	checkbutton bt01 "" width:wb height:hb pos:[_x + 00*(wb + 1), _y] tooltip:texture_types[1]
	checkbutton bt02 "" width:wb height:hb pos:[_x + 01*(wb + 1), _y] tooltip:texture_types[2]
	checkbutton bt03 "" width:wb height:hb pos:[_x + 02*(wb + 1), _y] tooltip:texture_types[3]
	checkbutton bt04 "" width:wb height:hb pos:[_x + 03*(wb + 1), _y] tooltip:texture_types[4]
	checkbutton bt05 "" width:wb height:hb pos:[_x + 04*(wb + 1), _y] tooltip:texture_types[5]
	checkbutton bt06 "" width:wb height:hb pos:[_x + 05*(wb + 1), _y] tooltip:texture_types[6]
	checkbutton bt07 "" width:wb height:hb pos:[_x + 06*(wb + 1), _y] tooltip:texture_types[7]
	checkbutton bt08 "" width:wb height:hb pos:[_x + 07*(wb + 1), _y] tooltip:texture_types[8]
	checkbutton bt09 "" width:wb height:hb pos:[_x + 08*(wb + 1), _y] tooltip:texture_types[8]
	checkbutton bt10 "" width:wb height:hb pos:[_x + 09*(wb + 1), _y] tooltip:texture_types[10]
	checkbutton bt11 "" width:wb height:hb pos:[_x + 10*(wb + 1), _y] tooltip:texture_types[11]
	checkbutton bt12 "" width:wb height:hb pos:[_x + 11*(wb + 1), _y] tooltip:texture_types[12]
	

	label lb_texture_one "Primary:" align:#right offset:[-30,6] across:2
	dropdownlist ui_texture_one items:texture_types selection:01 width:114 height:14 align:#left offset:[-26,4] 
	label lb_texture_two "Secondary:" align:#right offset:[-30,0] across:2
	dropdownlist ui_texture_two items:texture_types selection:13 width:114 height:14 align:#left offset:[-26,-2] 
	
	local buttons = #(bt01, bt02, bt03, bt04, bt05, bt06, bt07, bt08, bt09, bt10, bt11, bt12)
	
	fn changeTextureState index: state: = 
	(
		if state != unsupplied do
		(
			texture_states[index] = state
		)
		if index != unsupplied and index < 13 do
		(
			state = texture_states[index]

			if state == 1 do 
			(
				ui_texture_one.selection = index
				if ui_texture_two.selection == index do ui_texture_two.selection = 13
			)
			if state == 2 do 
			(
				ui_texture_two.selection = index
				if ui_texture_one.selection == index do ui_texture_one.selection = 13
			)
		)
		for k=1 to buttons.count do
		(
			if info.state then
			(
				buttons[k].text = texture_states[k] as string
			)
			else
			(
				if (k == ui_texture_one.selection) then
				(
					buttons[k].text = if (k == ui_texture_two.selection) then "x" else "1"
				)
				else
				(
					buttons[k].text = if (k == ui_texture_two.selection) then "2" else ""
				)
			)				
			buttons[k].state = (k == ui_texture_one.selection) or (k == ui_texture_two.selection)
		)
	)
	
	on ui_current_alt changed state do 
	(
		if (texture_one == texture_two) do 
		(
			texture_states[texture_one] = state
			changeTextureState index:texture_one
		)
	)

	on info changed state do changeTextureState()
	
	on bt01 changed state do changeTextureState index:1
	on bt02 changed state do changeTextureState index:2
	on bt03 changed state do changeTextureState index:3
	on bt04 changed state do changeTextureState index:4
	on bt05 changed state do changeTextureState index:5
	on bt06 changed state do changeTextureState index:6
	on bt07 changed state do changeTextureState index:7
	on bt08 changed state do changeTextureState index:8
	on bt09 changed state do changeTextureState index:9
	on bt10 changed state do changeTextureState index:10
	on bt11 changed state do changeTextureState index:11
	on bt12 changed state do changeTextureState index:12
		
	fn toggleTextureState index: = 
	(
		if buttons[index].state do
		(			
			texture_states[index] = if texture_states[index] == 1 then 2 else 1
			changeTextureState index:index
		)
	)
	
	on bt01 rightclick do toggleTextureState index:1
	on bt02 rightclick do toggleTextureState index:2
	on bt03 rightclick do toggleTextureState index:3
	on bt04 rightclick do toggleTextureState index:4
	on bt05 rightclick do toggleTextureState index:5
	on bt06 rightclick do toggleTextureState index:6
	on bt07 rightclick do toggleTextureState index:7
	on bt08 rightclick do toggleTextureState index:8
	on bt09 rightclick do toggleTextureState index:9
	on bt10 rightclick do toggleTextureState index:10
	on bt11 rightclick do toggleTextureState index:11
	on bt12 rightclick do toggleTextureState index:12
	
	on ui_texture_one selected index do 
	(
		if index < 13 and index == ui_texture_two.selection do ui_texture_two.selection = 13 
		changeTextureState index:index state:1
	)
	on ui_texture_two selected index do 
	(
		if index < 13 and index == ui_texture_one.selection do ui_texture_one.selection = 13 
		changeTextureState index:index state:2
	)
	
	on _params lbuttondown pos do
	(
		for k=1 to texture_states.count do 
		(
			buttons[k].text = texture_states[k] as string
			buttons[k].state = texture_states[k] != 1
		)
	)
	on _params lbuttonup pos do
	(
		changeTextureState()
		buttons.state = off
	)
	
	on _params open do undo off
	(
		changeTextureState()
	)
)
createdialog _params

some new features added… try to find them :wink: … maybe you will like some of them


#20

Okay, this is what I can understand. Thank you! But in this version for some reason when I chose diffuse in the top and then diffuse in the bottom the top became overwritten and number 1 is no longer visible in the rectangles. The same happens the other way around.