إدارة سلاسل بيانات المخطط في العروض التقديمية باستخدام بايثون
نظرة عامة
يخزن المخطط بياناته المرسومة في دفتر بيانات المخطط. تمثل ChartSeries مجموعة واحدة من القيم المرتبطة، وكل ChartDataPoint في السلسلة يشير إلى خلية أو أكثر في دفتر العمل. توفر كائنات ChartCategory التسميات أو قيم التجميع المشتركة بين السلاسل. وبالتالي فإن اسم السلسلة، الفئات، وقيم النقاط مرتبطة بكائنات ChartDataCell بدلاً من أن تُخزن كنص عرض فقط.
بالنسبة لمخطط فئة نموذجي، يستخدم دفتر العمل الافتراضي الصف 0 لأسماء السلاسل، العمود 0 لأسماء الفئات، وتُستخدم الخلايا المتبقية لقيم السلسلة. الفهارس الخاصة بورقة العمل والصف والعمود التي تُمرَّر إلى ChartDataWorkbook.getCell تبدأ من الصفر. هذا التصميم مفيد عندما تنشئ مخططًا ببيانات افتراضية، ولكن لا تفترض أن كل مخطط موجود يستخدمه. بالنسبة لعرض تقديمي محمَّل، افحص الخلايا التي تشير إليها السلاسل والفئات ونقاط البيانات قبل تعديل قيم دفتر العمل.
إعدادات المخطط لها ثلاث نطاقات مختلفة:
- إعدادات على مستوى السلسلة، مثل ChartSeries.getFormat، توفر الشكل الافتراضي لجميع النقاط في سلسلة واحدة.
- إعدادات على مستوى نقطة البيانات، مثل ChartDataPoint.getFormat، تتجاوز شكل السلسلة لنقطة واحدة.
- إعدادات المجموعة تنطبق على السلاسل المتوافقة التي تنتمي إلى نفس ChartSeriesGroup. يمكنك الوصول إلى المجموعة عبر ChartSeries.getParentSeriesGroup عندما تحتاج إلى ضبط خيارات مثل التداخل أو عرض الفجوة.
عند عدم تحديد تعبئة صريحة للنقطة أو السلسلة، يحدد نمط المخطط والموضع المظهر التلقائي. عندما تكون موجودة كل من تنسيقات السلسلة والنقطة، تتفوق تنسيق النقطة لتلك النقطة.

تعيين تداخل سلسلة المخطط
ChartSeries.getOverlap يُظهر مقدار تداخل الأشرطة أو الأعمدة في مخطط ثنائي الأبعاد، من -100 إلى 100 بالمائة. هو إسقاط للقراءة فقط للإعداد على مجموعة السلسلة الأصلية. استخدم ChartSeriesGroup.setOverlap لتحديث كل السلاسل المتوافقة في تلك المجموعة. هذا الخيار ينطبق على أنواع المخططات التي تعرض أشرطة أو أعمدة مجمعة؛ ولا يؤثر على مجموعات السلاسل غير المرتبطة في مخطط مركب.
المثال التالي يضبط التداخل للمجموعة التي تحتوي على السلسلة الأولى:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, Presentation, SaveFormat
first_slide_index = 0
first_series_index = 0
overlap_percent = 30
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
# المخطط الجديد يحتوي على سلاسل عينات وفئات وقيم.
chart = slide.getShapes().addChart(ChartType.ClusteredColumn, 20, 20, 500, 200)
series = chart.getChartData().getSeries().get_Item(first_series_index)
series.getParentSeriesGroup().setOverlap(overlap_percent)
presentation.save("series_overlap.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
النتيجة:

تغيير لون تعبئة السلسلة
استخدم ChartSeries.getFormat لتعيين التعبئة الافتراضية لسلسلة كاملة. إذا كانت النقطة لديها تعبئة صريحة، فإن إعداد ChartDataPoint.getFormat يتجاوز تعبئة السلسلة لتلك النقطة.
المثال التالي يطبق تعبئة زرقاء صلبة على السلسلة الأولى:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, FillType, Presentation, SaveFormat
Color = jpype.JClass("java.awt.Color")
first_slide_index = 0
first_series_index = 0
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
chart = slide.getShapes().addChart(ChartType.ClusteredColumn, 20, 20, 500, 200)
series = chart.getChartData().getSeries().get_Item(first_series_index)
series.getFormat().getFill().setFillType(FillType.Solid)
series.getFormat().getFill().getSolidFillColor().setColor(Color.BLUE)
presentation.save("series_color.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
النتيجة:

تغيير اسم السلسلة
يُخزن اسم السلسلة في دفتر بيانات المخطط وعادةً ما يُعرض في المفتاح. في دفتر العمل الافتراضي المُنشأ لمخطط عمودي مجمع، الخلية B1 هي الصف 0 العمود 1 وتحتوي على اسم السلسلة الأولى. تجعل المتغيرات المسماة في المثال التالي هذا التركيب واضحًا:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, Presentation, SaveFormat
first_slide_index = 0
worksheet_index = 0
series_name_row_index = 0
first_series_column_index = 1
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
chart = slide.getShapes().addChart(ChartType.ClusteredColumn, 20, 20, 500, 200)
workbook = chart.getChartData().getChartDataWorkbook()
series_name_cell = workbook.getCell(worksheet_index, series_name_row_index, first_series_column_index)
series_name_cell.setValue("Revenue")
presentation.save("series_name.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
يمكنك أيضًا تحديث الخلية التي يُشير إليها ChartSeries.getName. تُجنب هذه المقاربة الافتراض بوجود صف وعمود محددين في مخطط قائم:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, Presentation, SaveFormat
first_slide_index = 0
first_series_index = 0
first_name_cell_index = 0
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
chart = slide.getShapes().addChart(ChartType.ClusteredColumn, 20, 20, 500, 200)
series = chart.getChartData().getSeries().get_Item(first_series_index)
series_name_cell = series.getName().getAsCells().get_Item(first_name_cell_index)
series_name_cell.setValue("Revenue")
presentation.save("series_name.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
النتيجة:

الحصول على لون تعبئة السلسلة التلقائي
ChartSeries.getAutomaticSeriesColor يُعيد اللون المحسوب من فهرس السلسلة ونمط المخطط. هذا هو اللون المستخدم عندما لا تُعرَّف تعبئة السلسلة صراحة. استدعاء الطريقة يقرأ اللون المحسوب؛ لا يُعيّن تعبئة جديدة.
المثال التالي يطبع اللون التلقائي لكل سلسلة افتراضية:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, Presentation
first_slide_index = 0
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
chart = slide.getShapes().addChart(ChartType.ClusteredColumn, 20, 20, 500, 200)
series_count = chart.getChartData().getSeries().size()
for series_index in range(series_count):
series = chart.getChartData().getSeries().get_Item(series_index)
automatic_color = series.getAutomaticSeriesColor()
print(f"Series {series_index}: {automatic_color}")
finally:
presentation.dispose()
مثال الإخراج لنمط المخطط الافتراضي:
Series 0: java.awt.Color[r=79,g=129,b=189]
Series 1: java.awt.Color[r=192,g=80,b=77]
Series 2: java.awt.Color[r=155,g=187,b=89]
الألوان الدقيقة تعتمد على نمط المخطط والموضوع.
تعيين لون تعبئة معكوس لسلسلة المخطط
للشرائح العمودية والعمودية والفقاعية، يمكن لـ ChartSeries.setInvertIfNegative عرض القيم السالبة بتعبئة مختلفة. عيّن تعبئة السلسلة العادية إلى صلبة، فعل الانعكاس، وعيّن لون القيمة السالبة عبر ChartSeries.getInvertedSolidFillColor. الأرقام السالبة تبقى دون تغيير في دفتر العمل؛ يتغير لون العرض فقط.
المثال التالي يستبدل بيانات المخطط الافتراضية بسلسلة واحدة. الصف 0 في ورقة العمل يحتوي على اسم السلسلة، العمود 0 يحتوي على أسماء الفئات، والعمود 1 يحتوي على القيم:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, FillType, Presentation, SaveFormat
Color = jpype.JClass("java.awt.Color")
first_slide_index = 0
worksheet_index = 0
header_row_index = 0
category_column_index = 0
first_series_column_index = 1
first_data_row_index = 1
category_names = ["Category 1", "Category 2", "Category 3"]
series_values = [-20, 50, -30]
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
chart = slide.getShapes().addChart(ChartType.ClusteredColumn, 20, 20, 500, 200)
chart_data = chart.getChartData()
workbook = chart_data.getChartDataWorkbook()
chart_data.getSeries().clear()
chart_data.getCategories().clear()
series_name_cell = workbook.getCell(worksheet_index, header_row_index, first_series_column_index, "Series 1")
chart_type = chart.getType()
series = chart_data.getSeries().add(series_name_cell, chart_type)
for category_index in range(len(category_names)):
data_row_index = first_data_row_index + category_index
category_name = category_names[category_index]
series_value = series_values[category_index]
category_cell = workbook.getCell(worksheet_index, data_row_index, category_column_index, category_name)
chart_data.getCategories().add(category_cell)
value_cell = workbook.getCell(worksheet_index, data_row_index, first_series_column_index, series_value)
series.getDataPoints().addDataPointForBarSeries(value_cell)
automatic_series_color = series.getAutomaticSeriesColor()
series.getFormat().getFill().setFillType(FillType.Solid)
series.getFormat().getFill().getSolidFillColor().setColor(automatic_series_color)
series.setInvertIfNegative(True)
series.getInvertedSolidFillColor().setColor(Color.RED)
presentation.save("inverted_solid_fill_color.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
النتيجة:

يمكنك تفعيل الانعكاس لنقطة واحدة عبر ChartDataPoint.setInvertIfNegative. في المثال التالي يتم تعطيل الانعكاس للسلسلة وتفعيله فقط للنقطة المختارة. تُعطى النقطة أيضًا قيمة سالبة لتظهر التأثير:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, FillType, Presentation, SaveFormat
Color = jpype.JClass("java.awt.Color")
first_slide_index = 0
first_series_index = 0
target_data_point_index = 2
negative_value = -30
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
chart = slide.getShapes().addChart(ChartType.ClusteredColumn, 20, 20, 500, 200)
series = chart.getChartData().getSeries().get_Item(first_series_index)
automatic_series_color = series.getAutomaticSeriesColor()
series.getFormat().getFill().setFillType(FillType.Solid)
series.getFormat().getFill().getSolidFillColor().setColor(automatic_series_color)
series.getInvertedSolidFillColor().setColor(Color.RED)
series.setInvertIfNegative(False)
data_point = series.getDataPoints().get_Item(target_data_point_index)
data_point.getValue().getAsCell().setValue(negative_value)
data_point.setInvertIfNegative(True)
presentation.save("data_point_invert_color_if_negative.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
مسح قيمة نقطة بيانات معينة
لجعل نقطة واحدة فارغة دون إزالة النقاط الأخرى، عيّن خلية دفتر العمل الداعمة لها إلى None. بالنسبة لمخطط عمودي، تكون القيمة المرسومة متاحة عبر ChartDataPoint.getValue. تظل نقطة البيانات في موقع الفئة نفسه، لكن المخطط يتعامل مع قيمتها كفراغ وفقًا لإعدادات القيم الفارغة للمخطط.
المثال التالي يمسح فقط النقطة الثانية في السلسلة الأولى:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, Presentation, SaveFormat
first_slide_index = 0
first_series_index = 0
target_data_point_index = 1
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
chart = slide.getShapes().addChart(ChartType.ClusteredColumn, 20, 20, 500, 200)
series = chart.getChartData().getSeries().get_Item(first_series_index)
data_point = series.getDataPoints().get_Item(target_data_point_index)
data_point.getValue().getAsCell().setValue(None)
presentation.save("clear_data_point_value.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
تستخدم مخططات التبعثر خلايا X وY منفصلة، وتستخدم مخططات الفقاع خلية حجم أيضًا. امسح فقط الخلية التي تمثل القيمة التي تريد إزالتها. لا تستدعِ ChartDataPointCollection.clear عندما تريد الاحتفاظ بالنقاط الأخرى، لأن هذه الطريقة تُزيل كل نقاط البيانات من المجموعة.
التحكم في عرض الخلايا الفارغة
الخلايا المخفية التي تحتوي على قيم هي حالة منفصلة عن الخلايا الفارغة. لتضمين أو استبعاد البيانات من صفوف وأعمدة ورقة العمل المخفية، راجع Include Data from Hidden Rows and Columns.
الخلايا الفارغة في دفتر العمل تمثل بيانات مفقودة؛ الخلية التي تحتوي على 0 تمثل قيمة عددية معروفة. استدعِ ChartDataCell.setValue مع None لجعل الخلية فارغة. الصفر الرقمي يبقى صفرًا بغض النظر عن إعداد الخلايا الفارغة.
استخدم Chart.setDisplayBlanksAs لاختيار كيفية عرض المخطط للخلايا الفارغة. هذا الإعداد يُطبق على المخطط بأكمله. إنه يغيّر طريقة رسم الفراغات دون ملء خلية دفتر العمل الفارغة بالصفر أو بقيمة مُستنتجة.
المثال المتكامل التالي ينشئ مخططًا خطيًا بسلسلة واحدة، يمسح القيمة لليوم 3، ويحفظ المخطط نفسه بكل وضع. لا يلزم ملف إدخال. يستخدم ChartDataWorkbook ورقة العمل 0، العمود 0 لتسميات الفئات، والعمود 1 للقيم؛ الصف 0 يحمل اسم السلسلة. البيانات النهائية هي 10, 20, empty, 30, 40.
import jpime
import asposeslides
if not jpype.isJVMStarted():
jpime.startJVM()
from asposeslides.api import ChartType, DisplayBlanksAsType, Presentation, SaveFormat
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(0)
chart = slide.getShapes().addChart(ChartType.LineWithMarkers, 40, 40, 640, 400)
chart_data = chart.getChartData()
workbook = chart_data.getChartDataWorkbook()
chart_data.getSeries().clear()
chart_data.getCategories().clear()
series_name_cell = workbook.getCell(0, 0, 1, "Measurements")
series = chart_data.getSeries().add(series_name_cell, chart.getType())
values = [10, 20, 25, 30, 40]
for i, value in enumerate(values):
category_cell = workbook.getCell(0, i + 1, 0, f"Day {i + 1}")
chart_data.getCategories().add(category_cell)
value_cell = workbook.getCell(0, i + 1, 1, jpype.JInt(value))
series.getDataPoints().addDataPointForLineSeries(value_cell)
# اترك اليوم 3 فارغًا فعليًا، مع الحفاظ على فئته ونقطة البيانات الخاصة به.
workbook.getCell(0, 3, 1).setValue(None)
modes = [DisplayBlanksAsType.Gap, DisplayBlanksAsType.Zero, DisplayBlanksAsType.Span]
mode_names = ["Gap", "Zero", "Span"]
for mode, mode_name in zip(modes, mode_names):
chart.setDisplayBlanksAs(mode)
presentation.save(f"empty_cells_{mode_name}.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
كل ملف إخراج يُخزّن الوضع المحدد قبل الحفظ: empty_cells_Gap.pptx, empty_cells_Zero.pptx و empty_cells_Span.pptx. لحفظ نسخة واحدة فقط، عيّن الوضع المرغوب واحفظ العرض مرة واحدة بدلاً من التكرار عبر الوضعيات.
المقارنة أدناه تُظهر نفس البيانات في جميع الملفات الثلاثة. اليوم 3 فارغ في دفتر العمل في كل حالة:

التأثير المرئي يعتمد على نوع المخطط. يسهّل مخطط الخط مقارنة الوضعيات الثلاثة. المخططات الشريطية والعمودية لا تملك خطًا لتوصيل الفئات المفقودة، لذا لا يمكن لـ Span إنتاج الجزء المتصل المشار إليه أعلاه؛ قد يبدو العمود المفقود والعمود ذو الارتفاع الصفري متشابهين. بالمثل، مخطط التبعثر مع علامات فقط لا يملك خطًا موصولًا. لا تتوقع ثلاث نتائج متميزة لكل نوع مخطط؛ تحقق من النتيجة للنوع الذي تستخدمه.
تعيين عرض الفجوة بين السلاسل
عرض الفجوة هو المسافة بين مجموعات الأشرطة أو الأعمدة المتجاورة، تُعبّر كنسبة مئوية من عرض العمود أو الشريط. مثل التداخل، ينتمي إلى مجموعة السلسلة الأصلية وليس إلى سلسلة واحدة. استدعِ ChartSeriesGroup.setGapWidth مرة واحدة للمجموعة. القيمة الأكبر تُنشئ مساحة أكبر بين المجموعات؛ القيمة الأصغر تجعلها أكثر تجاورًا.
المثال التالي يغيّر عرض الفجوة ويحفظ العرض التقديمي النهائي فقط:
import jpype
import asposeslides
if not jpype.isJVMStarted():
jpype.startJVM()
from asposeslides.api import ChartType, Presentation, SaveFormat
first_slide_index = 0
first_series_index = 0
gap_width_percent = 30
presentation = Presentation()
try:
slide = presentation.getSlides().get_Item(first_slide_index)
chart = slide.getShapes().addChart(ChartType.StackedColumn, 20, 20, 500, 200)
series = chart.getChartData().getSeries().get_Item(first_series_index)
series.getParentSeriesGroup().setGapWidth(gap_width_percent)
presentation.save("gap_width_30.pptx", SaveFormat.Pptx)
finally:
presentation.dispose()
النتيجة:

الأسئلة المتكررة
ما أنواع المخططات التي تدعم سلاسل البيانات؟
جميع أنواع المخططات الممثلة في تعداد ChartType تستخدم بيانات مخطط، لكن سلاسلها ليست كلها ذات بنية قيم أو إعدادات متشابهة. على سبيل المثال، تستخدم المخططات الفئوية فئات وقيم، وتستخدم مخططات التبعثر قيم X وY، وتضيف مخططات الفقاع أحجام الفقاعات. استخدم طريقة إنشاء نقطة البيانات التي تتطابق مع نوع السلسلة. الخيارات مثل التداخل وعرض الفجوة تنطبق فقط على مجموعات الشريط أو العمود المتوافقة.
ما هي مجموعة سلاسل المخطط؟
ChartSeriesGroup تحتوي على سلاسل متوافقة تشترك في إعدادات الرسم على مستوى المجموعة. يمكن لمخطط مركب أن يحتوي على أكثر من مجموعة، لذا فإن تعديل المجموعة التي تُوصل من خلال سلسلة واحدة لا يُغير بالضرورة كل السلاسل في المخطط.
هل يحتوي المخطط المُنشأ حديثًا على بيانات افتراضية؟
نعم. بشكل افتراضي، تُنشئ ShapeCollection.addChart سلاسل، فئات، وقيم نموذجية. يمكنك تحرير تلك الخلايا أو مسح كل من مجموعات السلاسل والفئات قبل إضافة مجموعة بيانات مخصصة تمامًا. يمكن أيضًا وجود overload يُنشئ مخططًا بدون بيانات افتراضية.
كيف ترتبط كائنات المخطط بخلايا دفتر العمل؟
أسماء السلاسل، تسميات الفئات، وقيم نقاط البيانات تشير إلى خلايا في ChartDataWorkbook. تغيير خلية مُشار إليها يحدث تحديثًا للعنصر المقابل في المخطط. عند بناء بيانات مخصصة، احرص على أن تكون صفوف الفئات وصفوف قيم السلسلة متراصة بحيث تُرسم كل نقطة تحت الفئة المقصودة.
كيف أُمسح نقطة واحدة بدلاً من السلسلة بأكملها؟
عيّن خلية القيمة ذات الصلة إلى None لتبقى نقطة البيانات في موقع الفئة كنقطة فارغة. استخدم ChartDataPointCollection.clear فقط عندما تريد إزالة جميع النقاط من تلك السلسلة. إذا أزلت الفئات أيضًا، حدّث كل السلاسل بحيث تبقى قيمها متراصة مع مجموعة الفئات.
كيف تُعرض النقاط الفارغة؟
النتيجة تعتمد على نوع المخطط والقيمة المُكوَّنة عبر Chart.setDisplayBlanksAs. المخططات المدعومة يمكنها عرض الفارغ كفجوة، كقيمة صفرية، أو بربط النقاط المجاورة. اختر الإعداد الذي يتماشى مع معنى البيانات المفقودة في عرضك. راجع Control the Display of Empty Cells للحصول على مثال كامل ومقارنة بصرية.
كيف تُنسق القيم السالبة؟
للشريط، العمود، ومخططات الفقاعات المدعومة، استدعِ ChartSeries.setInvertIfNegative وضع اللون المرتد عبر ChartSeries.getInvertedSolidFillColor. يمكنك تجاوز السلوك لنقطة فردية باستخدام ChartDataPoint.setInvertIfNegative. هذه الطرق تؤثر على التنسيق فقط، لا على القيم الرقمية المخزنة.
ما هو التنسيق الذي ينتصر عندما يتم تنسيق كل من السلسلة والنقطة؟
تنسيق نقطة البيانات الصريح يتفوق لتلك النقطة. تستمر النقاط الأخرى في استخدام تنسيق السلسلة الصريح أو، إذا لم يُحدد تنسيق السلسلة، النمط والموضوع التلقائي للمخطط. إعدادات المجموعة مثل التداخل وعرض الفجوة تتحكم في التخطيط ولا تُعدّ تجاوزات تنسيق على مستوى النقطة.
هل هناك حد لعدد السلاسل التي يمكن أن يحتويها المخطط؟
Aspose.Slides لا يفرض حدًا ثابتًا لعدد السلاسل. عمليًا، قيود ملف العرض، الذاكرة المتاحة، زمن العرض، وقابلية قراءة المخطط تحدد الحد المفيد.
ماذا يجب أن أعدل عندما تكون الأعمدة قريبة جدًا أو متباعدة جدًا؟
استدعِ ChartSeriesGroup.setGapWidth على مجموعة السلسلة الأصلية المناسبة. زد القيمة لتوسيع المسافة بين المجموعات، أو قللها لتقريب المجموعات من بعضها.