Income Tax#

Income tax is a tax levied on the income earned by individuals and businesses. It is one of the primary sources of revenue for the UK government and is used to fund public services and government expenditures.

  • Tax Allowances: These are specific amounts of income that individuals can earn before they are required to pay income tax. Various types of allowances exist, such as Personal Allowance, Marriage Allowance, Property Allowance, and Dividend Allowance, each offering different benefits and eligibility criteria.

  • Tax Charges: Tax charges arise when an individual’s income exceeds certain thresholds or when specific conditions are met. These charges fluctuate based on income levels and are influenced by additional factors, such as the High-Income Child Benefit Charge.

  • Tax Rates: The government applies different percentages of tax rates based on the income bracket an individual falls into. There are Basic, Higher, and Additional rates, each applicable to respective income ranges. Moreover, specific types of income, like dividends, have their distinct tax rates.

  • Tax Reliefs: To promote certain behaviors or lower the tax burden for specific groups, the government provides tax reliefs. These provisions reduce tax liability for eligible individuals, with examples including reliefs for Pension Contributions, Charitable Donations, and Work-Related Expenses.

Legislation#

UK income tax legislation is grounded in primary legislation passed by the UK Parliament, supplemented by secondary legislation and administrative guidance issued by Her Majesty’s Revenue and Customs (HMRC).

  • Income Tax Act 2007 (ITA 2007): This is a central piece of legislation consolidating various statutes related to income tax in the UK. It comprehensively covers aspects such as the charge to tax, applicable rates, allowances, and reliefs, serving as a foundational reference for income tax matters.

  • Taxation of Chargeable Gains Act 1992 (TCGA 1992): Though primarily focused on capital gains tax, this Act intersects significantly with income tax, particularly in the realm of taxation of gains. It provides detailed regulations on how gains should be taxed and calculated.

  • Income Tax (Earnings and Pensions) Act 2003 (ITEPA 2003): ITEPA 2003 governs the rules related to the taxation of employment income, pension income, and social security income. It outlines the various categories and criteria for taxable earnings and pensions, ensuring a structured approach to taxation in these areas.

  • HMRC Manuals and Guidance: Produced by HMRC, these comprehensive guides aim to help taxpayers in understanding and complying with the complex tax legislation. They provide practical insights and interpretations of the laws, offering clarity and assistance to both individuals and businesses in navigating the income tax landscape.

Methodology:#

Income tax logic can be found in policyengine-uk/policyengine_uk/variables/gov/hmrc/income_tax.

The following table shows a series of income tax simulations using the PolicyEngine UK model.

Hide code cell source
import pandas as pd
from policyengine_uk import Simulation

def calculate_taxes(employment_income, dividend_income, savings_interest_income):
    simulation = Simulation(
        situation={
            "people": {
                "person": {
                    "employment_income": employment_income,
                    "dividend_income": dividend_income,
                    "savings_interest_income": savings_interest_income
                }
            }
        }
    )
    income_tax = simulation.calculate("income_tax")[0]
    dividend_income_tax = simulation.calculate("dividend_income_tax")[0]  # Added
    savings_income_tax = simulation.calculate("savings_income_tax")[0]  # Added
    
    return income_tax, dividend_income_tax, savings_income_tax

data = {
    "Person": ["Person1", "Person2", "Person3", "Person4", "Person5"],
    "Employment Income (£)": [50000, 60000, 70000, 80000, 90000],
    "Dividend Income (£)": [10000, 15000, 20000, 25000, 30000],
    "Savings Interest Income (£)": [5000, 10000, 15000, 20000, 25000],
    "Income Tax (£)": [],
    "Dividend Income Tax (£)": [],
    "Savings Income Tax (£)": []
}

for emp_income, div_income, sav_income in zip(data["Employment Income (£)"], data["Dividend Income (£)"], data["Savings Interest Income (£)"]):
    income_tax, div_tax, sav_tax = calculate_taxes(emp_income, div_income, sav_income)
    data["Income Tax (£)"].append(income_tax)
    data["Dividend Income Tax (£)"].append(div_tax)
    data["Savings Income Tax (£)"].append(sav_tax)

df = pd.DataFrame(data)
df
Person Employment Income (£) Dividend Income (£) Savings Interest Income (£) Income Tax (£) Dividend Income Tax (£) Savings Income Tax (£)
0 Person1 50000 10000 5000 10068.5 2582.5 0.0
1 Person2 60000 15000 10000 17457.0 4225.0 1800.0
2 Person3 70000 20000 15000 26082.0 5850.0 3800.0
3 Person4 80000 25000 20000 37707.0 7475.0 5800.0
4 Person5 90000 30000 25000 45360.0 9100.0 7800.0

Appendix:#

The following tables display the parameter values for income tax allowance.

Hide code cell source
from policyengine_uk.system import system
import pandas as pd

default = system.parameters.gov.hmrc.income_tax.allowances.annual_allowance.default
minimum = system.parameters.gov.hmrc.income_tax.allowances.annual_allowance.minimum
reduction_rate = system.parameters.gov.hmrc.income_tax.allowances.annual_allowance.reduction_rate
taper = system.parameters.gov.hmrc.income_tax.allowances.annual_allowance.taper
annual_allowance_data = {
    "Attribute": ["Annual Allowance"] * 4,
    "Type": ["Default", "Minimum", "Reduction Rate", "Taper"],
    "Value": [
        default.values_list[-1].value,
        minimum.values_list[-1].value,
        reduction_rate.values_list[-1].value,
        taper.values_list[-1].value,
    ],
    "Effective Date": [
        default.values_list[-1].instant_str,
        minimum.values_list[-1].instant_str,
        reduction_rate.values_list[-1].instant_str,
        taper.values_list[-1].instant_str,
    ],
    "Unit": [default.metadata["unit"], minimum.metadata["unit"], reduction_rate.metadata["unit"], taper.metadata["unit"]]
}


max = system.parameters.gov.hmrc.income_tax.allowances.marriage_allowance.max
rounding_increment = system.parameters.gov.hmrc.income_tax.allowances.marriage_allowance.rounding_increment
takeup_rate = system.parameters.gov.hmrc.income_tax.allowances.marriage_allowance.takeup_rate
marriage_allowance_data = {
    "Attribute": ["Marriage Allowance"] * 3,
    "Type": ["Max", "Rounding Increment", "Takeup Rate"],
    "Value": [
        max.values_list[-1].value,
        rounding_increment.values_list[-1].value,
        takeup_rate.values_list[-1].value
    ],
    "Effective Date": [
        max.values_list[-1].instant_str,
        rounding_increment.values_list[-1].instant_str,
        takeup_rate.values_list[-1].instant_str
    ],
     "Unit": [max.metadata["unit"], rounding_increment.metadata["unit"], takeup_rate.metadata["unit"]]
}


deduction_rate = system.parameters.gov.hmrc.income_tax.allowances.married_couples_allowance.deduction_rate
married_couples_allowance_data = {
    "Attribute": ["Married Couples Allowance"],
    "Type": ["Deduction Rate"],
    "Value": [
        deduction_rate.values_list[-1].value
    ],
    "Effective Date": [
        deduction_rate.values_list[-1].instant_str
    ],
    "Unit": [deduction_rate.metadata["unit"]]
}


amount = system.parameters.gov.hmrc.income_tax.allowances.personal_allowance.amount
values = [item.value for item in amount.values_list]
dates = [item.instant_str for item in amount.values_list]
personal_allowance_data = {
    "Attribute": ["Personal Allowance"] * len(values),
    "Type": ["Amount"] * len(values),
    "Value": values,
    "Effective Date": dates,
    "Unit": [amount.metadata["unit"]] * len(values)
}


addtional_threshold = system.parameters.gov.hmrc.income_tax.allowances.personal_savings_allowance.additional
basic_threshold = system.parameters.gov.hmrc.income_tax.allowances.personal_savings_allowance.basic
higher_threshold = system.parameters.gov.hmrc.income_tax.allowances.personal_savings_allowance.higher
personal_savings_allowance_data = {
    "Attribute": ["Personal Savings Allowance"] * 3,
    "Type": ["Addtional Threshold", "Basic Threshold", "Higher Threshold"],
    "Value": [
        addtional_threshold.values_list[-1].value,
        basic_threshold.values_list[-1].value,
        higher_threshold.values_list[-1].value
    ],
    "Effective Date": [
        addtional_threshold.values_list[-1].instant_str,
        basic_threshold.values_list[-1].instant_str,
        higher_threshold.values_list[-1].instant_str
    ],
    "Unit": [addtional_threshold.metadata["unit"], basic_threshold.metadata["unit"], higher_threshold.metadata["unit"]]
}


dividend_allowance = system.parameters.gov.hmrc.income_tax.allowances.dividend_allowance
dividend_allowance_data = {
    "Attribute": ["Dividend Allowance"],
    "Type": ["Dividend Allowance"],
    "Value": [
        dividend_allowance.values_list[-1].value
    ],
    "Effective Date": [
        dividend_allowance.values_list[-1].instant_str
    ],
    "Unit": [dividend_allowance.metadata["unit"]]
}


property_allowance = system.parameters.gov.hmrc.income_tax.allowances.property_allowance
property_allowance_data = {
    "Attribute": ["Property Allowance"],
    "Type": ["Property Allowance"],
    "Value": [
        property_allowance.values_list[-1].value
    ],
    "Effective Date": [
        property_allowance.values_list[-1].instant_str
    ],
    "Unit": [property_allowance.metadata["unit"]]
}


trading_allowance = system.parameters.gov.hmrc.income_tax.allowances.trading_allowance
trading_allowance_data = {
    "Attribute": ["Trading Allowance"],
    "Type": ["Trading Allowance"],
    "Value": [
        trading_allowance.values_list[-1].value
    ],
    "Effective Date": [
        trading_allowance.values_list[-1].instant_str
    ],
    "Unit": [trading_allowance.metadata["unit"]]
}

annual_allowance_df = pd.DataFrame(annual_allowance_data)
marriage_allowance_df = pd.DataFrame(marriage_allowance_data)
married_couples_allowance_df = pd.DataFrame(married_couples_allowance_data)
personal_allowance_df = pd.DataFrame(personal_allowance_data)
personal_savings_allowance_df = pd.DataFrame(personal_savings_allowance_data)
dividend_allowance_df = pd.DataFrame(dividend_allowance_data)
property_allowance_df = pd.DataFrame(property_allowance_data)
trading_allowance_df = pd.DataFrame(trading_allowance_data)

income_tax_allowance_df = pd.concat([
    annual_allowance_df,
    marriage_allowance_df,
    married_couples_allowance_df,
    personal_allowance_df,
    personal_savings_allowance_df,
    dividend_allowance_df,
    property_allowance_df,
    trading_allowance_df
], ignore_index=True)
income_tax_allowance_df
Attribute Type Value Effective Date Unit
0 Annual Allowance Default 40000.000000 2015-06-01 currency-GBP
1 Annual Allowance Minimum 4000.000000 2015-06-01 currency-GBP
2 Annual Allowance Reduction Rate 0.500000 2015-06-01 marginal-rate
3 Annual Allowance Taper 240000.000000 2015-06-01 currency-GBP
4 Marriage Allowance Max 0.100000 2016-04-01 /1
5 Marriage Allowance Rounding Increment 10.000000 2016-04-01 currency-GBP
6 Marriage Allowance Takeup Rate 1.000000 2000-01-01 /1
7 Married Couples Allowance Deduction Rate 0.100000 2010-01-01 /1
8 Personal Allowance Amount 12559.449065 2026-01-01 currency-GBP
9 Personal Allowance Amount 12570.000000 2025-04-06 currency-GBP
10 Personal Allowance Amount 12570.000000 2021-04-06 currency-GBP
11 Personal Allowance Amount 12500.000000 2019-04-06 currency-GBP
12 Personal Allowance Amount 11850.000000 2018-04-06 currency-GBP
13 Personal Allowance Amount 11500.000000 2017-04-06 currency-GBP
14 Personal Allowance Amount 10600.000000 2015-04-06 currency-GBP
15 Personal Savings Allowance Addtional Threshold 0.000000 2005-06-01 currency-GBP
16 Personal Savings Allowance Basic Threshold 1000.000000 2005-06-01 currency-GBP
17 Personal Savings Allowance Higher Threshold 500.000000 2005-06-01 currency-GBP
18 Dividend Allowance Dividend Allowance 2000.000000 2015-06-05 currency-GBP
19 Property Allowance Property Allowance 1000.000000 2005-06-01 currency-GBP
20 Trading Allowance Trading Allowance 1000.000000 2005-06-01 currency-GBP

Other income tax parameters can be found in policyengine-uk/policyengine_uk/parameters/gov/hmrc/income_tax.

Simulation#

The figure illustrates the implementation of a simulation for computing income tax and dividend income tax using PolicyEngine UK model. The simulation is conducted for an individual aged 30 with a fixed dividend income of £10,000 while varying the employment income between £0 and £200,000.

Hide code cell source
from policyengine_uk import Simulation

simulation = Simulation(
    situation=dict(
            people=dict(
            person=dict(
                age=30,
                dividend_income=10_000,
            )
        ),
        axes=[[
            dict(
                name="employment_income",
                min=0,
                max=200_000,
                count=1_000,
            )
        ]]
    ),
)

import plotly.express as px
import pandas as pd
from policyengine_core.charts import format_fig

df = pd.DataFrame({
    "Employment income": simulation.calculate("employment_income"),
    "Income tax": simulation.calculate("income_tax"),
    "Dividend income tax": simulation.calculate("dividend_income_tax"),
})

fig = px.line(
    df,
    x="Employment income",
    y=["Income tax", "Dividend income tax"],
    title="Income tax vs employment income",
    labels={
        "value": "Income tax (£)",
        "variable": "Tax type",
    },
)

format_fig(fig)