Тема: Побудова графіка з використанням DataGrigView та Chart
Всім привіт!
Потрібна ваша допомога, щоб коректно побудувати за допомогою Chart та DataGridView графік такої функції:
(Exp(1 / (1 - x^2))) / (1 + x^2)
Як бачите в точках х=+-1 будуть асимптоти.
Але в мене виходить не зовсім те, що має бути (дивіться нижче в коментарях на очікуваний результат і мій наявний)
Ось мій код
namespace WindowsFormsApp_lab3
{
public partial class Form1 : Form
{
bool pointFocusEnabled = false;
private double startX, endX, maxY, minY, step, startY, endY;
private int tabulateDotsQuantity;
public Form1()
{
InitializeComponent();
buttonChartConstruction.Enabled = false;
}
private double f(double x)
{
return ((Math.Exp(1 / (1 - Math.Pow(x, 2)))) / (1 + Math.Pow(x, 2)));
}
private bool parseData()
{
//check input data
if (textBoxX1.Text == "" ||
textBoxX2.Text == "" ||
textBoxNumbOfPoint.Text == "")
{
MessageBox.Show("Enter all data!",
"Critical Warning",
MessageBoxButtons.OK,
MessageBoxIcon.Warning);
return false;
}
//get data from textBoxes
startX = Double.Parse(textBoxX1.Text.Replace(".", ","));
endX = Double.Parse(textBoxX2.Text.Replace(".", ","));
tabulateDotsQuantity = Int32.Parse(textBoxNumbOfPoint.Text);
step = (endX - startX) / tabulateDotsQuantity;
return true;
}
private void setChart()
{
chart.ChartAreas.Clear();
chart.Series.Clear();
chart.Legends.Clear();
chart.Titles.Clear();
chart.Series.Add("Main");//set series to visualize graphic line
chart.Series["Main"].Color = Color.Blue;
chart.Series.Add("Points");//set series to visualize selected points
chart.Series["Points"].Color = Color.Red;
chart.Series["Main"].ChartType = System.Windows.Forms.DataVisualization.Charting.SeriesChartType.Line;
chart.Series["Main"].XValueType = System.Windows.Forms.DataVisualization.Charting.ChartValueType.Double;
chart.Series["Main"].YValueType = System.Windows.Forms.DataVisualization.Charting.ChartValueType.Double;
chart.Series["Points"].ChartType = System.Windows.Forms.DataVisualization.Charting.SeriesChartType.Point;
chart.Series["Points"].XValueType = System.Windows.Forms.DataVisualization.Charting.ChartValueType.Double;
chart.Series["Points"].YValueType = System.Windows.Forms.DataVisualization.Charting.ChartValueType.Double;
chart.ChartAreas.Add("Main");
//set title
chart.Titles.Add("MainTitle");
chart.Titles[0].Text = "y = (Math.Exp(1 / (1 - Math.Pow(x, 2)))) / (1 + Math.Pow(x, 2))";
chart.Titles[0].Alignment = ContentAlignment.TopLeft;
chart.Titles[0].Visible = false;
//set up chart area
chart.ChartAreas["Main"].AxisX.Minimum = startX;
chart.ChartAreas["Main"].AxisX.Interval = 1;
chart.ChartAreas["Main"].AxisX.Maximum = endX;
chart.ChartAreas["Main"].AxisX.ArrowStyle = System.Windows.Forms.DataVisualization.Charting.AxisArrowStyle.SharpTriangle;
chart.ChartAreas["Main"].AxisX.Name = "X";
chart.ChartAreas["Main"].AxisX.Title = "X";
chart.ChartAreas["Main"].AxisY.ArrowStyle = System.Windows.Forms.DataVisualization.Charting.AxisArrowStyle.SharpTriangle;
chart.ChartAreas["Main"].AxisY.Name = "Y";
chart.ChartAreas["Main"].AxisY.Title = "Y";
if (textBoxY1.Text == "" && !(textBoxY2.Text == "")) //для масштабирования относительно y
{
endY = Double.Parse(textBoxY2.Text.Replace(".", ","));
chart.ChartAreas["Main"].AxisY.Minimum = minY;
chart.ChartAreas["Main"].AxisY.Maximum = endY;
}
else if (!(textBoxY1.Text == "") && (textBoxY2.Text == ""))
{
startY = Double.Parse(textBoxY1.Text.Replace(".", ","));
chart.ChartAreas["Main"].AxisY.Minimum = startY;
chart.ChartAreas["Main"].AxisY.Maximum = maxY;
}
else if (!(textBoxY1.Text == "") && !(textBoxY2.Text == ""))
{
startY = Double.Parse(textBoxY1.Text.Replace(".", ","));
endY = Double.Parse(textBoxY2.Text.Replace(".", ","));
chart.ChartAreas["Main"].AxisY.Minimum = startY;
chart.ChartAreas["Main"].AxisY.Maximum = endY;
}
else if ((textBoxY1.Text == "") && (textBoxY2.Text == ""))
{
chart.ChartAreas["Main"].AxisY.Minimum = minY;
chart.ChartAreas["Main"].AxisY.Maximum = maxY;
}
//set the position of axes
chart.ChartAreas["Main"].AxisX.Crossing = 0;
chart.ChartAreas["Main"].AxisY.Crossing = 0;
}
private void dataGridView_ColumnHeaderMouseClick(object sender, DataGridViewCellMouseEventArgs e)
{
//update row indexes after sorting
foreach (DataGridViewRow row in dataGridView.Rows)
{
row.Cells["Number"].Value = row.Index;
}
}
private void textBoxes_KeyPress(object sender, KeyPressEventArgs e)
{
if (e.KeyChar == ',')
{
e.KeyChar = '.';
}
if ((sender as TextBox) == textBoxNumbOfPoint)
{
//verify that input text is only numeric and positive integer and not show other
if (!char.IsControl(e.KeyChar) && !char.IsDigit(e.KeyChar))
{
e.Handled = true;
}
}
else
//Verify that the pressed key is Ctrl or digits or dot or minus and not show others
if (!char.IsControl(e.KeyChar) && !char.IsDigit(e.KeyChar) && (e.KeyChar != '.') && (e.KeyChar != '-'))
{
e.Handled = true;
}
}
private void buttonSubmit_Click(object sender, EventArgs e) //табулирования финкции
{
if (!parseData())
return;
if(!ambit_checkX())
{
MessageBox.Show("Error! Enter correct data for X!",
"Critical Warning",
MessageBoxButtons.OK,
MessageBoxIcon.Warning);
textBoxX2.Text = "";
textBoxX1.Text = "";
textBoxX1.Focus();
return;
}
dataGridView.Rows.Clear();
double x, y;
for (int i = 0; i <= tabulateDotsQuantity; i++)
{
x = Math.Round(startX + step * i, 4);
y = Math.Round(f(startX + step * i), 4);
if (y > maxY)
maxY = y;
else if (y < minY)
minY = y;
dataGridView.Rows.Add(i, x, y);//add row with tabulated values in dataGridView table
}
//set values in min-max textBoxes
textBoxFmax.Text = maxY.ToString();
textBoxFmin.Text = minY.ToString();
setChart();
//enable appropriate buttons
buttonChartConstruction.Enabled = true;
}
private bool ambit_checkX() //check x1 <= x2
{
if (Double.TryParse(textBoxX1.Text, out startX) && Double.TryParse(textBoxX2.Text, out endX))
{
double x1, x2;
x1 = double.Parse(textBoxX1.Text);
x2 = double.Parse(textBoxX2.Text);
if (x1 >= x2)
{ return false; }
}
return true;
}
private void buttonLoadChart_Click(object sender, EventArgs e)
{
if (dataGridView.Rows.Count == 1)
{
MessageBox.Show("Please, enter data!",
"Critical Warning",
MessageBoxButtons.OK,
MessageBoxIcon.Warning);
return;
}
chart.Series["Main"].Points.Clear();
chart.Titles[0].Visible = true;
if (dataGridView.SelectedRows.Count == 0)
{
//visualize all data rows
for (int i = 0; i < dataGridView.RowCount - 1; i++)
{
chart.Series["Main"].Points.AddXY(dataGridView[1, i].Value, dataGridView[2, i].Value);
}
}
else
{
//visualize only selected data rows
int i;
for (int j = 0; j < dataGridView.SelectedRows.Count; j++)
{
i = dataGridView.Rows.IndexOf(dataGridView.SelectedRows[j]);
chart.Series["Main"].Points.AddXY(dataGridView[1, i].Value, dataGridView[2, i].Value);
}
}
pointFocusEnabled = true;
}
private void textBoxDotsQuantity_Leave(object sender, EventArgs e)
{
//check quantity of dots to tabulate
if (textBoxNumbOfPoint.Text == "")
return;
int dots = Int32.Parse(textBoxNumbOfPoint.Text);
if (dots <= 1)
{
MessageBox.Show("Enter more than 2 point for the tab!",
"Critical Warning",
MessageBoxButtons.OK,
MessageBoxIcon.Warning);
textBoxNumbOfPoint.Text = "";
textBoxNumbOfPoint.Focus();
}
}
private void dataGridView_RowHeaderMouseClick(object sender, DataGridViewCellMouseEventArgs e)
{
if (pointFocusEnabled == false)
return;
chart.Series["Points"].Points.Clear();
//add selected dots from selected rows to visualize on chart
int i;
for (int j = 0; j < dataGridView.SelectedRows.Count; j++)
{
i = dataGridView.Rows.IndexOf(dataGridView.SelectedRows[j]);
chart.Series["Points"].Points.AddXY(dataGridView[1, i].Value, dataGridView[2, i].Value);
}
chart.Update();
}
private void dataGridView_CellClick(object sender, DataGridViewCellEventArgs e)
{
chart.Series["Points"].Points.Clear();
chart.Update();
}
private void textBoxStartY_Leave(object sender, EventArgs e)
{
if (textBoxX1.Text == "" || textBoxX2.Text == "")
return;
//check ranges of interval
double startY, endY;
startY = Double.Parse(textBoxY1.Text);
endY = Double.Parse(textBoxY2.Text);
if (startY >= endY)
{
MessageBox.Show("Error! Enter correct data for Y",
"Critical Warning",
MessageBoxButtons.OK,
MessageBoxIcon.Warning);
textBoxY1.Text = "";
textBoxY2.Text = "";
textBoxY1.Focus();
}
}
}
}
Я пробувала будувати три різних графіки на інтервалах (-infinity; -1), (-1; 1), (1; infinity), але всеодно не виходило коректно реалізувати завдання.
Допоможіть, будь ласка, вирішити дану проблему)