Avoid collision of nodes while representing Binary Tree in SFML

Hello, following is the code of the prgoram I have created in SFML (Please note, this is a Binary SEARCH Tree and also that I have only given the codes of Display and Insertion as others aren't required, so that to keep the code's length as small as possible. Moreover, the nodes won't show the values as I haven't done that yet. This is really a very basic code but does explain the problem)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
 
#include <SFML/Graphics.hpp>
#include <queue>
#include <iostream>
using namespace std;
sf::RenderWindow window(sf::VideoMode(1070, 920), "SFML works!");
struct node
{
	int data;
	node *left, *right, *parent; 
	sf::CircleShape shape; 
	sf::RectangleShape leftone;
	sf::RectangleShape rightone; 
}*root;
class Tree
{
public:
	Tree();
	void insert(int, node*, int, int, int, int);
	void Display(node*); 
	void inOrder(node*); 
	void PostOrder(node*); 
	void PreOrder(node*); 
	bool isEmpty(); 
	void Deletion(int); 
	node* SearchNode(int, node*); 
};
bool Tree::isEmpty()
{
	if (!root)
		return true;
	return false; 
}
Tree::Tree() { root = NULL; }
void Tree::insert(int data, node* Node = root, int x = 250, int y = 50, int a = 260, int b = 85)
{
	node* new_node = new node; 
	new_node->shape.setRadius(20);
	new_node->shape.setFillColor(sf::Color::Green);
	new_node->left = new_node->right = new_node->parent = NULL; 
	new_node->data = data; 
	new_node->shape.setPosition(sf::Vector2f(x, y));
	if (!root)
	{
		root = new_node;
		return; 
	}
	if (data >= Node->data)
	{
		if (Node->right)
			insert(data, Node->right, x + 50, y + 50, a + 50, b + 50); 
		else
		{
			Node->right = new_node;
			new_node->parent = Node; 
			new_node->shape.setPosition(sf::Vector2f((x + 50), (y + 50))); 
			new_node->parent->rightone.setSize(sf::Vector2f(50, 5)); 
			new_node->parent->rightone.setFillColor(sf::Color::Red);
			new_node->parent->rightone.setRotation(230);
			new_node->parent->rightone.setPosition(sf::Vector2f(a+50, b+40));
		}
	}
	else if (data < Node->data)
	{
		if (Node->left)
			insert(data, Node->left, x - 50, y + 50, a - 50, b + 50);
		else
		{
			Node->left = new_node; 
			new_node->parent = Node; 
			new_node->shape.setPosition(sf::Vector2f((x - 50), (y + 50)));
			new_node->parent->leftone.setSize(sf::Vector2f(50, 5));
			new_node->parent->leftone.setFillColor(sf::Color::Red);
			new_node->parent->leftone.setRotation(130);
			new_node->parent->leftone.setPosition(sf::Vector2f(a, b));
		}
	}
}
void Tree::Display(node* Root = root)
{
	if (!root)
	{
		cout << "Nothing to Display";
		return;
	}
	queue<node*> obj;
	obj.push(Root);
	while (!obj.empty())
	{
		node* temp = obj.front();
		window.draw(temp->shape);
		if (temp->left)
			window.draw(temp->leftone);
		if (temp->right)
			window.draw(temp->rightone); 
		//cout << temp->data << " ";
		obj.pop();
		if (temp->left)
			obj.push(temp->left);
		if (temp->right)
			obj.push(temp->right);
	}
	window.display();
}

int main()
{
	sf::CircleShape shape(100.f);
	shape.setFillColor(sf::Color::Green);
	int n; 
	Tree obj;
	while (window.isOpen())
	{
		cout << "Enter Number to Insert: "; 
		cin >> n;
		obj.insert(n); 
		sf::Event event;
		obj.Display(); 
		while (window.pollEvent(event))
		{
			if (event.type == sf::Event::Closed)
				window.close();
		}

		window.clear();
	}

	return 0;
}


So, basically, I am taking an input on Console (I still can't figure out how to take integer input on SFML Window.. I am pretty new to SFML) and then creating a tree and using BFS method (Queue) to display the nodes of trees...
As you would be able to see (if you run the code), the nodes are being created successfully and their connections as well.
However, there is one big issue that I am facing.

Suppose these values are added to the tree,
1
2
3
4
5
 50 -> Added as Root Node
75 -> Added to the right of Root Node
25 -> Added to the left of Root Node
37 -> Added to the right of 25
67 -> Added to the left of 75

So, it works well until addition of 37 (that also prints out exactly below the root node, though which is wrong) however, as soon as I enter the node 67, it gets added to the same position as 37 and hence, only one of them shows on window.
Now, I can alter their coordinates and expand them a bit but eventually, I will end up facing the same issue after addition of few more values.
How can I avoid it? Could you help please?

There's a BST Visualizer available online which provides a pretty good solution. (Please refer here if you want to: https://www.cs.usfca.edu/~galles/visualization/BST.html )
It decreases/increases the x coordinate of the left/right child of root whenever it detects this pattern of addition (Root->Left->Right... or Root->Right->Left) but I am failing to make a proper logic to implement this idea. Can you help in this regard, please? Or provide a different solution? Thank you!
Last edited on
First let's talk about some basic stuff.

Root is a global, so:
1
2
3
Tree t1;
// do stuff with t1
Tree t2  // Oops, I just set root to null,  

Root should be a a member of Tree. Then the methods should be:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
public:
	void Display() { Display(root);  }
	void inOrder() {inOrder(root);  }
	void PostOrder() {postOrder(root);  }
	void PreOrder(); { PreOrder(root); }
	bool isEmpty(); 
	void Deletion(int); 
	node* SearchNode(int); { return SearchNode(root); }
private:
	void Display(node*); 
	void inOrder(node*); 
	void PostOrder(node*); 
	void PreOrder(node*); 
	node* SearchNode(int, node*); 

Insert() should not take a ton of parameters that go into the node. It should just take a node:
1
2
public: void Insert(node* data) {Insert(data, root); }
private: void Insert(node *data, node *top);


Why oh WHY does a node store information about its left and right children (leftone and rightone)?? It should be something like:
1
2
3
4
5
6
7
struct node
{
	int data;
	node *left, *right, *parent; 
	sf::CircleShape shape; 
	sf::RectangleShape rshape;   // shape of THIS node, not a child
}


As for the placement. The basic problem is that you don't know where to draw the nodes until you have the entire tree constructed. Then you can recursively determine the dimensions of each subtree.
Topic archived. No new replies allowed.