Вопрос или проблема
Моя диаграмма в Microsoft Forms, использующая Visual Studio, не может показать даты в правильном формате. Когда вы вводите целые числа, всё работает отлично, но числа, отформатированные как даты, не отображаются.
Это моя таблица в SQLite с pd_data в виде целых чисел.
CREATE TABLE producao(
pd_pr_codigo INTEGER,
pd_data INTEGER,
pd_codigo INTEGER,
pd_qtd_produzida REAL,
PRIMARY KEY (pd_pr_codigo, pd_codigo, pd_data)
FOREIGN KEY (pd_pr_codigo) REFERENCES produtos(pr_codigo)
Это мой код:
private void BtProdBlocos_Click(object sender, EventArgs e)
{
try
{
string sql = "SELECT pd_data, pd_qtd_produzida FROM producao";
SqliteParameter[] emptyparameter = new SqliteParameter[]{ };
chart1.DataSource = Funcoes.Cursor(sql, emptyparameter);
chart1.Series["Producao"].XValueMember = "pd_data";
chart1.Series["Producao"].YValueMembers = "pd_qtd_produzida";
chart1.DataBind();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
И вот график, значения по оси X — целые числа, соответствующие датам 2024/10/22 и 2024/10/23.
Теперь, используя pd_data как текст и задавая даты в формате дд/мм/гггг в SQL:
CREATE TABLE producao(
pd_pr_codigo INTEGER,
pd_data TEXT,
pd_codigo INTEGER,
pd_qtd_produzida REAL,
PRIMARY KEY (pd_pr_codigo, pd_codigo, pd_data)
FOREIGN KEY (pd_pr_codigo) REFERENCES produtos(pr_codigo)
Столбцы таблицы, показывающие даты, есть.
Я отладил код и пришел к выводу, что все даты приходят, но по какой-то причине не отображаются правильно на диаграмме. Также Funcoes.cursor — это соединение с базой данных. Я отправляю SQL-запрос через эту функцию, и она возвращает все значения.
ИЗМЕНЕНИЕ: Мне удалось найти решение. Значение X должно быть типа datetime в C#, чтобы оно было верно понято. Поскольку SQLite не имеет родного типа datetime, решением было перенести оба значения в DataTable и внутри него преобразовать значения pd_data и pd_qtd_quantidade в datetime и double соответственно. В коде я также отформатировал ось X, чтобы отображать под углом 45 градусов для лучшей читаемости, и она будет показывать только первые и последние значения в качестве опциональных. Единственное, что я не смог изменить, это то, что если между датами есть разрыв, программа его заполняет (например: с 10/11/2024 по 10/13/2024, диаграмма добавит 10/12/2024 между ними, даже без значения Y), что мне не понравилось, и я хотел бы это изменить, хотя еще не нашел решения. Надеюсь, это поможет и другим!
Вот код:
private void BtProdBlocos_Click(object sender, EventArgs e)
{
string comandosql = "SELECT pd_data, pd_qtd_produzida FROM producao";
SqliteParameter[] parametrovazio = new SqliteParameter[] { };
DataTable dataTable = Funcoes.Cursor(comandosql, parametrovazio);
// Проверяем, имеет ли диаграмма правильные серии
if (chart1.Series.Count == 0)
{
chart1.Series.Add("Producao");
}
// Конфигурируем серию
chart1.Series["Producao"].XValueType = System.Windows.Forms.DataVisualization.Charting.ChartValueType.DateTime;
chart1.Series["Producao"].YValueType = System.Windows.Forms.DataVisualization.Charting.ChartValueType.Double;
// Очищаем предыдущие данные (если есть)
chart1.Series["Producao"].Points.Clear();
// Добавляем точки на диаграмму
foreach (DataRow row in dataTable.Rows)
{
DateTime data = Convert.ToDateTime(row["pd_data"]);
double quantidadeProduzida = Convert.ToDouble(row["pd_qtd_produzida"]);
// Добавляем точку (дата, количество) в серию
chart1.Series["Producao"].Points.AddXY(data, quantidadeProduzida);
}
// Устанавливаем формат меток оси X, чтобы отображались только день и месяц
chart1.ChartAreas[0].AxisX.LabelStyle.Format = "dd/MM/yyyy";
// Устанавливаем угол меток на оси X
chart1.ChartAreas[0].AxisX.LabelStyle.Angle = -45;
// Устанавливаем интервал для меток оси X (в данном случае установлен на 1 день)
chart1.ChartAreas[0].AxisX.Interval = 1;
chart1.ChartAreas[0].AxisX.IntervalType = System.Windows.Forms.DataVisualization.Charting.DateTimeIntervalType.Days;
// Опционально: принудительно устанавливаем границы оси X, чтобы она начиналась и заканчивалась в точных датах
chart1.ChartAreas[0].AxisX.Minimum = chart1.Series["Producao"].Points[0].XValue;
chart1.ChartAreas[0].AxisX.Maximum = chart1.Series["Producao"].Points[chart1.Series["Producao"].Points.Count - 1].XValue;
// Обновляем диаграмму
chart1.Invalidate();
}
Ответ или решение
Конечно! Вот полный ответ на ваш вопрос о работе с датами в диаграмме C# в Visual Studio и решения проблемы отображения дат корректно.
Проблема
Ваша диаграмма, используемая в приложении Windows Forms, не может обрабатывать даты, когда они представлены в виде целых чисел или строк. Вместо этого вы наблюдаете только частичное отображение данных или неправильную интерпретацию оси X.
Решение
Для правильной обработки дат в диаграмме вам необходимо убедиться в следующих вещах:
-
Тип даты в C#: Так как SQLite не имеет родного типа данных для даты, вы можете преобразовать ваши даты, сохраненные как текст (например, в формате "dd/MM/yyyy"), в объект
DateTime
в C#. -
Настройка оси X: Установите
XValueType
для серии диаграммы вChartValueType.DateTime
, чтобы диаграмма понимала, что по оси X у вас даты. -
Очистка точек графика: Перед добавлением новых точек в серию диаграммы обязательно очистите предыдущие данные.
-
Форматирование оси X: Убедитесь, что у вас правильно установлен формат даты для меток оси X, и установите угол наклона меток для улучшения читаемости.
-
Обработка пробелов в датах: Чтобы избежать автоматического заполнения промежутков дат, вы можете использовать дополнительные проверки перед добавлением точек в серию диаграммы.
Полный пример кода
Вот полный код, который вы можете использовать для решения вашей проблемы:
private void BtProdBlocos_Click(object sender, EventArgs e)
{
try
{
string sql = "SELECT pd_data, pd_qtd_produzida FROM producao";
SqliteParameter[] emptyparameter = new SqliteParameter[] { };
DataTable dataTable = Funcoes.Cursor(sql, emptyparameter);
// Проверка наличия серий в графике
if (chart1.Series.Count == 0)
{
chart1.Series.Add("Producao");
}
// Настройка серии
chart1.Series["Producao"].XValueType = System.Windows.Forms.DataVisualization.Charting.ChartValueType.DateTime;
chart1.Series["Producao"].YValueType = System.Windows.Forms.DataVisualization.Charting.ChartValueType.Double;
// Очистка предыдущих данных
chart1.Series["Producao"].Points.Clear();
// Добавление точек в график
foreach (DataRow row in dataTable.Rows)
{
DateTime data = Convert.ToDateTime(row["pd_data"]);
double quantidadeProduzida = Convert.ToDouble(row["pd_qtd_produzida"]);
// Добавить точку (дата, количество) в серию
chart1.Series["Producao"].Points.AddXY(data, quantidadeProduzida);
}
// Настройка формата меток оси X
chart1.ChartAreas[0].AxisX.LabelStyle.Format = "dd/MM/yyyy";
chart1.ChartAreas[0].AxisX.LabelStyle.Angle = -45;
// Установка интервала меток по оси X
chart1.ChartAreas[0].AxisX.Interval = 1;
chart1.ChartAreas[0].AxisX.IntervalType = System.Windows.Forms.DataVisualization.Charting.DateTimeIntervalType.Days;
// Настройка границ оси X
if (chart1.Series["Producao"].Points.Count > 0)
{
chart1.ChartAreas[0].AxisX.Minimum = chart1.Series["Producao"].Points[0].XValue;
chart1.ChartAreas[0].AxisX.Maximum = chart1.Series["Producao"].Points[chart1.Series["Producao"].Points.Count - 1].XValue;
}
// Обновление графика
chart1.Invalidate();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
}
Заключение
После внесения перечисленных изменений ваше приложение должно правильно обрабатывать даты на диаграмме, позволяет отображать информацию в нужном формате и избегать автоматической подстановки промежуточных дат. Если у вас есть дополнительные вопросы или необходима помощь с конкретной частью кода, не стесняйтесь обращаться за помощью!