ข้ามไปเนื้อหา

มอดูล:Sports series

จากวิกิพีเดีย สารานุกรมเสรี
Documentation icon คู่มือการใช้งานมอดูล[ดู] [แก้] [ประวัติ] [ล้างแคช]

This is a module for generating match results for a sports series, such as a two-legged tie. However, the module can support single-leg ties up to an unlimited number of legs. The template supports domestic and international football matches. While designed for association football, it can be used for any sport that features a series between teams.

Usage

[แก้]

In its simplest form, only a few parameters are needed to build a table.

International club football

[แก้]

For two-legged ties in international club football, seven parameters are expected to be passed for each row. This includes each club's name and national association country name/code, the aggregate score and the score of both legs.

{{#invoke:Sports series|main
|first_team|first_association|aggregate|second_team|second_association|first_leg|second_leg
}}

National team or domestic club football

[แก้]

For two-legged ties in national team or domestic club football, five parameters are expected to be passed for each row. This includes each club's name, the aggregate score and the score of both legs. The parameter |flag=n must be passed to disable the country flag parameter.

{{#invoke:Sports series|main|flag=n
|first_team|aggregate|second_team|first_leg|second_leg
}}

Examples

[แก้]

International club football

[แก้]
Usage
{{#invoke:Sports series|main
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
|[[Real Madrid CF|Real Madrid]]|ESP|4–4 (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG|3–3|1–1 (aet)
|[[Paris Saint-Germain FC|Paris Saint-Germain]]|FRA|6–4|[[FC Barcelona|Barcelona]]|ESP|2–3|4–1
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4
Real Madrid สเปน4–4 (4–3 p)อังกฤษ Manchester City3–31–1 (a.e.t.)
Paris Saint-Germain ฝรั่งเศส6–4สเปน Barcelona2–34–1

Domestic club football

[แก้]
Usage
{{#invoke:Sports series|main|flag=n
|[[Valencia CF|Valencia]]|3–3 (3–2 p)|[[Deportivo Alavés|Alavés]]|2–1|1–2 (aet)
|[[Atlético Madrid]]|2–5|[[Sevilla FC|Sevilla]]|1–2|1–3
|[[RCD Espanyol|Espanyol]]|1–2|[[FC Barcelona|Barcelona]]|1–0|0–2
|[[CD Leganés|Leganés]]|2–2 ([[Away goals rule|a]])|[[Real Madrid CF|Real Madrid]]|0–1|2–1
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Valencia3–3 (3–2 p)Alavés2–11–2 (a.e.t.)
Atlético Madrid2–5Sevilla1–21–3
Espanyol1–2Barcelona1–00–2
Leganés2–2 (a)Real Madrid0–12–1

National team football

[แก้]
Usage
{{#invoke:Sports series|main|flag=n
|{{fb-rt|UKR}}|3–1|{{fb|SVN}}|2–0|1–1
|{{fb-rt|SWE}}|4–3|{{fb|DEN}}|2–1|2–2
|{{fb-rt|BIH}}|1–3|{{fb|IRL}}|1–1|0–2
|{{fb-rt|NOR}}|1–3|{{fb|HUN}}|0–1|1–2
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
ยูเครน ธงชาติยูเครน3–1ธงชาติสโลวีเนีย สโลวีเนีย2–01–1
สวีเดน ธงชาติสวีเดน4–3ธงชาติเดนมาร์ก เดนมาร์ก2–12–2
บอสเนียและเฮอร์เซโกวีนา ธงชาติบอสเนียและเฮอร์เซโกวีนา1–3ธงชาติสาธารณรัฐไอร์แลนด์ สาธารณรัฐไอร์แลนด์1–10–2
นอร์เวย์ ธงชาตินอร์เวย์1–3ธงชาติฮังการี ฮังการี0–11–2

Parameter list

[แก้]

Below is a full list of the named parameters for this module. Additionally, the unnamed parameters are used to pass the teams and scores of each of the ties (as shown above). All parameters are optional.

Parameter name Description Type

flag

flag
Determines the flag icon template which will be used in the table. The default is {{fbaicon}}. If set to a negative value (e.g. n, no, 0), no flags will be displayed. If the flag template passed through the parameter does not exist, the module will default to {{flagicon}}. String

legs

legs
Determines the number of legs that will be displayed in the table, and how many scores are expected to be passed to each row. The default is 2. If set to a negative value (e.g. n, no, 0), the table will display no legs and will be formatted to display the results of single-leg ties (the aggregate column header will then be changed to "Score").

Example 1

[แก้]
Usage
{{#invoke:Sports series|main|legs=5
|[[Arsenal F.C.|Arsenal]]|ENG|6–8|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1|2–2|0–1|2–2
|[[Atlético Madrid]]|ESP|10–11|[[Borussia Dortmund]]|GER|2–1|2–4|2–1|2–4|2–1
|[[Real Madrid CF|Real Madrid]]|ESP|11–11 (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG|3–3|1–1|3–3|1–1|3–3 (aet)
|[[Paris Saint-Germain FC|Paris Saint-Germain]]|FRA|14–11|[[FC Barcelona|Barcelona]]|ESP|2–3|4–1|2–3|4–1|2–3
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg3rd leg4th leg5th leg
Arsenal อังกฤษ6–8เยอรมนี Bayern Munich2–20–12–20–12–2
Atlético Madrid สเปน10–11เยอรมนี Borussia Dortmund2–12–42–12–42–1
Real Madrid สเปน11–11 (4–3 p)อังกฤษ Manchester City3–31–13–31–13–3 (a.e.t.)
Paris Saint-Germain ฝรั่งเศส14–11สเปน Barcelona2–34–12–34–12–3

Example 2

[แก้]
Usage
{{#invoke:Sports series|main|legs=n
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER
|[[Real Madrid CF|Real Madrid]]|ESP|4–4 (aet) (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG
|[[Paris Saint-Germain FC|Paris Saint-Germain]]|FRA|6–4|[[FC Barcelona|Barcelona]]|ESP
}}
Output
ทีมหนึ่งผลทีมสอง
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund
Real Madrid สเปน4–4 (a.e.t.) (4–3 p)อังกฤษ Manchester City
Paris Saint-Germain ฝรั่งเศส6–4สเปน Barcelona
Number

bold_winner

bold_winner
Automatically enabled by default. To disable, set to a negative value (e.g. n, no, 0). The module automatically bolds the winning team of the tie. First priority is given to the winning team of scores listed inside brackets (which is commonly used to denote the results of a penalty shoot-out). Otherwise, the regular score will be used. If the aggregate scores are level for two-legged ties and no results of penalty shoot-outs are given, the away goals rule will be applied to determine the winning team (unless |away_goals= is used to turn off this feature). In all other cases, if no winner can be determined based on the input, neither team in a given tie will be bolded. String

color_winner

color_winner
To enable, set to a positive value (e.g. y, yes, 1). Automatically gives the winning team of the tie with a background color of green (#CCFFCC). First priority is given to the winning team of scores listed inside brackets (which is commonly used to denote the results of a penalty shoot-out). Otherwise, the regular score will be used. If the aggregate scores are level for two-legged ties and no results of penalty shoot-outs are given, the away goals rule will be applied to determine the winning team (unless |away_goals= is used to turn off this feature). In all other cases, if no winner can be determined based on the input, neither team in a given tie will be colored.

When this parameter is enabled for single-leg ties, the score cell of any draws will be automatically given a background color of yellow (#FFFFBB).

String
generate_links
To enable, set to a positive value (e.g. y, yes, 1). Automatically generates wikilinks around match scores, linking to anchors in the format of "[Team 1] v [Team 2]" for the first leg and single-leg ties, and "[Team 2] v [Team 1]" for the second leg. If the first and/or second team from a tie is missing, the text within the anchor will default to "Team 1" and/or "Team 2", respectively. A link will be placed around the match score (or match date for future fixtures), excluding any text in parentheses, unless a link is already present around the score, in which case no change will be made.

This feature is intended to complement the automatic anchor generation feature of {{Football box}}. On that template, anchors are automatically generated for articles with "group" or "knockout" in the title, as well as templates using the parameter |id=auto.

Example 3

[แก้]
Usage
{{#invoke:Sports series|main|generate_links=y
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
|[[Real Madrid CF|Real Madrid]]|ESP|4–4 (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG|3–3|1–1 (aet)
|[[Paris Saint-Germain FC|Paris Saint-Germain]]|FRA|6–4|[[FC Barcelona|Barcelona]]|ESP|2–3|4–1
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4
Real Madrid สเปน4–4 (4–3 p)อังกฤษ Manchester City3–31–1 (a.e.t.)
Paris Saint-Germain ฝรั่งเศส6–4สเปน Barcelona2–34–1
String

matches_style

matches_style
When set to FBR for single-leg ties, it automatically changes the background color of the score cells based on the result of the match. Home wins are shown in blue (#BBF3FF), draws in yellow (#FFFFBB) and away wins in red (#FFBBBB). A legend for the colors will also be added below the table, and the team column headers will be changed to "Home team" and "Away team" (as done with |h_a=, making that parameter redundant when FBR is enabled). This functions similar to Module:Sports results. String

solid_cell

solid_cell
When set to a positive value (e.g. y, yes, 1), any leg cells with a value of null will be given a background color of grey (#BBBBBB). String

small_text

small_text
Automatically enabled by default. To disable, set to a negative value (e.g. n, no, 0). The module automatically generates small text (85% font size) for legs (or the score column for single-leg ties) when no match score is present, and no small text exists in the cell already. This is to allow for the proper formatting of future matches, which typically lists the date of the fixture in a reduced font size. Small text is not applied to any references, notes or superscripts present. String

collapsed

collapsed
To enable, set to a positive value (e.g. y, yes, 1). If set, it collapses the table using mw-collapsed. This results in the table being spread across the entire width of the page.

Example 4

[แก้]
Usage
{{#invoke:Sports series|main|collapsed=y
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4
String

center_table

center_table
To enable, set to a positive value (e.g. y, yes, 1). If set, it centers the wikitable horizontally across the page. Does not work if |collapsed= is set. String

caption

caption
Adds a caption to the table.

Example 5

[แก้]
Usage
{{#invoke:Sports series|main|caption=This is a caption
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
}}
Output
This is a caption
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4
String

title

title
Adds a title to the table in the form of a table header spanning all columns, placed above the standard column headings.

Example 6

[แก้]
Usage
{{#invoke:Sports series|main|title=This is a title
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
}}
Output
This is a title
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4
String

id

id
Adds an anchor to the top of the table which allows direct linking to the table. String

section

section
Allows for a custom name to be given to the table for the purposes of transclusion. This is useful when there are multiple instances of this module (or also Module:Sports table) on the same page within transclusion tags, allowing for selective calling of specific tables on another page. When the parameter is set and the module code is placed in between <onlyinclude>...</onlyinclude> tags, other pages transcluding the table and using |transcludesection= will only show tables with a matching |section= and not all tables.

For example, if the article "Example" has this module placed in between <onlyinclude>...</onlyinclude> tags with |section=First round, then the table can be transcluded to other articles using {{:Example|transcludesection=First round}}.

String

nowrap

nowrap
By default, only the aggregate/leg scores and column headers will have a nowrap value applied to the cell style.

To enable nowrap for the entire table, set to a positive value (e.g. y, yes, 1).

To disable nowrap for the cells that it is included for by default, set to a negative value (e.g. n, no, 0).

String

font_size

font_size
Modifies the font size of the table to a given percentage. The percentage sign is optional. Default is 100. Due to MOS:SMALLTEXT, values lower than 85% will be converted to 85%. Number

flag_size

flag_size
Modifies the size of the flags to a specific pixel count. The size is specified in pixels: Width px or x Height px or Width x Height px. This scales the image to be no greater than the given width or height, keeping its aspect ratio. For more information, see Wikipedia:Extended image syntax. The trailing "px" text is optional. By default, the size is controlled by the flag icon or country data templates, but is usually 23x15px. Number

show_country

show_country
When set to a specific country name or code, only rows containing a team with that accompanying country name/code will be displayed in the final output. For example, if |show_country=GER, rows only containing teams with the accompanying country code of "GER" (for Germany) will be displayed. Nothing will occur if |flag=n is also set. Any custom headings within the table (set via |headingN=) will be suppressed when |show_country= is used.

This feature is useful when transcluding content to country-related articles, for example 2024–25 in German football. However, note that if the module is being transcluded via labeled section transclusion, template parameters cannot be passed, and therefore this parameter would not work.

Example 7

[แก้]
Usage
{{#invoke:Sports series|main|show_country=ENG
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
|[[Real Madrid CF|Real Madrid]]|ESP|4–4 (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG|3–3|1–1 (aet)
|[[Paris Saint-Germain FC|Paris Saint-Germain]]|FRA|6–4|[[FC Barcelona|Barcelona]]|ESP|2–3|4–1
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Real Madrid สเปน4–4 (4–3 p)อังกฤษ Manchester City3–31–1 (a.e.t.)
String

fill_blanks

fill_blanks
To enable, set to a positive value (e.g. y, yes, 1). Adds a placeholder flag icon to the space next to a team's name when flag parameters are present in the table, but the parameter for a given team is left blank. This will have no impact if |flag=n. String

team_width

team_width
Set to an integer value for the width of the two team columns, in pixels. Default is 250. Number

score_width

score_width
Set to an integer value for the width of the aggregate score column and each leg score column, in pixels. Default is 80. Number

away_goals

away_goals
If set to a negative value (e.g. n, no, 0), the module will not apply the away goals rule for two-legged ties in which the aggregate score is level. Otherwise, by default the module will use the away goals rule to determine the winner. String

team1

team1
Adds a custom heading for the first team column. Default is Team 1. String

team2

team2
Adds a custom heading for the second team column. Default is Team 2. String

h_a

h_a
To enable, set to a positive value (e.g. y, yes, 1). Changes the default column headers for the teams to "Home team" and "Away team". If |team1= and/or |team2= is set, those respective parameter(s) will override headers set by |h_a=. String

aggregate

aggregate
Adds a custom heading for the aggregate score column. Default is {{Abbrlink|Agg.|Aggregate score}}, unless |legs= is set to a negative value (e.g. n, no, 0), for which the default will be Score. String

legN

legN
Adds a custom heading for the Nth leg column (e.g. |leg1= for the first leg column, |leg3= for the third leg column, etc.). Default is <ordinal> leg (e.g. 1st leg for the first leg column, 3rd leg for the third leg column, etc.).

Example 8

[แก้]
Usage
{{#invoke:Sports series|main|leg1=Game 1|leg2=Second Leg
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
|[[Real Madrid CF|Real Madrid]]|ESP|4–4 (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG|3–3|1–1 (aet)
|[[Paris Saint-Germain FC|Paris Saint-Germain]]|FRA|6–4|[[FC Barcelona|Barcelona]]|ESP|2–3|4–1
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4
Real Madrid สเปน4–4 (4–3 p)อังกฤษ Manchester City3–31–1 (a.e.t.)
Paris Saint-Germain ฝรั่งเศส6–4สเปน Barcelona2–34–1
String

leg_prefix

leg_prefix
Changes the format of the leg score column headings. Instead of using "<ordinal> leg", now the format will be "<leg_prefix> N". Any string can be specified through the parameter to add as a custom prefix. However, when set only to a positive value (e.g. y, yes, 1), the output will default to Leg N. (Note that negative values cannot be used, as they will be treated literally for the prefix text.) If |legN= is set, this will replace the Nth leg score column heading, overriding the custom prefix.

Example 9

[แก้]
Usage
{{#invoke:Sports series|main|flag=n|legs=7|leg_prefix=Game|aggregate=Series
|[[Golden State Warriors]]|3–4|[[Cleveland Cavaliers]]|104–89|110–77|90–120|108–97|97–112|101–115|89–93
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสองGame 1Game 2Game 3Game 4Game 5Game 6Game 7
Golden State Warriors3–4Cleveland Cavaliers104–89110–7790–120108–9797–112101–11589–93

Example 10

[แก้]
Usage
{{#invoke:Sports series|main|leg_prefix=y
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
|[[Real Madrid CF|Real Madrid]]|ESP|4–4 (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG|3–3|1–1 (aet)
|[[Paris Saint-Germain FC|Paris Saint-Germain]]|FRA|6–4|[[FC Barcelona|Barcelona]]|ESP|2–3|4–1
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสองนัดที่ 1นัดที่ 2
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4
Real Madrid สเปน4–4 (4–3 p)อังกฤษ Manchester City3–31–1 (a.e.t.)
Paris Saint-Germain ฝรั่งเศส6–4สเปน Barcelona2–34–1
String

leg_suffix

leg_suffix
Adds a custom suffix after the ordinal for the leg score column headings. Default is leg. If |legN= is set, this will replace the Nth leg score column heading, overriding the custom suffix. In addition, |leg_prefix= takes precedence over |leg_suffix=.

Example 11

[แก้]
Usage
{{#invoke:Sports series|main|leg_suffix=match
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
|[[Real Madrid CF|Real Madrid]]|ESP|4–4 (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG|3–3|1–1 (aet)
|[[Paris Saint-Germain FC|Paris Saint-Germain]]|FRA|6–4|[[FC Barcelona|Barcelona]]|ESP|2–3|4–1
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st match2nd match
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4
Real Madrid สเปน4–4 (4–3 p)อังกฤษ Manchester City3–31–1 (a.e.t.)
Paris Saint-Germain ฝรั่งเศส6–4สเปน Barcelona2–34–1
String

headingN

headingN
Adds a custom heading spanning all columns above the Nth row of the table (e.g. |heading1= for above the first row, |heading20= for above the twentieth row, etc.).

Example 12

[แก้]
Usage
{{#invoke:Sports series|main|flag=n|legs=n|h_a=y|heading1=Semi-finals|heading3=Final
|{{fb-rt|POL}}|5–1|{{fb|EST}}
|{{fb-rt|WAL}}|4–1|{{fb|FIN}}
|{{fb-rt|WAL}}|0–0 (aet) (4–5 p)|{{fb|POL}}
}}
Output
ทีมเหย้าผลทีมเยือน
Semi-finals
โปแลนด์ ธงชาติโปแลนด์5–1ธงชาติเอสโตเนีย เอสโตเนีย
เวลส์ ธงชาติเวลส์4–1ธงชาติฟินแลนด์ ฟินแลนด์
Final
เวลส์ ธงชาติเวลส์0–0 (a.e.t.) (4–5 p)ธงชาติโปแลนด์ โปแลนด์
String

note_group

note_group
Determines the group that will be used for the notes. Can be either a custom-named group (e.g. |note_group=nb will generate [nb 1], [nb 2], etc.), or a predefined group (options are lower-alpha (default), upper-alpha, lower-roman, upper-roman and lower-greek). For more information, see H:PREGROUP. The predefined group decimal is also valid, but this will render the same as a standard reference. String

note_list

note_list
When set to a positive value (e.g. y, yes, 1), a list of notes will be forced to display, with the group based on the value of |note_group= (lower-alpha by default). This is not necessary for standard note usage, as a note list will always be displayed when notes are created integrally through via the respective parameters. This is primarily useful if the module does not contain any notes, but you want to display notes below the table from elsewhere above on the page.

When set to a negative value (e.g. n, no, 0), no list of notes will be generated below the module. This is useful if it is desired to display the note list elsewhere below on the page.

String

note_agg_N

note_agg_N
Creates a footnote after the aggregate score of the Nth row of the table (excluding header rows). The parameter can contain either the contents of the note, or a reference to another note.

Notes can be reused across different rows and different types of notes (aggregate or leg). To reuse a note, set the value to the identifier of the original note (e.g., agg_1 to reuse the aggregate note of row 1, or leg2_5 to reuse the second leg note of row 5).

A list of all the notes will then be generated in the table footer.

If the value of the note parameter begins with a reference, footnote or superscript, it will be directly prepended to the aggregate score without creating a separate note. These cannot be reused like standard notes. This is useful if it is desired to use an outside note system, or reference a note that exists elsewhere on the page.

Example 13

[แก้]
Usage
{{#invoke:Sports series|main|flag=n|legs=n|h_a=y|heading1=Semi-finals|heading3=Final
|{{fb-rt|POL}}|5–1|{{fb|EST}}
|{{fb-rt|WAL}}|4–1|{{fb|FIN}}
|{{fb-rt|WAL}}|0–0 (aet) (4–5 p)|{{fb|POL}}

|note_agg_1=Played behind closed doors
|note_agg_3=agg_1
}}
Output
ทีมเหย้าผลทีมเยือน
Semi-finals
โปแลนด์ ธงชาติโปแลนด์5–1[a]ธงชาติเอสโตเนีย เอสโตเนีย
เวลส์ ธงชาติเวลส์4–1ธงชาติฟินแลนด์ ฟินแลนด์
Final
เวลส์ ธงชาติเวลส์0–0 (a.e.t.) (4–5 p)[a]ธงชาติโปแลนด์ โปแลนด์
Notes:
  1. 1.0 1.1 Played behind closed doors
String

note_legX_N

note_legX_N
Creates a footnote after the Xth leg score of the Nth row of the table (excluding header rows). The parameter can contain either the contents of the note, or a reference to another note.

Notes can be reused across different rows and different types of notes (aggregate or leg). To reuse a note, set the value to the identifier of the original note (e.g., leg2_5 to reuse the second leg note of row 5, or agg_1 to reuse the aggregate note of row 1).

A list of all the notes will then be generated in the table footer.

If the value of the note parameter begins with a reference, footnote or superscript, it will be directly prepended to the aggregate score without creating a separate note. These cannot be reused like standard notes. This is useful if it is desired to use an outside note system, or reference a note that exists elsewhere on the page.

Example 14

[แก้]
Usage
{{#invoke:Sports series|main
|[[Arsenal F.C.|Arsenal]]|ENG|2–3|[[FC Bayern Munich|Bayern Munich]]|GER|2–2|0–1
|[[Atlético Madrid]]|ESP|4–5|[[Borussia Dortmund]]|GER|2–1|2–4
|[[Real Madrid CF|Real Madrid]]|ESP|4–4 (4–3 p)|[[Manchester City F.C.|Manchester City]]|ENG|3–3|1–1 (aet)
|'''[[Paris Saint-Germain FC|Paris Saint-Germain]]'''|FRA|[[Walkover|w/o]]|[[FC Barcelona|Barcelona]]|ESP|2–3|Canc.

|note_leg1_2=Played behind closed doors.
|note_agg_4=Paris Saint-Germain were awarded a walkover victory after Barcelona refused to play the second leg.
|note_leg2_4=agg_4
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Arsenal อังกฤษ2–3เยอรมนี Bayern Munich2–20–1
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–1[a]2–4
Real Madrid สเปน4–4 (4–3 p)อังกฤษ Manchester City3–31–1 (a.e.t.)
Paris Saint-Germain ฝรั่งเศสw/o[b]สเปน Barcelona2–3Canc.[b]
Notes:
  1. Played behind closed doors.
  2. 2.0 2.1 Paris Saint-Germain were awarded a walkover victory after Barcelona refused to play the second leg.
String

Other features/notes

[แก้]

Please note that in order to display a row in the table, at least one cell of said row must have value that is not empty or whitespace (this includes the note parameters for the aggregate and leg score columns). Otherwise, the module will not create a row for that line and all others below it.

Team country codes

[แก้]

The country codes supplied for each club are by default wrapped into {{fbaicon}}, based on Wikipedia's country data system of templates, and displayed next to each team.

Leg and aggregate scores

[แก้]

For the legs and aggregate scores, all incorrect types of dashes (such as a hyphen, em dash or minus sign) will be converted to an en dash (–). This does not apply to dashes contained in the article title/section anchor portion of wikilinks. These cells will also have nowrap applied to them, as long as two or more sets of parentheses are not present.

In addition, the module will also automatically convert text in brackets (as it relates to how matches were decided) to wikilinks. The following are supported:

  • (X–Y p), (X–Y pen) or (X–Y pso)(X–Y [[Penalty shoot-out (association football)|p]])
  • (aet) or (a.e.t.)([[Overtime (sports)#Association football|a.e.t.]])
  • (a) or (agr)([[Away goals rule|a]])
Usage
{{#invoke:Sports series|main|flag=n
|[[Valencia CF|Valencia]]|3-3 (3-2 p)|[[Deportivo Alavés|Alavés]]|2-1|1-2 (aet)
|[[CD Leganés|Leganés]]|2-2 (a)|[[Real Madrid CF|Real Madrid]]|0-1|2-1
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Valencia3–3 (3–2 p)Alavés2–11–2 (a.e.t.)
Leganés2–2 (a)Real Madrid0–12–1

Null/nil leg scores

[แก้]

If a cell of one of the leg scores contains only null, the cell will only contain an em dash (—). If |generate_links=y, then this em dash will be linked. However, if |solid_cell=y, then the cell will be left empty and given a background color of grey (#BBBBBB).

If a cell of one of the leg scores contains only nil, the cell will not be generated.

These features are useful for rounds of competitions that have an inconsistent number of legs, for example competitions that have a possible replay or play-off match after two legs.

Usage 1 (for null)
{{#invoke:Sports series|main
|[[İstanbul Başakşehir F.K.|İstanbul Başakşehir]]|TUR|1–3|[[F.C. Copenhagen|Copenhagen]]|DEN|1–0|0–3
|[[Olympiacos F.C.|Olympiacos]]|GRE|1–2|[[Wolverhampton Wanderers F.C.|Wolverhampton Wanderers]]|ENG|1–1|0–1
|[[Rangers F.C.|Rangers]]|SCO|1–4|[[Bayer 04 Leverkusen|Bayer Leverkusen]]|GER|1–3|0–1
|[[VfL Wolfsburg]]|GER|1–5|[[FC Shakhtar Donetsk|Shakhtar Donetsk]]|UKR|1–2|0–3
|[[Inter Milan]]|ITA|2–0|[[Getafe CF|Getafe]]|ESP|null|null
|[[Sevilla FC|Sevilla]]|ESP|2–0|[[AS Roma|Roma]]|ITA|null|null
|[[Eintracht Frankfurt]]|GER|0–4|[[FC Basel|Basel]]|SUI|0–3|0–1
|[[LASK]]|AUT|1–7|[[Manchester United F.C.|Manchester United]]|ENG|0–5|1–2
}}
Output 1 (for null)
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
İstanbul Başakşehir ตุรกี1–3เดนมาร์ก Copenhagen1–00–3
Olympiacos กรีซ1–2อังกฤษ Wolverhampton Wanderers1–10–1
Rangers สกอตแลนด์1–4เยอรมนี Bayer Leverkusen1–30–1
VfL Wolfsburg เยอรมนี1–5ยูเครน Shakhtar Donetsk1–20–3
Inter Milan อิตาลี2–0สเปน Getafe
Sevilla สเปน2–0อิตาลี Roma
Eintracht Frankfurt เยอรมนี0–4สวิตเซอร์แลนด์ Basel0–30–1
LASK ออสเตรีย1–7อังกฤษ Manchester United0–51–2
Usage 2 (for null, |solid_cell=y)
{{#invoke:Sports series|main|solid_cell=y
|[[İstanbul Başakşehir F.K.|İstanbul Başakşehir]]|TUR|1–3|[[F.C. Copenhagen|Copenhagen]]|DEN|1–0|0–3
|[[Olympiacos F.C.|Olympiacos]]|GRE|1–2|[[Wolverhampton Wanderers F.C.|Wolverhampton Wanderers]]|ENG|1–1|0–1
|[[Rangers F.C.|Rangers]]|SCO|1–4|[[Bayer 04 Leverkusen|Bayer Leverkusen]]|GER|1–3|0–1
|[[VfL Wolfsburg]]|GER|1–5|[[FC Shakhtar Donetsk|Shakhtar Donetsk]]|UKR|1–2|0–3
|[[Inter Milan]]|ITA|2–0|[[Getafe CF|Getafe]]|ESP|null|null
|[[Sevilla FC|Sevilla]]|ESP|2–0|[[AS Roma|Roma]]|ITA|null|null
|[[Eintracht Frankfurt]]|GER|0–4|[[FC Basel|Basel]]|SUI|0–3|0–1
|[[LASK]]|AUT|1–7|[[Manchester United F.C.|Manchester United]]|ENG|0–5|1–2
}}
Output 2 (for null, |solid_cell=y)
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
İstanbul Başakşehir ตุรกี1–3เดนมาร์ก Copenhagen1–00–3
Olympiacos กรีซ1–2อังกฤษ Wolverhampton Wanderers1–10–1
Rangers สกอตแลนด์1–4เยอรมนี Bayer Leverkusen1–30–1
VfL Wolfsburg เยอรมนี1–5ยูเครน Shakhtar Donetsk1–20–3
Inter Milan อิตาลี2–0สเปน Getafe
Sevilla สเปน2–0อิตาลี Roma
Eintracht Frankfurt เยอรมนี0–4สวิตเซอร์แลนด์ Basel0–30–1
LASK ออสเตรีย1–7อังกฤษ Manchester United0–51–2
Usage 3 (for nil)
{{#invoke:Sports series|main|flag=n|legs=3|leg3=Play-off
|{{fb-rt|LUX}}|5–6|{{fb|DEN}}|3–3|2–2|0–1
|{{fb-rt|ESP|1945}}|7–1|{{fb|IRL}}|5–1|2–0|nil
|{{fb-rt|FRA}}|2–5|{{fb|HUN}}|1–3|1–2|nil
|{{fb-rt|SWE}}|2–4|{{fb|URS}}|1–1|1–3|nil
}}
Output 3 (for nil)
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg3rd leg
ลักเซมเบิร์ก ธงชาติลักเซมเบิร์ก5–6ธงชาติเดนมาร์ก เดนมาร์ก3–32–20–1
สเปน ธงชาติสเปน7–1ธงชาติสาธารณรัฐไอร์แลนด์ สาธารณรัฐไอร์แลนด์5–12–0
ฝรั่งเศส ธงชาติฝรั่งเศส2–5ธงชาติฮังการี ฮังการี1–31–2
สวีเดน ธงชาติสวีเดน2–4ธงชาติสหภาพโซเวียต สหภาพโซเวียต1–11–3
[แก้]

Pages utilizing this module often include a wikilink with an anchor to the scores of the legs of a tie, linking to full match summaries.

Typically, when using anchored wikilinks, the page title can be omitted if the anchor appears on the same page. However, such links generally do not function properly when transcluded to other articles.

However, for this module, if any parameter contains an anchored wikilink that omits the page title (for example, [[#A vs B|2–2]]), the module will automatically insert the page title during transclusion to ensure proper linking. For proper functionality, the "sports series" module code must originate from the same page that contains the anchors.

Quasi-parameters

[แก้]

Plus sign (+) for country codes/flag variants

[แก้]

To allow for the use of flag variants, this module supports within the country code parameter the use of a plus sign (+) in between the country name/code and the name of the flag variant.

Usage
{{#invoke:Sports series|main
|[[Atlético Madrid]]|ESP+1945|4–5|[[Borussia Dortmund]]|GER+empire|2–1|2–4
}}
Output
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
Atlético Madrid สเปน4–5เยอรมนี Borussia Dortmund2–12–4

Three apostrophes (''') for manual bolding

[แก้]

While the template automatically bolds winning teams (unless |bold_winner=n), in some situations the module will be unable to determine the winner. Or, some users may find it undesirable to have the module bold the winner automatically. In these cases, manual bolding can be used to indicate the winning team of a tie. This can be done by placing the three apostrophes before and after the name of the team. If |bold_winner= is not disabled, the team that is manually bolded will override the winning team as determined by the module. If |color_winner= is also set, the cell of the team that is manually bolded will also be colored.

This may be used in conjunction with the below method by using five apostrophes on either side of a team to bold and color the cell.

(Note: The usage of three apostrophes was slightly modified for the purposes of this module to bold the cell. Therefore, it is not possible to selectively bold parts of the team parameters, while leaving other parts of said parameter unbolded.)

Usage 1
{{#invoke:Sports series|main|flag=n|bold_winner=n
|{{fb-rt|LUX}}|5–6|'''{{fb|DEN}}'''|3–3|2–3
|'''{{fb-rt|ESP}}'''|7–1|{{fb|IRL}}|5–1|2–0
|{{fb-rt|FRA}}|2–5|'''{{fb|HUN}}'''|1–3|1–2
|{{fb-rt|SWE}}|2–4|'''{{fb|NOR}}'''|1–1|1–3
}}
Output 1
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
ลักเซมเบิร์ก ธงชาติลักเซมเบิร์ก5–6ธงชาติเดนมาร์ก เดนมาร์ก3–32–3
สเปน ธงชาติสเปน7–1ธงชาติสาธารณรัฐไอร์แลนด์ สาธารณรัฐไอร์แลนด์5–12–0
ฝรั่งเศส ธงชาติฝรั่งเศส2–5ธงชาติฮังการี ฮังการี1–31–2
สวีเดน ธงชาติสวีเดน2–4ธงชาตินอร์เวย์ นอร์เวย์1–11–3
Usage 2 (third row overrides automatic bolding)
{{#invoke:Sports series|main|flag=n
|{{fb-rt|SWE}}|2–4|{{fb|NOR}}|1–1|1–3
|{{fb-rt|LUX}}|5–5 ([[Away goals rule|a]])|'''{{fb|DEN}}'''|3–3|2–2
|{{fb-rt|ESP}}|7–1|'''{{fb|IRL}}'''|5–1|2–0
}}
Output 2 (third row overrides automatic bolding)
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
สวีเดน ธงชาติสวีเดน2–4ธงชาตินอร์เวย์ นอร์เวย์1–11–3
ลักเซมเบิร์ก ธงชาติลักเซมเบิร์ก5–5 (a)ธงชาติเดนมาร์ก เดนมาร์ก3–32–2
สเปน ธงชาติสเปน7–1ธงชาติสาธารณรัฐไอร์แลนด์ สาธารณรัฐไอร์แลนด์5–12–0

Two apostrophes ('') for manual coloring

[แก้]

While the template allows for automatic coloring of the cells of winning teams via |color_winner=y, in some situations (such as matches tied on away goals) the module will be unable to determine the winner. Or, some users may find it undesirable to use |color_winner= to color the winner automatically. In these cases, manual coloring can be used to indicate the winning team of a tie. This can be done by placing the two apostrophes before and after the name of the team. If |color_winner= is set, the cell of team that is manually colored will override the winning team as determined by the module. If |bold_winner= is not disabled, the cell of the team that is manually colored will also be bolded.

This may be used in conjunction with the above method by using five apostrophes on either side of a team to color and bold the cell.

Two apostrophes surrounding an aggregate score (or the score of a single-leg tie) can also be used to manually indicate a draw/tie.

(Note: While two apostrophes surrounding both sides of text are usually used to add italics in wikitext, the usage was modified here to allow for a simple way to color the cell. Therefore, it is not possible to italicize team names or aggregate scores using this formatting.)

Usage 1
{{#invoke:Sports series|main|flag=n|bold_winner=n
|{{fbw-rt|LUX}}|5–6|''{{fbw|DEN}}''|3–3|2–3
|''{{fbw-rt|ESP}}''|7–1|{{fbw|IRL}}|5–1|2–0
|{{fbw-rt|FRA}}|2–5|''{{fbw|HUN}}''|1–3|1–2
|{{fbw-rt|SWE}}|2–4|''{{fbw|NOR}}''|1–1|1–3
}}
Output 1
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
ลักเซมเบิร์ก ธงชาติลักเซมเบิร์ก5–6ธงชาติเดนมาร์ก เดนมาร์ก3–32–3
สเปน ธงชาติสเปน7–1ธงชาติสาธารณรัฐไอร์แลนด์ ไอร์แลนด์5–12–0
ฝรั่งเศส ธงชาติฝรั่งเศส2–5ธงชาติฮังการี ฮังการี1–31–2
สวีเดน ธงชาติสวีเดน2–4ธงชาตินอร์เวย์ นอร์เวย์1–11–3
Usage 2 (third row overrides automatic coloring)
{{#invoke:Sports series|main|flag=n|color_winner=y|bold_winner=n
|{{fbw-rt|SWE}}|2–4|{{fbw|NOR}}|1–1|1–3
|{{fbw-rt|LUX}}|5–5 ([[Away goals rule|a]])|''{{fbw|DEN}}''|3–3|2–2
|{{fbw-rt|ESP}}|7–1|''{{fbw|IRL}}''|5–1|2–0
}}
Output 2 (third row overrides automatic coloring)
ทีมหนึ่งผลTooltip Aggregate scoreทีมสอง1st leg2nd leg
สวีเดน ธงชาติสวีเดน2–4ธงชาตินอร์เวย์ นอร์เวย์1–11–3
ลักเซมเบิร์ก ธงชาติลักเซมเบิร์ก5–5 (a)ธงชาติเดนมาร์ก เดนมาร์ก3–32–2
สเปน ธงชาติสเปน7–1ธงชาติสาธารณรัฐไอร์แลนด์ ไอร์แลนด์5–12–0
Usage 3
{{#invoke:Sports series|main|flag=n|legs=0|bold_winner=n
|{{fbw-rt|LUX}}|5–6|''{{fbw|DEN}}''
|''{{fbw-rt|ESP}}''|7–1|{{fbw|IRL}}
|{{fbw-rt|FRA}}|''2–2''|{{fbw|HUN}}
}}
Output 3
ทีมหนึ่งผลทีมสอง
ลักเซมเบิร์ก ธงชาติลักเซมเบิร์ก5–6ธงชาติเดนมาร์ก เดนมาร์ก
สเปน ธงชาติสเปน7–1ธงชาติสาธารณรัฐไอร์แลนด์ ไอร์แลนด์
ฝรั่งเศส ธงชาติฝรั่งเศส2–2ธงชาติฮังการี ฮังการี

See also

[แก้]

-- Module to build tables for aggregated match results in sports
-- See documentation for details

local p = {}

-- Function to parse and expand a template with given parameters
local function expandTemplate(frame, templateName, params)
    return frame:expandTemplate{ title = templateName, args = params }
end

-- Function to check the existence of flagTemplate
local function templateExists(templateName)
    local title = mw.title.new('Template:' .. templateName)
    return title and title.exists
end

-- Function to process country codes and variants, dividing parameters by the "+" sign
local function processIcon(iconString)
    if not iconString or iconString:match("^%s*$") then
        return nil, nil  -- Return nil for both iconCode and variant if the input is empty or only whitespace
    elseif iconString:find('+') then
        local parts = mw.text.split(iconString, '+', true)
        local iconCode = parts[1]
        local variant = parts[2]
        return iconCode, variant
    else
        return iconString, nil  -- Return the input string as iconCode if no "+" is present
    end
end

-- Function to determine the correct ordinal suffix for a given number for the heading
local function ordinal(n)
    local last_digit = n % 10
    local last_two_digits = n % 100
    if last_digit == 1 and last_two_digits ~= 11 then
        return n .. 'st'
    elseif last_digit == 2 and last_two_digits ~= 12 then
        return n .. 'nd'
    elseif last_digit == 3 and last_two_digits ~= 13 then
        return n .. 'rd'
    else
        return n .. 'th'
    end
end

-- Function to replace wiki links with their display text or link text
local function replaceLink(match)
    local pipePos = match:find("|")
    if pipePos then
        return match:sub(pipePos + 1, -3) -- Return text after the '|'
    else
        return match:sub(3, -3) -- Return text without the brackets
    end
end

-- Function to clean and process the aggregate score for comparison
local function cleanScore(score)
    -- Return an empty string if score is nil or empty to avoid errors
    if not score or score:match("^%s*$") then
        return ''
    end

    -- Replace wiki links
    score = score:gsub("%[%[.-%]%]", replaceLink)

    -- Remove MediaWiki's unique placeholder sequences for references
    score = score:gsub('\127%\'"`UNIQ.-QINU`"%\'\127', '')

    -- Remove superscript tags and their contents
    score = score:gsub('<sup.->.-</sup>', '')

    -- Convert dashes to a standard format
    score = score:gsub('[–—―‒−]+', '-')

    -- Strip all characters except numbers, dashes and parentheses
    return score:gsub('[^0-9%-()]+', '')
end

-- Function to determine the winner based on scores within parentheses (first) or regular format (second)
local function determineWinner(cleanAggregate, team1, team2, boldWinner, colorWinner, aggregate, isFBRStyle, legs, leg1Score, leg2Score, disableAwayGoals, skipAutoWinner, aggFormat)
    local team1Winner, team2Winner = false, false
    local score1, score2
    local manualBold = false
    local manualColor = false
    local isDraw = false

    -- Handling for manual bolding
    if team1 and type(team1) == 'string' then
        manualBold1 = team1:find("'''") and not (team1:gsub("'''", ""):match("^%s*$"))
        team1 = team1:gsub("'''", "")
    end
    if team2 and type(team2) == 'string' then
        manualBold2 = team2:find("'''") and not (team2:gsub("'''", ""):match("^%s*$"))
        team2 = team2:gsub("'''", "")
    end

    if manualBold1 then
        team1Winner = true
        manualBold = true
    end
    if manualBold2 then
        team2Winner = true
        manualBold = true
    end

    -- Handling for manual coloring of team or aggregate cells
    if team1 and type(team1) == 'string' then
        manualColor1 = team1:find("''") and not (team1:gsub("''", ""):match("^%s*$"))
        team1 = team1:gsub("''", "")
    end
    if team2 and type(team2) == 'string' then
        manualColor2 = team2:find("''") and not (team2:gsub("''", ""):match("^%s*$"))
        team2 = team2:gsub("''", "")
    end
    if aggregate then
        if aggFormat == 'bold' or aggFormat == 'both' then
            aggregate = "<b>" .. aggregate .. "</b>"
        end
        manualColorDraw = aggFormat == 'italic' or aggFormat == 'both'
    end

    if manualColor1 then
        if not team1Winner then
            team1Winner = true
        end
        manualColor = true
    end
    if manualColor2 then
        if not team2Winner then
            team2Winner = true
        end
        manualColor = true
    end
    if manualColorDraw then
        isDraw = true
        manualColor = true
    end

    -- Regular winner determination logic if manual bolding or coloring is not conclusive
    if not team1Winner and not team2Winner and not isDraw and not skipAutoWinner and (boldWinner or colorWinner or isFBRStyle) then
        local parenthetical = cleanAggregate:match('%((%d+%-+%d+)%)')
        local outsideParenthetical = cleanAggregate:match('^(%d+%-+%d+)')
        if parenthetical then -- Prioritize checking score inside parenthetical
            score1, score2 = parenthetical:match('(%d+)%-+(%d+)')
        elseif outsideParenthetical then
            score1, score2 = outsideParenthetical:match('(%d+)%-+(%d+)')
        end

        if score1 and score2 then
            score1 = tonumber(score1)
            score2 = tonumber(score2)

            if score1 > score2 then
                team1Winner = true
            elseif score1 < score2 then
                team2Winner = true
            elseif score1 == score2 and legs == 2 and not disableAwayGoals then
                -- Apply away goals rule
                local cleanLeg1 = cleanScore(leg1Score):gsub('[()]', '')
                local cleanLeg2 = cleanScore(leg2Score):gsub('[()]', '')
                local _, team2AwayGoals = cleanLeg1:match('(%d+)%-+(%d+)')
                local team1AwayGoals = cleanLeg2:match('(%d+)%-+(%d+)')

                if team1AwayGoals and team2AwayGoals then
                    team1AwayGoals, team2AwayGoals = tonumber(team1AwayGoals), tonumber(team2AwayGoals)

                    if team1AwayGoals > team2AwayGoals then
                        team1Winner = true
                    elseif team2AwayGoals > team1AwayGoals then
                        team2Winner = true
                    end
                end
            end

            if (colorWinner or isFBRStyle) and legs == 0 then
                isDraw = not team1Winner and not team2Winner
            end
        end
    end

    return team1, team2, team1Winner, team2Winner, manualBold, manualColor, isDraw, aggregate
end

-- Function to process score bold/italic formatting
function processScore(s)
    if not s or s == "" then
        return "", false
    end

    local scoreFormat = false

    -- Check for 5+ apostrophes (both bold and italic)
    if s:match("'''''+") then
        scoreFormat = "both"
        s = s:gsub("''+", "")
        return s, scoreFormat
    end

    -- Check for 3+ apostrophes (bold)
    if s:match("'''+") then
        scoreFormat = "bold"
        s = s:gsub("''+", "")
        return s, scoreFormat
    end

    -- Check for 2 apostrophes (italic)
    if s:match("''") then
        scoreFormat = "italic"
        s = s:gsub("''+", "")
        return s, scoreFormat
    end

    -- If no matches found, return original string and false
    return s, scoreFormat
end

-- Function to check if any parameter in a given row is non-nil and non-empty
local function anyParameterPresent(startIndex, step, args)
    -- Check regular parameters
    for index = startIndex, startIndex + step - 1 do
        if args[index] and args[index]:match("^%s*(.-)%s*$") ~= "" then
            return true
        end
    end

    -- Check aggregate note
    local rowIndex = math.floor((startIndex - 1) / step) + 1
    local aggNote = args['note_agg_' .. rowIndex]
    if aggNote and aggNote:match("^%s*(.-)%s*$") ~= "" then
        return true
    end

    -- Check leg notes
    local numLegs = step - (noFlagIcons and 3 or 5)  -- Calculate number of legs
    for leg = 1, numLegs do
        local legNote = args['note_leg' .. leg .. '_' .. rowIndex]
        if legNote and legNote:match("^%s*(.-)%s*$") ~= "" then
            return true
        end
    end

    return false
end

-- Function to check whether to reduce font size for upcoming matches
local function checkSmallText(str)
    -- Check for font size or small/big HTML tags
    if str:match("font%s?%-?size") or str:match("<small>") or str:match("<big>") then
        return false
    end

    -- Remove MediaWiki's unique placeholder sequences for references
    str = str:gsub('\127%\'"`UNIQ.-QINU`"%\'\127', '')

    -- Remove superscript tags and their contents
    str = str:gsub('<sup.->.-</sup>', '')

    -- Check for walkover-related strings (never shown in small text)
    if str:lower():match("walkover") or str:lower():match("w%.o%.") or str:lower():match("w/o") then
        return false
    end

    -- Replace wiki links with their display text or link text
    str = str:gsub("%[%[.-%]%]", replaceLink)

    -- Remove all text inside parentheses
    str = str:gsub("%b()", "")

    -- Exit if string contains only en/em dash
    if str == "—" or str == "–" then
        return false
    end

    -- Convert dashes to a standard format
    str = str:gsub('[–—―‒−]+', '-')

    -- Remove opening and closing HTML tags
    str = str:gsub("</?%w+[^>]*>", "")

    -- Remove apostrophes
    str = str:gsub("''+", "")

    -- Remove all whitespace
    str = str:gsub("%s+", "")

    -- Check if the string matches only a scoreline
    if str:match("^%d+-%d+$") then
        return false
    else
        return true
    end
end

-- Function to format the dashes and winning notes for aggregate/leg score parameters, and divide the score from references/notes/superscripts
local function format_and_extract_score(s, addSpan)
    if not s then return '', '' end -- Return empty strings if input is nil

    local function format_dash(pattern)
        s = mw.ustring.gsub(s, '^' .. pattern, '%1–%2')
        s = mw.ustring.gsub(s, '%(' .. pattern, '(%1–%2')
    end

    -- Format dashes
    format_dash('%s*([%d%.]+)%s*[–—―‒−%-]%s*([%d%.]+)')
    format_dash('%s*([%d%.]+)%s*&[MmNn][Dd][Aa][Ss][Hh];%s*([%d%.]+)')
    format_dash('%s*(%[%[[^%[%]]*%|[%d%.]+)%s*[–—―‒−%-]%s*([%d%.]+)')
    format_dash('%s*(%[[^%[%]%s]*%s+[%d%.]+)%s*[–—―‒−%-]%s*([%d%.]+)')
    format_dash('%s*(%[%[[^%[%]]*%|[%d%.]+)%s*&[MmNn][Dd][Aa][Ss][Hh];%s*([%d%.]+)')
    format_dash('%s*(%[[^%[%]%s]*%s+[%d%.]+)%s*&[MmNn][Dd][Aa][Ss][Hh];%s*([%d%.]+)')

    -- Extract end text
    local supStart = s:find('<sup')
    local placeholderStart = s:find('\127%\'"`UNIQ')

    -- Function to find the first parenthesis outside of wikilinks
    local function find_paren_outside_wikilinks(s)
        local pos = 1
        while true do
            pos = s:find('%(', pos)
            if not pos then break end
            
            local beforeParen = s:sub(1, pos - 1)
            local openLinks = select(2, beforeParen:gsub('%[%[', '')) - select(2, beforeParen:gsub('%]%]', ''))
            
            if openLinks == 0 then
                return pos
            end
            
            pos = pos + 1
        end
        return nil
    end

    local parenStart = find_paren_outside_wikilinks(s)

    local startPositions = {}
    if supStart then table.insert(startPositions, supStart) end
    if placeholderStart then table.insert(startPositions, placeholderStart) end
    if parenStart then table.insert(startPositions, parenStart) end

    local scoreMatch, endText
    if #startPositions > 0 then
        local startPos = math.min(unpack(startPositions))
        
        -- Find the last non-whitespace character before startPos
        local scoreEnd = s:sub(1, startPos - 1):match(".*%S") or ""
        scoreEnd = #scoreEnd

        -- Extract the score and endText
        scoreMatch = s:sub(1, scoreEnd)
        endText = s:sub(scoreEnd + 1)
    else
        -- If no match found, return the entire score
        scoreMatch = s
        endText = ""
    end

    -- Format winning notes in brackets (only if endText is not empty)
    if endText ~= "" then
        if addSpan then
            endText = mw.ustring.gsub(endText, '(%(%d+%s*–%s*%d+)%s+[Pp]%.?[EeSs]?%.?[NnOo]?%.?%)', '<span class="nowrap">%1 [[การดวลลูกโทษ|p]])</span>')
            endText = mw.ustring.gsub(endText, '%([Aa]%.?[Ee]%.?[Tt]%.?%)', '<span class="nowrap">([[เวลาพิเศษ#ฟุตบอล|a.e.t.]])</span>')
        else
            endText = mw.ustring.gsub(endText, '(%(%d+%s*–%s*%d+)%s+[Pp]%.?[EeSs]?%.?[NnOo]?%.?%)', '%1 [[การดวลลูกโทษ|p]])')
            endText = mw.ustring.gsub(endText, '%([Aa]%.?[Ee]%.?[Tt]%.?%)', '([[เวลาพิเศษ#ฟุตบอล|a.e.t.]])')
        end
        endText = mw.ustring.gsub(endText, '%([Aa]%.?[Gg]?%.?[Rr]?%.?%)', '([[กฎประตูทีมเยือน|a]])')
    end

    return scoreMatch, endText
end

-- Function to clean team names and generate links
local function cleanAndGenerateLinks(team1, team2, score, isSecondLeg)
    local function cleanTeam(str, defaultName)
        if str and str ~= "" then
        	str = str:gsub('<sup.->.-</sup>', '')
            str = str:gsub("</?%w+[^>]*>", "")
            str = str:gsub('\127%\'"`UNIQ.-QINU`"%\'\127', '')
            str = str:gsub("%[%[[Ff]ile:[^%]]+%]%]", "")
            str = str:gsub("%[%[[Ii]mage:[^%]]+%]%]", "")
            str = str:gsub("%[%[.-%]%]", replaceLink)
            str = str:gsub("%s*&nbsp;%s*", "")
            str = str:match("^%s*(.-)%s*$")  -- Remove leading and trailing whitespace
            return str ~= "" and str or defaultName
        end
        return defaultName
    end

    team1 = cleanTeam(team1, "ทีมหนึ่ง")
    team2 = cleanTeam(team2, "ทีมสอง")

    if score and score:match("%S") then
        local linkScore = score
        if score:find('%[') then
            linkScore = score:match('^([%d%.]+–[%d%.]+)')
            if not linkScore then
                return score
            end
        end

        if linkScore then
            local link
            if isSecondLeg then
                link = "[[#" .. team2 .. " v " .. team1 .. "|" .. linkScore .. "]]"
            else
                link = "[[#" .. team1 .. " v " .. team2 .. "|" .. linkScore .. "]]"
            end
            return link .. score:sub(#linkScore + 1)
        end
    end

    return score
end

-- Function to process notes for aggregate and leg scores
local function processNote(frame, notes, noteKey, noteText, endText, rowIndex, rand_val, noteGroup)
    if not noteText then return endText, notes end
    if noteText:match("^%s*<sup") or noteText:match("^\127%\'%\"`UNIQ") then
        return noteText .. endText, notes
    end

    local function createInlineNote(name)
        return frame:extensionTag{
            name = 'ref',
            args = {
                name = name,
                group = noteGroup
            }
        }
    end

    -- Check if noteText is a reference to another note
    local referenced_note = noteText:match("^(agg_%d+)$") or noteText:match("^(leg%d+_%d+)$")
    if referenced_note then
        local referenced_note_id = '"table_note_' .. referenced_note .. '_' .. rand_val .. '"'
        return endText .. createInlineNote(referenced_note_id), notes
    end

    local note_id = '"table_note_' .. noteKey .. '_' .. rowIndex .. '_' .. rand_val .. '"'
    if not notes[note_id] then
        notes[note_id] = noteText
    end

    return endText .. createInlineNote(note_id), notes
end

-- Function to generate the footer if necessary
local function createFooter(frame, notes, noteGroup, isFBRStyle, displayNotes, externalNotes, legs)
    local needFooter = (isFBRStyle and legs == 0) or displayNotes or (next(notes) ~= nil)

    if not needFooter then
        return ''  -- Return an empty string if no footer is needed
    end

    local divContent = mw.html.create('div')
        :addClass('sports-series-notes')

    if isFBRStyle and legs == 0 then
        divContent:wikitext("Legend: Blue = home team win; Yellow = draw; Red = away team win.")
    end

    if (next(notes) ~= nil and not externalNotes) or displayNotes then
        divContent:wikitext((isFBRStyle and legs == 0) and "<br>Notes:" or "Notes:")
    end

    local footer = tostring(divContent)

    if next(notes) ~= nil or displayNotes then
        local noteDefinitions = {}
        for noteId, noteText in pairs(notes) do
            if type(noteId) == 'string' and noteId:match('^"table_note') then
                table.insert(noteDefinitions, frame:extensionTag{
                    name = 'ref',
                    args = {
                        name = noteId,
                        group = noteGroup
                    },
                    content = noteText
                })
            end
        end

        if externalNotes then
            local hiddenRefs = mw.html.create('span')
                :addClass('sports-series-hidden')
                :wikitext(table.concat(noteDefinitions))
            if isFBRStyle and legs == 0 then
                footer = footer .. tostring(hiddenRefs)
            else
                footer = tostring(hiddenRefs)
            end
        else
            local reflistArgs = {
                refs = table.concat(noteDefinitions),
                group = noteGroup
            }
            footer = footer .. frame:expandTemplate{
                title = 'reflist',
                args = reflistArgs
            }
        end
    end

    return footer
end

-- Main function that processes input and returns the wikitable
function p.main(frame)
    local args = require('มอดูล:Arguments').getArgs(frame, {trim = true})
    local yesno = require('มอดูล:Yesno')

    -- Check for section transclusion
    local tsection = frame:getParent().args['transcludesection'] or frame:getParent().args['section'] or ''
    local bsection = args['section'] or ''
    if tsection ~= '' and bsection ~= '' then
        if tsection ~= bsection then
            return ''  -- Return an empty string if sections don't match
        end
    end

    local root = mw.html.create()
    local templatestyles = frame:extensionTag{
        name = 'templatestyles',
        args = { src = 'มอดูล:Sports series/styles.css' }
    }
    root:wikitext(templatestyles)

    local flagYesno = yesno(args.flag)
    local showFlags = flagYesno ~= false
    local noFlagIcons = not showFlags
    local fillBlanks = yesno(args.fill_blanks)
    local generateLinks = yesno(args.generate_links)
    local solidCell = yesno(args.solid_cell) or args.solid_cell == 'grey' or args.solid_cell == 'gray'
    local baselink = frame:getParent():getTitle()
    local currentPageTitle = mw.title.getCurrentTitle().fullText
    if currentPageTitle == baselink then baselink = '' end
    local notes = {}
    local noteGroup = args.note_group or 'lower-alpha'
    local noteListValue = yesno(args.note_list)
    local displayNotes = noteListValue == true
    local externalNotes = noteListValue == false
    math.randomseed(os.clock() * 10^8)  -- Initialize random number generator
    local rand_val = math.random()

    -- Process the font size parameter
    local fontSize
    if args.font_size then
        -- Remove trailing '%' if present and convert to number
        fontSize = tonumber((args.font_size:gsub('%s*%%$', '')))
        if fontSize then
            fontSize = math.max(fontSize, 85)  -- Ensure font size is at least 85
        end
    end

    -- Process flag parameter to determine flag template and variant
    local flagTemplate = 'fbaicon'
    local flagSize = args.flag_size
    if showFlags then
        if args.flag and args.flag ~= '' and not flagYesno then
            flagTemplate = args.flag:gsub('^Template:', '')
            if not templateExists(flagTemplate) then
                flagTemplate = 'flag icon'
            end
        end

        if flagSize and not flagSize:match('px$') then
            flagSize = flagSize .. 'px'
        end
    end

    -- Determine whether line should be displayed
    local showCountry = args.show_country
    local function shouldShowRow(team1Icon, team2Icon)
        if not showCountry or noFlagIcons then
            return true
        end
        return team1Icon == showCountry or team2Icon == showCountry
    end

    local legs = 2
    if args.legs then
        if yesno(args.legs) == false or args.legs == '1' then
            legs = 0
        else
            legs = tonumber(args.legs) and math.max(tonumber(args.legs), 2) or 2
        end
    end
    local teamWidth = (tonumber(args['team_width']) and args['team_width'] .. 'px') or '250px'
    local scoreWidth = (tonumber(args['score_width']) and args['score_width'] .. 'px') or '80px'
    local boldWinner = args.bold_winner == nil or yesno(args.bold_winner, true)
    local colorWinner = yesno(args.color_winner)
    local matchesStyle = args.matches_style
    local isFBRStyle = matchesStyle and matchesStyle:upper() == "FBR"
    local isHA = yesno(args.h_a) or (isFBRStyle and legs == 0)
    local disableAwayGoals = yesno(args.away_goals) == false
    local disableSmallText = yesno(args.small_text) == false
    local noWrapValue = yesno(args.nowrap)
    local noWrap = noWrapValue == true
    local disableNoWrap = noWrapValue == false
    local aggFormat

    local tableClass = 'wikitable sports-series'
    local doCollapsed = yesno(args.collapsed)
    if doCollapsed then
        tableClass = tableClass .. ' mw-collapsible mw-collapsed'
    end
    if yesno(args.center_table) and not doCollapsed then
        tableClass = tableClass .. ' center-table'
    end
    if fontSize then
        table:css('font-size', fontSize .. '%')
    end

    -- Create the table element
    local table = root:tag('table')
        :addClass(tableClass)
        :cssText(tableStyle)
    if args.id then
        table:attr('id', args.id)  -- Optional id parameter to allow anchor to table
    end
    if noWrap then
        table:attr('data-nowrap', 'y')
    elseif not disableNoWrap then
        table:attr('data-nowrap', 'n')
    end

    -- Add a caption to table if the "caption" parameter is passed
    if args.caption then
        table:tag('caption'):wikitext(args.caption)
    end

    -- Count number of columns
    local colCount = 3 + legs

    -- Add a title row above column headings if the "title" parameter is passed
    if args.title then
        local titleRow = table:tag('tr'):addClass('title-row')
        titleRow:tag('th')
            :attr('colspan', colCount)
            :attr('scope', 'colgroup')
            :wikitext(args.title)
    end

    -- Create the header row with team and score columns
    local header = table:tag('tr')
    local defaultTeam1 = isHA and 'ทีมเหย้า' or 'ทีมหนึ่ง'
    local defaultTeam2 = isHA and 'ทีมเยือน' or 'ทีมสอง'
    header:tag('th'):attr('scope', 'col'):css('width', teamWidth):wikitext(args['team1'] or defaultTeam1)
    header:tag('th'):attr('scope', 'col'):css('width', scoreWidth):wikitext(args['ผลประตูรวม'] or legs == 0 and 'ผล' or '[[ผลประตูรวม|<abbr title="ผลประตูรวม">ผล</abbr>]]<span class="sports-series-sr-only">Tooltip Aggregate score</span>')
    header:tag('th'):attr('scope', 'col'):css('width', teamWidth):wikitext(args['team2'] or defaultTeam2)

    -- Add columns for each leg if applicable
    if legs > 0 then
        for leg = 1, legs do
            local legHeading = args['นัดที่' .. leg]

            -- Check if "legN" parameter is present
            if not legHeading then
                if args.leg_prefix then
                    legHeading = yesno(args.leg_prefix) and ('นัดที่ ' .. leg) or (args.leg_prefix .. ' ' .. leg)
                elseif args.leg_suffix and not yesno(args.leg_suffix) then
                    legHeading = ordinal(leg) .. ' ' .. args.leg_suffix
                else
                    legHeading = ordinal(leg) .. ' leg'
                end
            end

            header:tag('th'):attr('scope', 'col'):css('width', scoreWidth):wikitext(legHeading)
        end
    end

    local step = (noFlagIcons and 3 or 5) + legs  -- Determine the step size based on the presence of flag icons
    local i = 1
    while anyParameterPresent(i, step, args) do
        local rowIndex = math.floor((i - 1) / step) + 1
        local aggNote = args['note_agg_' .. rowIndex]
        local headingParam = args['heading' .. rowIndex]

        local team1, team2, aggregateScore, aggregateEndText, legEndText, team1Icon, team2Icon, team1Variant, team2Variant
        local team1Winner, team2Winner, manualBold, manualColor, isDraw = false, false, false, false, false
        local leg1Score, leg2Score = false, false

        -- Process rows from input
        team1 = args[i]
        if noFlagIcons then
            aggregateScore = args[i+1]
            team2 = args[i+2]
        else
            team1Icon, team1Variant = processIcon(args[i+1])
            aggregateScore = args[i+2]
            team2 = args[i+3]
            team2Icon, team2Variant = processIcon(args[i+4])
        end

        -- Check if the line should be shown based on both teams
        if shouldShowRow(team1Icon, team2Icon) then
            -- Add a heading above a given row in the table
            if headingParam and not showCountry then
                local headingRow = table:tag('tr'):addClass('heading-row')
                headingRow:tag('td')
                    :attr('colspan', colCount)
                    :wikitext('<strong>' .. headingParam .. '</strong>')
            end

            local row = table:tag('tr')

            -- Name the 1st/2nd leg scores for two-legged ties
            if legs == 2 then
                if noFlagIcons then
                    leg1Score = args[i+3]
                    leg2Score = args[i+4]
                else
                    leg1Score = args[i+5]
                    leg2Score = args[i+6]
                end
            end

            -- Clean the aggregate score
            local cleanAggregate = cleanScore(aggregateScore)
            aggregateScore, aggFormat = processScore(aggregateScore)
            -- Format anchor links for aggregate score
            local aggParen = cleanAggregate:match("%(.*%(")
            local aggSpan = (disableNoWrap or (not noWrap and not disableNoWrap and aggParen))
            aggregateScore, aggregateEndText = format_and_extract_score(aggregateScore, aggSpan)
            aggregateEndText, notes = processNote(frame, notes, 'agg', aggNote, aggregateEndText, rowIndex, rand_val, noteGroup)
            if generateLinks and legs == 0 then
                aggregateScore = cleanAndGenerateLinks(team1, team2, aggregateScore, false)
            end

            local skipAutoWinner = legs == 0 and aggregateScore ~= '' and checkSmallText(aggregateScore)

            -- Determine the winning team on aggregate
            team1, team2, team1Winner, team2Winner, manualBold, manualColor, isDraw, aggregateScore = determineWinner(cleanAggregate, team1, team2, boldWinner, colorWinner, aggregateScore, isFBRStyle, legs, leg1Score, leg2Score, disableAwayGoals, skipAutoWinner, aggFormat)

            -- Function to create flag template parameters
            local function getFlagParams(icon, variant)
                local params = {icon, variant = variant}
                if flagSize then
                    params.size = flagSize
                end
                return params
            end

            -- Generate text to display for each team
            local team1Text = noFlagIcons and (team1 or '') or ((team1Icon ~= "" and team1Icon ~= nil) and ((team1 or '') .. '&nbsp;' .. expandTemplate(frame, flagTemplate, getFlagParams(team1Icon, team1Variant))) or (team1 or ''))
            local team2Text = noFlagIcons and (team2 or '') or ((team2Icon ~= "" and team2Icon ~= nil) and (expandTemplate(frame, flagTemplate, getFlagParams(team2Icon, team2Variant)) .. '&nbsp;' .. (team2 or '')) or (team2 or ''))

            -- When set by user, adds blank flag placeholder next to team names
            if fillBlanks and showFlags then
            	local flagDimensions = flagSize or "25x17px"
            	local placeholderFlag = string.format('<span class="flagicon">[[ไฟล์:Flag placeholder.svg|%s|link=]]</span>', flagDimensions)
                if not team1Icon or team1Icon == "" then
                    team1Text = team1Text .. '&nbsp;' .. placeholderFlag
                end
                if not team2Icon or team2Icon == "" then
                    team2Text = placeholderFlag .. '&nbsp;' .. team2Text
                end
            end

            local aggregateContent
            if not disableSmallText and skipAutoWinner then
                aggregateContent = '<span class="sports-series-small">' .. aggregateScore .. '</span>' .. aggregateEndText
            else
                aggregateContent = aggregateScore .. aggregateEndText
            end

            -- Create aggregate score cell with conditional styling
            local aggregateClass = ''
            if isFBRStyle and legs == 0 then
                if team1Winner then
                    aggregateClass = 'fbr-home-win'
                elseif team2Winner then
                    aggregateClass = 'fbr-away-win'
                elseif isDraw then
                    aggregateClass = 'draw'
                end
            elseif isDraw then
                aggregateClass = 'draw'
            end
            if not disableNoWrap and (not noWrap and aggParen) then
                aggregateClass = (aggregateClass ~= '' and aggregateClass .. ' ' or '') .. 'allow-wrap'
            end

            -- Create rows for aggregate score and team names, bolded if set by user
            row:tag('td'):addClass(team1Winner and (colorWinner or manualColor) and 'winner' or nil):wikitext((team1Winner and (boldWinner or manualBold) and team1Text ~= '') and ('<strong>' .. team1Text .. '</strong>') or team1Text)
            row:tag('td'):addClass(aggregateClass ~= '' and aggregateClass or nil):wikitext(aggregateContent)
            row:tag('td'):addClass(team2Winner and (colorWinner or manualColor) and 'winner' or nil):wikitext((team2Winner and (boldWinner or manualBold) and team2Text ~= '') and ('<strong>' .. team2Text .. '</strong>') or team2Text)

            -- Add columns for each leg score if applicable
            if legs > 0 then
                for leg = 1, legs do
                    local legIndex = i + 4 + leg + (noFlagIcons and -2 or 0)
                    local legScore = args[legIndex]
                    local legNote = args['note_leg' .. leg .. '_' .. rowIndex]
                    if legScore ~= "nil" then
                        if legScore == "null" then
                            if solidCell then
                                row:tag('td'):addClass('solid-cell')
                            else
                                legScore = '—'
                            end
                        end

                        if legScore ~= "null" then
                            -- Format anchor links for leg scores
                            local cleanLeg = cleanScore(legScore)
                            local legFormat
                            legScore, legFormat = processScore(legScore)
                            local legParen = cleanLeg:match("%(.*%(")
                            local legSpan = (disableNoWrap or (not noWrap and not disableNoWrap and legParen))
                            legScore, legEndText = format_and_extract_score(legScore, legSpan)
                            legEndText, notes = processNote(frame, notes, 'leg' .. leg, legNote, legEndText, rowIndex, rand_val, noteGroup)
                            if generateLinks and not aggregateContent:lower():find("bye") then
                                if leg == 1 then
                                    legScore = cleanAndGenerateLinks(team1, team2, legScore, false)
                                elseif leg == 2 then
                                    legScore = cleanAndGenerateLinks(team1, team2, legScore, true)
                                end
                            end
                            if legFormat == 'bold' or legFormat == 'both' then legScore = '<b>' .. legScore .. '</b>' end
                            if legFormat == 'italic' or legFormat == 'both' then legScore = '<i>' .. legScore .. '</i>' end
                            local legContent
                            if not disableSmallText and legScore ~= '' and checkSmallText(legScore) then
                                legContent = '<span class="sports-series-small">' .. legScore .. '</span>' .. legEndText
                            else
                                legContent = legScore .. legEndText
                            end
                            local legClass = ''
                            if not disableNoWrap and (not noWrap and legParen) then
                                legClass = 'allow-wrap'
                            end
                            -- Write cells for legs
                            row:tag('td'):addClass(legClass ~= '' and legClass or nil):wikitext(legContent)
                        end
                    end
                end
            end
        end

        i = i + step
    end

    -- Generate footer text
    local footerText = createFooter(frame, notes, noteGroup, isFBRStyle, displayNotes, externalNotes, legs)
    root:wikitext(footerText)

    local tableCode = tostring(root)

    -- Rewrite anchor links for the entire table
    if baselink ~= '' then
        tableCode = mw.ustring.gsub(tableCode, '(%[%[)(#[^%[%]]*%|)', '%1' .. baselink .. '%2')
    end
    local escapedTitle = currentPageTitle:gsub("([%(%)%.%%%+%-%*%?%[%^%$])", "%%%1")
    local titlePattern = '%[%[' .. escapedTitle .. '(#[^%[%]]*%|)'
    tableCode = mw.ustring.gsub(tableCode, titlePattern, '[[%1')

    return tableCode
end

return p