Author Topic: How to coloring particles by its properties  (Read 2477 times)

eason1021

  • Newbie
  • *
  • Posts: 21
How to coloring particles by its properties
« on: July 27, 2018, 02:57:42 PM »
Hello everyone.
I use the python script to define the particle's new properties.
Now I want to coloring the atom with its properties.
For example:atom 1 is type A,then coloring the blue,atom 2 is type B,then coloring the orange...and I can choose the color by myself.
Has any modifiers can do this function? I read the vis modifiers,but I don't see the similar function to coloring by atom.

Constanze Kalcher

  • Administrator
  • Full Member
  • *****
  • Posts: 121
Re: How to coloring particles by its properties
« Reply #1 on: July 27, 2018, 03:29:33 PM »
Hi,
if you want to color atoms according to a certain atomic property the Color Coding modifier is what you're looking for.
~Constanze

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #2 on: July 29, 2018, 08:00:16 AM »
Thanks your reply.
But I want to do is like CNA modifier , if central atom is FCC coloring green.....
now I has been decide each atom's type and color.
But I still don't know how to visualize it.
I see the color coding modifier.But it seem not  to do this?

« Last Edit: July 29, 2018, 09:43:41 AM by eason1021 »

Constanze Kalcher

  • Administrator
  • Full Member
  • *****
  • Posts: 121
Re: How to coloring particles by its properties
« Reply #3 on: July 29, 2018, 12:05:06 PM »
Have a look at this topic, where I explained how to use your own color map in the Color Coding modifier. This gives you more control over the color coding.
In the python scripting interface you can import an image file of your own custom color gradient like this:

Code: [Select]
pipeline.modifiers.append(ColorCodingModifier(
    property = ... ',
    gradient = ColorCodingModifier.Custom("<image file>")
))

Let me know if that works for you.
-Constanze

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #4 on: July 29, 2018, 01:50:47 PM »
Color coding modifier need to input property.
My property is calculating by my method,I seem to use ParticleProperty.Type.User   
But I don't put my method into property function.
Should I need to transform my method to property form?
If I need ,how should I do this?

Constanze Kalcher

  • Administrator
  • Full Member
  • *****
  • Posts: 121
Re: How to coloring particles by its properties
« Reply #5 on: July 30, 2018, 09:51:16 AM »
Yes, it needs to be a particle property.
Let's say the output of your method is called "results" and you want to store these values in a new particle property "myproperty".
This is how you can do this:

Code: [Select]
data.particles.create_property('myproperty', data=results)

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #6 on: July 31, 2018, 11:49:50 AM »
Thanks for your reply!!!
I have a idea now

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #7 on: August 02, 2018, 08:12:36 AM »
Ask a question.After coding a Color coding Modifier.
It can visualization directly?Or I need to add any visualization code?
Because I use a color coding modifier and run success(no error message)
But it is nothing happen,I can't see my color coding result.
How should I do to see my color coding visualization?

Constanze Kalcher

  • Administrator
  • Full Member
  • *****
  • Posts: 121
Re: How to coloring particles by its properties
« Reply #8 on: August 03, 2018, 10:51:12 AM »
Hi eason1021,

it would be a lot easier to help you if you uploaded your code here. Then I can understand what you're trying to do.

-Constanze

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #9 on: August 03, 2018, 02:32:30 PM »
Ok,that's my code now:
if I coding:
Code: [Select]
#create a list to store all particle's result
    result_list = []

#calculate every particle's result and add it to a list
    for k in range(data.particles.count):
        property_list.append(result)

#create a particles property by result
    data.particles.create_property('myproperty', data=result_list)
    node.modifiers.append(ColorCodingModifier(property = 'myproperty',gradient = ColorCodingModifier.Rainbow(),start_value = 0,end_value= 19))

    node.add_to_scene()
    vis = node.get_vis(ParticlesVis)
It will happen
RuntimeError: Data pipeline evaluation failed: Modifier 'Color coding' reported: The property with the name 'myproperty' does not exist.

if I coding:
Code: [Select]
#create a list to store all particle's result
    property_list = []

#calculate every particle's result and add it to a list
    for k in range(data.particles.count):
        property_list.append(locals()["variant_color%s"%k])

#create a particles property by result
    data.particles.create_property('myproperty', data=property_list)
    node.modifiers.append(ColorCodingModifier(property = 'myproperty',gradient = ColorCodingModifier.Rainbow(),start_value = 0,end_value= 19))
It doesn't have any error message but there is nothing happen

Alexander Stukowski

  • Administrator
  • Hero Member
  • *****
  • Posts: 516
Re: How to coloring particles by its properties
« Reply #10 on: August 06, 2018, 11:58:36 AM »
Dear eason1021,

The code snippet that you posted doesn't seem to be complete. It would be helpful if you could show us the entire source code of your script, otherwise it is difficult to tell what is happening exactly.

But the RuntimeError produced by the first code version is likely due to the following sequence:
Code: [Select]
    data.particles.create_property('myproperty', data=result_list)
    node.modifiers.append(ColorCodingModifier(property = 'myproperty',gradient = ColorCodingModifier.Rainbow(),start_value = 0,end_value= 19))

The variable 'data' points to a DataCollection object, which represents the computation output of a data pipeline, which has been obtained earlier through a call to the pipeline's compute() method. A DataCollection is always a static snapshot of the data that left the pipeline. You can manipulate it as you like after the fact, for example add a new particle property using a call to create_property(). However, no such changes will affect the pipeline that originally produced the DataCollection. In particular, if you add a new ColorCodingModifier to that pipeline using node.modifiers.append(), that modifier will still see the original data flowing through the pipeline, not the data copy that you manipulated separately outside of the pipeline. That's why the ColorCodingModifier complains that it cannot see the 'myproperty' particle property.

To avoid this error, the addition of the new property to the DataCollection must happen as part of the pipeline. Then subsequent modifiers will see the extended dataset and can work with the new property. One way to accomplish this is by writing a user-defined modifier function adding the new property to the DataCollection as it flows through the pipeline, and insert that function into the pipeline as a PythonScriptModifier. Here is a sketch of that solution:

Code: [Select]
# Initial data import and creation of the pipeline:
node = import_file(...)

# Append any modifiers here to the pipeline which compute information that you will need as input for 'myproperty'...
node.modifiers.append(...)

# User-defined modifier function which computes and adds the 'myproperty' particle property:
def compute_myproperty(frame, input, output):
    mydata = ...  # Compute the property values...
    output.particles.create_property('myproperty', data=mydata)

# Insert the user-defined modifier function into the pipeline.
# The system will call compute_myproperty() automatically later as soon as the pipeline is evaluated.
node.modifiers.append(PythonScriptModifier(function = compute_myproperty))

# Finally, append a coloring modifier to the pipeline which uses 'myproperty' as input, e.g.
node.modifiers.append(ColorCodingModifier(property = 'myproperty',gradient = ColorCodingModifier.Rainbow(),start_value = 0,end_value= 19))

# Optional: Evaluate the full pipeline to get the colored particles.
data = node.compute()

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #11 on: August 06, 2018, 04:26:49 PM »
Thanks your reply Mr.Alexander.
Due to my code is very long,if I post here,the readability will be poor.
Has any way to send my script for you?

Alexander Stukowski

  • Administrator
  • Hero Member
  • *****
  • Posts: 516
Re: How to coloring particles by its properties
« Reply #12 on: August 06, 2018, 04:29:27 PM »
When you post a message on this forum, you have the option to attach entire files to your message (similar to attachments in emails). Other forum users like me can then download the attached file and open it in a text editor, for example.

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #13 on: August 06, 2018, 04:40:55 PM »
I run this version's code.
It run successful but nothing happen

Alexander Stukowski

  • Administrator
  • Hero Member
  • *****
  • Posts: 516
Re: How to coloring particles by its properties
« Reply #14 on: August 06, 2018, 04:54:25 PM »
Thanks. I got your code and I am still trying to understand what you are doing and what your goal is.

You wrote that nothing happens when you run this script. What do you expect it to do? Do you want to produce an image or a movie? Or would you like to see the computation results in the viewports of OVITO? Or do you want to produce a series of data output files?

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #15 on: August 06, 2018, 05:20:56 PM »
I want to produce an image or see the computation results in the viewports.

Alexander Stukowski

  • Administrator
  • Hero Member
  • *****
  • Posts: 516
Re: How to coloring particles by its properties
« Reply #16 on: August 06, 2018, 05:27:13 PM »
If you intend to produce a visual output, it's important that you add the pipeline (or rather its output) to the scene. This doesn't happen automatically for datasets imported via the import_file() function. See the first note on this page in the green box:

http://ovito.org/manual_testing/python/introduction/file_io.html

To add the pipeline's output to the scene and make it visible in the viewports of OVITO and in rendered images, add a call to the add_to_scene() method to your script:

Code: [Select]
node.add_to_scene()

Alexander Stukowski

  • Administrator
  • Hero Member
  • *****
  • Posts: 516
Re: How to coloring particles by its properties
« Reply #17 on: August 06, 2018, 05:39:52 PM »
Typically, you would insert this statement right after the line that creates the pipeline, i.e. right after the call to import_file().

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #18 on: August 06, 2018, 08:55:10 PM »
I am running successful!
Thank you very much,Mr.Alexander!

Alexander Stukowski

  • Administrator
  • Hero Member
  • *****
  • Posts: 516
Re: How to coloring particles by its properties
« Reply #19 on: August 08, 2018, 01:26:58 PM »
Your script still didn't do the right thing. I see that you have written a for-loop over all input simulation frames. Within that loop, you do the following:

  • request the output of the data pipeline
  • perform some calculation on that output data
  • define a modifier function, which takes that computed data array to create a particle property from it, and append the function to the data pipeline
  • append a Color Coding modifier to the pipeline

Note that steps 3 and 4 will have no effect during the first loop iteration, because the pipeline was already evaluated in step 1, without the two modifiers being inserted into the pipeline yet. Thus, the user-defined modifier function is never called by the pipeline system. Furthermore, in consecutive loop iterations, the pipeline will get longer and longer, because you insert the user-defined modifier function and the Color Coding modifier multiple times.

The correct approach should look as follows (I have rearranged your script accordingly, see the attached file):

  • define a custom modifier function that takes whatever input data is provided by the pipeline system and performs some calculation on it; append that modifier function to the pipeline
  • append a Color Coding modifier to the pipeline
  • loop over the simulation frames and evaluate the pipeline at each timestep

Note that in this approach, the pipeline is first set up completely. Once all modifiers have been inserted into the pipeline, the static pipeline can be evaluated multiple times, once for each frame. The pipeline system will repeatedly call the user-defined function with the correct input data.
« Last Edit: August 09, 2018, 02:29:22 PM by Constanze Kalcher »

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #20 on: August 08, 2018, 02:23:16 PM »
Thanks your reply.
So I need to create a modifier function at first and then loop over the frames.
I know where I am wrong now.
Thanks you again,Mr.Alexander.

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #21 on: August 08, 2018, 03:12:16 PM »
After execute the modified version, the old problem still happen.
RuntimeError: Data pipeline evaluation failed: Modifier 'Color coding' reported: The property with the name 'myproperty' does not exist.
This error happen at final line:
Code: [Select]
data = node.compute(frame_index)

Alexander Stukowski

  • Administrator
  • Hero Member
  • *****
  • Posts: 516
Re: How to coloring particles by its properties
« Reply #22 on: August 08, 2018, 04:18:20 PM »
I don't have an explanation for this at the moment. I took the script, removed most of the calculation code and tested it with one of my data files. I didn't see any errors in this case.

Maybe the problem only occurs with your input files, or originates from the actual calculation code which I had to remove for testing. Could you please post your input data files, at least some of them? Then I can test the script with the original input data and investigate why it stops. Please let me also know which exact version of OVITO you are using. Thanks.

Alexander Stukowski

  • Administrator
  • Hero Member
  • *****
  • Posts: 516
Re: How to coloring particles by its properties
« Reply #23 on: August 09, 2018, 09:49:36 AM »
Thanks for uploading the data files. I ran the script on these files and got the following error message:

Code: [Select]
moglios:eason1021 stuko$ ~/prj/ovito/build/debug/Ovito.app/Contents/MacOS/ovitos.exe test88_modified_orig.py
Traceback (most recent call last):
  File "test88_modified_orig.py", line 349, in compute_myproperty
    locals()["px_f_%s"%k] = np.dot(locals()["px_matrix_%s"%k],locals()["px_matrix_inv_ref%s"%k])
KeyError: 'px_matrix_inv_ref0'
Traceback (most recent call last):
  File "test88_modified_orig.py", line 812, in <module>
    data = node.compute(frame_index)
  File "/Users/stuko/prj/ovito/build/debug/Ovito.app/Contents/MacOS/../Resources/python/ovito/pipeline/pipeline_class.py", line 178, in _Pipeline_compute
    raise RuntimeError("Data pipeline evaluation failed: %s" % state.status.text)
RuntimeError: Data pipeline evaluation failed: Modifier 'Color coding' reported: The property with the name 'myproperty' does not exist.
ERROR: The Python script 'test88_modified_orig.py' has exited with an error.

Note that these are actually two errors. The first one occurs in line 349 of the script file ("KeyError: 'px_matrix_inv_ref0'"). The second one, in line 812, is only a subsequent error. Because the user-defined modifier function raises an error, the new particle property is never created and that's why the Color Coding modifier complains about the missing property.

The problem in your script seems to be the usage of the locals() function in various places. Note that it may return a different dictionary depending on the context from where you call it. Inside the user-defined modifier function you have a different set of locals than in the main body of the program where you process the reference structure. Furthermore, modifying the locals() dictionary is generally discouraged any, see the official Python docs: https://docs.python.org/3/library/functions.html#locals

I suggest you replace it with a simple dictionary that you create at the beginning of your program:

Code: [Select]
myvars = {}

Then replace all occurrences of "locals()" in your code with "myvars".

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #24 on: August 09, 2018, 02:26:05 PM »
Thank you,Mr.Alexander.
You really help me a lot!
I will try to fix my error.And use this modifier to compare my old result.
Thank you again.

Another thing,can I please you remove the test88modified temporarily?
Because the calculation method has not been validated,and I want to keep the process secret.
After verification its accuracy,I will post it again in the net.
Thanks.

Constanze Kalcher

  • Administrator
  • Full Member
  • *****
  • Posts: 121
Re: How to coloring particles by its properties
« Reply #25 on: August 09, 2018, 02:30:36 PM »
Hi,
I removed the attached file in Alexander's post.
Best,
Constanze

eason1021

  • Newbie
  • *
  • Posts: 21
Re: How to coloring particles by its properties
« Reply #26 on: August 10, 2018, 08:34:59 AM »
Thanks your help.
Sincere thanks to you.