Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature/tree map vis #66

Merged
merged 13 commits into from
May 8, 2018
Merged

Feature/tree map vis #66

merged 13 commits into from
May 8, 2018

Conversation

NicoKNL
Copy link
Collaborator

@NicoKNL NicoKNL commented May 5, 2018

Overview

fixes #55
fixes #48

OpenGL demo visualization

To provide a visual demo of the openGL methods and a visual guide (the red centered-cross) indicating how our axis are aligned. The cross has a domain and range of [-200, 200] with ticks every 10 units. The addition of this visualization can prove a decent starting point for those who want to get started with creating their own visualization. In the future this visualization can be modified to suit our needs better as more features are added to the tool in general. (i.e. we could also -soon- showcase basic usage of parameters in this visualization as well when #59 is merged)

Additionally I made the demo visualization the first visualization to be loaded, as that seems like a reasonable thing to do at this stage.

The demo visualization

image

Treemap implementation

I had to do research on the tree-map, and whilst there are many variations, I opted to start with the most straight-forward implementation. I know the task originally only said to research, but determining the algorithm for the tree-map is something I found easier to do whilst implementing it immediately. Hence we now have an extra visualization implemented in a basic form.

As a minor feature there is also a 2-color gradient implemented, but that works better when the offset is also implemented later on. This is because a non-nested treemap visualizes the leaves, which have colorA in a colorA -> colorB gradient. A common use-case for color in a treemap which could perhaps be better, is to do it based on some property of the node, e.g. file-extension in a filesystem.

the treemap visualization

image

Problems / issues

The treemap visually works better if there is both an outline ánd a fill. This however means that on a hierarchy of 300.000 items, there are 600.000 calls to draw a rectangle on screen.

Hence large-hierarchies on a laptop system are not yet supported, and untested on a better system.

What also popped up is that by default my laptop would render using the internal IntelHD graphics chip, this caused performance to be bad, even when only drawing the filled quads. (Hence having only 300.000 elements, not 600.000). Forcing my laptop to use the gtx1050m it has gave rise to major improvements in terms of speed. However, my system has 16GB of memory, and it can't manage drawing the 600.000 elements with either GPU without causing the openGL context to be lost.

Perhaps something to discuss in a different issue/topic/thread.

Future todo

As visualizations are very stand-alone, I would propose to merge this as is right now. However, the treemap visualization aspect of this PR is still open to some improvements which, due to the modular nature of visualizations, I would opt to push forward a bit in a future issue/PR.

The following items I would like to improve upon in the future / separate issues:

  1. Offset implementation to create a 'nested' tree-map
  2. Colour parameters
  3. Offset parameter
  4. Intitial base-width/height based on canvas size
  5. Better color usage
  6. Optimazation

@RoanH RoanH self-requested a review May 5, 2018 20:00
@RoanH RoanH added this to review in SPRINT 02 May 5, 2018
Copy link
Collaborator

@RoanH RoanH left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The output looks really nice, well done ^^

As a general remark. There are still a lot of commented lines of code and console.log statements present in the tree map code. I believe that some code cleanup is in order.

It's a pity though that ellipses came too late for the demo ;-;

let width = Math.abs(bounds.right - bounds.left);
let height = Math.abs(bounds.top - bounds.bottom);

// TODO: fix performance issues related to drawing BOTH a fill ánd outline
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Performance should be fine for this, however memory I estimate to reach about 10GB with the current OpenGL implementation. I plan to take care of that in #64.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't really see how to get around doing a Math.abs() if I need to get a width/height from 2 points which could both be negative. Is Math.abs relatively heavy then?

The only alternative I see is to start working with if/else statements, but that sounds to me as re-implementing Math.abs().

If you have a suggestion I'd love to hear it.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Math.abs is about as cheap as a math function can be. My comment was added to line 45.


var childOrientation = '';
// console.log(orientation, (orientation==='HORIZONTAL'));
if (orientation === 'HORIZONTAL') {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why use expensive strings for this? I'm not sure if enums exist in Typescript, but I would use that if they exist. Or at the very least make these class level readonly constants so that new strings don't get created all the time.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because I'm lazy and wanted to do something enum-like, but couldn't be arsed to look up how to do this in practice. I'll try and revise later this weekend.

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Enums do exist, you can check my PR for forms

top = parentBounds.top - parentHeight * doneSize / parentSize;
}

const newBounds = {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You should be able to return this immediately without first storing it in a local variable. Not that big of an issue though.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point, will update. It's not often that I had to think about performance in the past.

this.colorB[3] - this.colorA[3]
];
this.totalNodes = tree.subTreeSize;
this.offset = 2; // TODO: implement as parameter
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Might want to make an issue for this. Similar to how enhancements for the Pythagoras tree were handled.

Copy link
Collaborator Author

@NicoKNL NicoKNL May 5, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

With regards to the color, yes I think so as well. The offset is tree-map specific, though I don't think you're referring to line 34 with your comment.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was referring to line 34 since I thought that it was a visualization setting :P

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

#71 is now a thing.

gl.fillAAQuad(100, 100, 100, 100, [0, 1, 0, 1]);
gl.drawAAQuad(100, -200, 100, 100, [0, 1, 0, 1]);
gl.fillLinedAAQuad(-200, -200, 100, 100, [0, 1, 0, 1], [0, 0, 0, 1]);
gl.drawRotatedQuad(-200, 100, 100, 100, 45, [0, 1, 0, 1]);
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know this is intended behavior, but it's seriously bugging me out that it isn't aligned with the other quads 😅

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🤷‍♂️

@RoanH
Copy link
Collaborator

RoanH commented May 5, 2018

I should probably also add that I actually managed to render the entire NCBI dataset on my TU/e laptop. But performance wasn't acceptable and Firefox kept asking me to kill a tab that was using a lot of resources.

@NicoKNL
Copy link
Collaborator Author

NicoKNL commented May 5, 2018

Thank you for the feedback @RoanH . I thought I'd do the cleanup at a later stage as there are quite some changes coming up to this in the future I believe. Though I understand the wish to keep the codebase clean.

I'll revise and update with a new commit somewhere later this sunday.

When I'm at it, I'll also add in circles to the demo visualization.

bartwesselink
bartwesselink previously approved these changes May 6, 2018
Copy link
Owner

@bartwesselink bartwesselink left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks very nice! Well done. My only remark is that you remove the console.log calls, but as @RoanH already mentioned this, I approve 👍

@NicoKNL
Copy link
Collaborator Author

NicoKNL commented May 6, 2018

Update

Demo visualization

As can also be seen in #55 there is now an update to the openGL demo visualization which includes the addition of circles and ellipses to that visualization.

image

Tree-Map

The following changes were made:

  • Code cleanup
  • Added comments
  • Implemented an interface for the Bounds to support more complete ducktyping in this module/file
  • Implemented an enum for the Orientation to deal more efficiently and consistently with specifying the orientation of nodes.

@RoanH RoanH self-requested a review May 6, 2018 14:14
@NicoKNL NicoKNL closed this May 7, 2018
@RoanH RoanH moved this from review to in progress in SPRINT 02 May 7, 2018
@NicoKNL
Copy link
Collaborator Author

NicoKNL commented May 8, 2018

Update OpenGL demo visualization

The demo visualization now supports a few settings to play around with! Set the color on a 0 to 255 scale per channel, and toggle the sine waves on or off!

image

image

Update treemap visualization

The treemap visualization now support a first user-setting as well! Namely, offset. This creates the effect of nested treemaps.

image

image

@NicoKNL NicoKNL reopened this May 8, 2018
@NicoKNL
Copy link
Collaborator Author

NicoKNL commented May 8, 2018

@bartwesselink I think the CI thingy doesn't like the properties missing which I posted about on the telegram group. Unfortunately I can't see the details of the check.

@RoanH RoanH moved this from in progress to review in SPRINT 02 May 8, 2018
Copy link
Collaborator

@RoanH RoanH left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks awesome!

Small remarks:

  • You might want to put a cap on your offset, since otherwise stuff starts looking a bit weird.
    afbeelding
    Or perhaps this is intended behavior?

]
this.sinewaves = settings.sinewaves; // update whether we should draw the sine waves

this.gl.releaseBuffers(); // remove old data from buffers
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This looks like something a lower level component should probably handle, the visualisation framework for example. There are also better ways to update the OpenGL state without clearing all the buffers, but those would have to be implemented first so for now this is indeed the only way.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would imagine a partial buffer update then?

But this seemed like a straightforward approach which just worked.
We can come back to this later then, I'll post an issue, if there isn't one already.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, we'll also have to see to what extent an implementation for partial updates would be desired (since it would also add some overhead). For example the tree map vis wouldn't really benefit from it as changing the offset invalidates just about all the coordinates.

@NicoKNL
Copy link
Collaborator Author

NicoKNL commented May 8, 2018

I'm aware of the offset thing. It flips the quads as lowerbound-edges become upperbound-edges and visa versa. However, as I'm already way past executing the research tree-map task, there are some future changes that probably should be made, aaand the basic visualization is already functional... I would prefer to update this behaviour later on.

Thanks for the input though!

@bartwesselink Thanks for implementing and changing it to a slider, and fixing the errors!

@NicoKNL NicoKNL merged commit 4465737 into develop May 8, 2018
SPRINT 02 automation moved this from review to done May 8, 2018
@bartwesselink bartwesselink deleted the feature/tree-map-vis branch May 10, 2018 09:58
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
No open projects
SPRINT 02
  
done
Development

Successfully merging this pull request may close these issues.

opengl demo visualization Research Spatial Tree map
3 participants