LinuxQuestions.org
Welcome to the most active Linux Forum on the web.
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices


Reply
  Search this Thread
Old 11-26-2022, 10:03 AM   #1
lucmove
Senior Member
 
Registered: Aug 2005
Location: Brazil
Distribution: Debian
Posts: 1,320

Rep: Reputation: 100Reputation: 100
What is the math for proportionally plotting a chart?


Assuming I have a chart and know exactly how many pixels I have on width and height, I know what the highest and lowest plot values are going to be, and I want to display a y axis on the side with some regular interval values. For example:

Code:
y
50  x                                        x  x
40     x     x                 x          x      
30        x     x           x     x    x
20                 x     x           x
10                    x
0
x-> 1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16
I can draw that, but the plot values don't match the y axis indicator.

So my problem is, what are the x/y pixel coordinates for value 25.6, or 34.7 or 44.1?

And what if the y axis changes and goes from 70 to 210? Or from 300 to 1,700?

How do I reliably calculate the x/y pixel chart coordinates across multiple scale scenarios?

TIA
 
Old 11-26-2022, 10:32 AM   #2
pan64
LQ Addict
 
Registered: Mar 2012
Location: Hungary
Distribution: debian/ubuntu/suse ...
Posts: 19,594

Rep: Reputation: 6629Reputation: 6629Reputation: 6629Reputation: 6629Reputation: 6629Reputation: 6629Reputation: 6629Reputation: 6629Reputation: 6629Reputation: 6629Reputation: 6629
what language is it and what kind of display is it (console, graphical whatever or??) What tool is it at all?
 
Old 11-26-2022, 11:42 AM   #3
jailbait
LQ Guru
 
Registered: Feb 2003
Location: Virginia, USA
Distribution: Debian 11
Posts: 8,153

Rep: Reputation: 498Reputation: 498Reputation: 498Reputation: 498Reputation: 498
Quote:
Originally Posted by lucmove View Post
Assuming I have a chart and know exactly how many pixels I have on width and height, I know what the highest and lowest plot values are going to be, and I want to display a y axis on the side with some regular interval values. For example:

Code:
y
50  x                                        x  x
40     x     x                 x          x      
30        x     x           x     x    x
20                 x     x           x
10                    x
0
x-> 1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16
I can draw that, but the plot values don't match the y axis indicator.

So my problem is, what are the x/y pixel coordinates for value 25.6, or 34.7 or 44.1?

And what if the y axis changes and goes from 70 to 210? Or from 300 to 1,700?

How do I reliably calculate the x/y pixel chart coordinates across multiple scale scenarios?

TIA
For the y axis you take the total number of pixels available (say 1800 after you take account of the labels on the x axis) and divide that by the maximum value of the Y axis (say 50 in your example). This gives you the number of pixels per unit on the y axis (1800/50 = 36 pixels per unit).

For the x axis you take the total number of pixels available (say 1100 after you take account of the labels on the y axis) and divide that by the maximum value of the Y axis (say 16 in your example). This gives you the number of pixels per unit on the y axis (1100/16 = 68 pixels per unit).

You can make your graph more readable if you leave a few extra pixels around all four sides to make a clean border.

You can also make a more readable graph if you only include the data range on the y axis. For example if your data was all in the range of 30 to 45 then showing a range of 25 to 50 gives a nicer presentation than a range of 0 through 50. In this case the number of pixels per unit on the y axis would be (1800/25 = 72). The formula for where to place a dot d on the y axis would be ((d-25) * 72).

A similar exercise can be done on the x axis when the label does not start at 0.

Last edited by jailbait; 11-26-2022 at 12:33 PM.
 
1 members found this post helpful.
Old 11-26-2022, 11:57 AM   #4
lucmove
Senior Member
 
Registered: Aug 2005
Location: Brazil
Distribution: Debian
Posts: 1,320

Original Poster
Rep: Reputation: 100Reputation: 100
Quote:
Originally Posted by jailbait View Post
For example if your data was all in the range of 30 to 45 then showing a range of 25 to 50 gives a nicer presentation than a range of 0 through 50. In this case the number of pixels per unit on the y axis would be (1800/25 = 72). The formula for where to place a dot d on the y axis would be ((d-30) * 120).
Excellent answer, thank you. But the part I really needed is still not clear. Why 120? Where did that number come from?
 
Old 11-26-2022, 12:02 PM   #5
jailbait
LQ Guru
 
Registered: Feb 2003
Location: Virginia, USA
Distribution: Debian 11
Posts: 8,153

Rep: Reputation: 498Reputation: 498Reputation: 498Reputation: 498Reputation: 498
Quote:
Originally Posted by lucmove View Post
Excellent answer, thank you. But the part I really needed is still not clear. Why 120? Where did that number come from?
That number should be 72. I'll change it in the original post.
 
1 members found this post helpful.
Old 11-26-2022, 12:04 PM   #6
lucmove
Senior Member
 
Registered: Aug 2005
Location: Brazil
Distribution: Debian
Posts: 1,320

Original Poster
Rep: Reputation: 100Reputation: 100
Quote:
Originally Posted by jailbait View Post
That number should be 72. I'll change it in the original post.
Oh. OK. Thank you again.
 
Old 11-26-2022, 12:12 PM   #7
lucmove
Senior Member
 
Registered: Aug 2005
Location: Brazil
Distribution: Debian
Posts: 1,320

Original Poster
Rep: Reputation: 100Reputation: 100
Quote:
Originally Posted by pan64 View Post
what language is it and what kind of display is it (console, graphical whatever or??) What tool is it at all?
It's perl, but I don't want any code. I want the math. Writing the code is how I have my fun.
Thank you for your attention.
 
Old 11-26-2022, 02:59 PM   #8
dugan
LQ Guru
 
Registered: Nov 2003
Location: Canada
Distribution: distro hopper
Posts: 10,773

Rep: Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097
Wouldn't you just google "curve fitting"?
 
Old 11-26-2022, 03:23 PM   #9
lucmove
Senior Member
 
Registered: Aug 2005
Location: Brazil
Distribution: Debian
Posts: 1,320

Original Poster
Rep: Reputation: 100Reputation: 100
No, that formula is not working. Let's see.

Number of pixels = 1800
range = 25 to 50
1800/25 = 72
dot d = ((d-25) * 72)
Assuming dot d = 10, which is close to the bottom (pixel 0)
dot 10 = ((10-25) * 72)
dot 10 = (-15 * 72)
dot 10 = -1080.0

So dot 10 would be plotted at -1080 in the y axis? That is wrong. It shouldn't be negative.

Let's try another value for dot d.

Number of pixels = 1800
range = 25 to 50
1800/25 = 72
dot d = ((d-25) * 72)
Assuming dot d = 45, which is close to the top (pixel 1800)
dot 45 = ((45-25) * 72)
dot 10 = (20 * 72)
dot 10 = 1440

1440 seems a bit too far from 1800.

Now let's try some different figures and deal with fractions.

Number of pixels = 1800
range = 10400 to 13800
1800/13800 = 0.13043478260869565
dot d = ((d-10400) * 0.13043478260869565)
Assuming dot d = 10500, which is close to the bottom (pixel 0)
dot 10500 = ((10500-10400) * 0.13043478260869565)
dot 10 = (100 * 0.13043478260869565)
dot 10 = 13.043478260869565
OK, looks good.

Number of pixels = 1800
range = 10400 to 13800
1800/13800 = 0.13043478260869565
dot d = ((d-10400) * 0.13043478260869565)
Assuming dot d = 13700, which is close to the top (pixel 1800)
dot 13700 = ((13700-10400) * 0.13043478260869565)
dot 13700 = (3300 * 0.13043478260869565)
dot 13700 = 430.4347826086956
430 is VERY far from 1800!

Back to the drawing board. :-(
 
Old 11-26-2022, 04:44 PM   #10
astrogeek
Moderator
 
Registered: Oct 2008
Distribution: Slackware [64]-X.{0|1|2|37|-current} ::12<=X<=15, FreeBSD_12{.0|.1}
Posts: 6,005
Blog Entries: 23

Rep: Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967
Quote:
Originally Posted by lucmove View Post
No, that formula is not working. Let's see.

Number of pixels = 1800
range = 25 to 50
1800/25 = 72
dot d = ((d-25) * 72)
Assuming dot d = 10, which is close to the bottom (pixel 0)
dot 10 = ((10-25) * 72)
dot 10 = (-15 * 72)
dot 10 = -1080.0

So dot 10 would be plotted at -1080 in the y axis? That is wrong. It shouldn't be negative.
Well, if the range of values, that is the y-axis of your graph is 25 to 50, then by definition you will have no dots with a value of 10 in the graph! The negative value tells you it is out of y-axis range.

If you have a lowest dot with a value of 10 then the lower end of the range must be 10 or less!

Then the formula would be something like this:

Code:
range-min = 10
range-max = 50
pixels = 1800

pixels-per-y-unit = pixels / (range-max - range-min)

dot-y-coordinate = (dot - range-min) * pixels-per-y-unit

dot = 10 : dot-y-coordinate -> 0
dot = 25 : dot-y-coordinate -> 1125
dot = 50 : dot-y-coordinate -> 1800
You must understand the formula to use it correctly.

If the range of actual values were 10 to 50 and you want to leave some pad at top and bottom then set range-min lower than 10 and the range-max greater than 50, 0 to 60 for example:

Code:
range-min = 0
range-max = 60
pixels = 1800
...
dot = 10 : dot-y-coordinate -> 300
dot = 25 : dot-y-coordinate -> 750
dot = 50 : dot-y-coordinate -> 1500

Last edited by astrogeek; 11-26-2022 at 06:12 PM.
 
1 members found this post helpful.
Old 11-26-2022, 06:21 PM   #11
lucmove
Senior Member
 
Registered: Aug 2005
Location: Brazil
Distribution: Debian
Posts: 1,320

Original Poster
Rep: Reputation: 100Reputation: 100
Quote:
Originally Posted by astrogeek View Post
Well, if the range of values, that is the y-axis of your graph is 25 to 50, then by definition you will have no dots with a value of 10 in the graph! The negative value tells you it is out of y-axis range.

If you have a lowest dot with a value of 10 then the lower end of the range must be 10 or less!
Yes, my mistake. I'm sorry. Thank you for pointing that out.

Quote:
Originally Posted by astrogeek View Post
Then the formula would be something like this:

Code:
range-min = 10
range-max = 50
pixels = 1800

pixels-per-y-unit = pixels / (range-max - range-min)
dot-y-coordinate = (dot - range-min) * pixels-per-y-unit

I have tested that formula in multiple scenarios and it seems to work well. Looks like this is solved now.
Thank you very much!
 
Old 12-17-2022, 09:26 PM   #12
rnturn
Senior Member
 
Registered: Jan 2003
Location: Illinois (SW Chicago 'burbs)
Distribution: openSUSE, Raspbian, Slackware. Older: Coherent, MacOS, Red Hat, Big Iron IXs: AIX, Solaris, Tru64
Posts: 2,731

Rep: Reputation: 547Reputation: 547Reputation: 547Reputation: 547Reputation: 547Reputation: 547
Quote:
Originally Posted by lucmove View Post
It's perl, but I don't want any code. I want the math. Writing the code is how I have my fun.
You need to determine the limits in the size plot you wish to create. It seems you already have this. Establish the scaling that needs to done with each data point in both the X and Y directions: Xscale = (Xpxlmax - Xpxlmin) / (Xmax - Xmin). (Same for Y.) Apply the scaling to each point to, basically, turn the data coordinates to coordinates in the "pixel space". If either the X or Y data crosses 0.0, you'll need to apply an offset as well to get the data positioned around the X/Y axes correctly and within you plotting space. Tinkering with a small dataset should make it clear how this works.

I used to do stuff like to to get data plotted on pen plotters; things got hairy when there were multiple/stacked plots. I stopped caring about things like this when tools like Gnuplot did all of it for me. It's interesting to know how the guts of the tool works but if I'm more interested in seeing the plot and I'm no longer banging my head on the table trying to get a homegrown surface plot w/ hidden-line removal code to work, I'm more than happy.

Anyhoo... good luck.
 
1 members found this post helpful.
Old 12-17-2022, 11:22 PM   #13
lucmove
Senior Member
 
Registered: Aug 2005
Location: Brazil
Distribution: Debian
Posts: 1,320

Original Poster
Rep: Reputation: 100Reputation: 100
Quote:
Originally Posted by rnturn View Post
I stopped caring about things like this when tools like Gnuplot did all of it for me. It's interesting to know how the guts of the tool works but if I'm more interested in seeing the plot and I'm no longer banging my head on the table trying to get a homegrown surface plot w/ hidden-line removal code to work, I'm more than happy.
Gnuplot is nightmarishly difficult. Coding my own plotter from scratch is easier.

Not a lot of good plotters for Windows either. Most offerings today are exclusively online.
 
Old 12-18-2022, 12:38 AM   #14
astrogeek
Moderator
 
Registered: Oct 2008
Distribution: Slackware [64]-X.{0|1|2|37|-current} ::12<=X<=15, FreeBSD_12{.0|.1}
Posts: 6,005
Blog Entries: 23

Rep: Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967Reputation: 3967
Quote:
Originally Posted by lucmove View Post
Gnuplot is nightmarishly difficult. Coding my own plotter from scratch is easier.
I thought so too, at one time, but learn it systematically and keep a reference set of your own worked out examples - it will reward you nicely!

Quote:
Originally Posted by lucmove View Post
Not a lot of good plotters for Windows either. Most offerings today are exclusively online.
They know what your data is worth even when you do not... all your data are theirs this way!
 
1 members found this post helpful.
Old 12-18-2022, 02:38 AM   #15
dugan
LQ Guru
 
Registered: Nov 2003
Location: Canada
Distribution: distro hopper
Posts: 10,773

Rep: Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097Reputation: 5097
A lot of people these days use Python, Matplotlib and Jupyter Notebook, all of which are offline. Here are two links:

https://towardsdatascience.com/makin...l-23c8a35c0d5d

https://www.makeuseof.com/draw-graphs-jupyter-notebook/
 
1 members found this post helpful.
  


Reply


Thread Tools Search this Thread
Search this Thread:

Advanced Search

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
Perl Math::Bezier returns Math::Bizarre output captainentropy Programming 3 10-09-2013 10:00 PM
C (math.h)not doing right math? exp() issue. knockout_artist Programming 7 11-25-2011 03:13 PM
[SOLVED] What plotting software should I use for Plotting ASCII data in Ubuntu? msbstar Linux - Newbie 7 04-12-2011 11:30 PM
Running a 2.6.* kernel with math emulation ( Does the math emulation work ?) dar_beh_dar Linux - Kernel 3 05-21-2009 12:43 AM
math program that I can enter math functions ... Four General 5 04-19-2006 09:02 PM

LinuxQuestions.org > Forums > Non-*NIX Forums > Programming

All times are GMT -5. The time now is 11:56 PM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Open Source Consulting | Domain Registration