Select and Delete DataFrame Rows from Tkinter Treeview

This project extends our Tkinter DataFrame search tutorial. After filtering a Pandas DataFrame and displaying the matching records in Treeview, the user can select one result, display its values and delete that exact row from the working DataFrame.

Selecting a filtered Pandas DataFrame row in Tkinter Treeview

The application keeps a connection between every displayed Treeview item and the corresponding row in the source DataFrame. This is more reliable than assuming the first DataFrame column contains a unique ID.

Source DataFrame
       |
       v
Search / Filter
       |
       v
Filtered DataFrame
       |
       v
Treeview
       |
       v
Select row
       |
       v
Source DataFrame index
       |
       v
Delete row
       |
       v
Run search again
       |
       v
Updated Treeview
Deletion note: deleting a row changes the DataFrame held in memory. It does not automatically delete the row from the original Excel or CSV file.

The search logic comes from Part I of the DataFrame search project.

A numeric query can perform an exact comparison against the id column:

if query.isdigit() and 'id' in df.columns:
    id_values=pd.to_numeric(
        df['id'],
        errors='coerce'
    )
    filtered_df=df[
        id_values==int(query)
    ].copy()

Text searches use case-insensitive matching:

names=df['name'].fillna('').astype(str)

mask=names.str.contains(
    word,
    case=False,
    na=False,
    regex=False
)

Multiple search words are combined with a Boolean mask rather than repeatedly appending or concatenating DataFrames.

Display Filtered Results in Treeview Top ↑

The Treeview is created once when the application starts.

Whenever the search changes, only its rows are replaced:

for item in tree.get_children():
    tree.delete(item)

The filtered DataFrame is then inserted again.

This is better than creating another Treeview every time the user presses a key or deletes a row.

Map Treeview Items to Source DataFrame Rows Top ↑

The older application used the first value of a row as the Treeview item ID:

iid=v[0]

and later assumed that value was the DataFrame id.

This can fail when:

  • the first column is not an ID;
  • the ID is text rather than numeric;
  • duplicate first-column values exist;
  • the selected file has a completely different structure.

The revised application creates its own Treeview item IDs and stores a mapping to the actual source DataFrame index:

row_map={}

for display_no,(source_index,row) in enumerate(
    filtered_df.iterrows()
):
    iid=f'row_{display_no}'
    row_map[iid]=source_index

    tree.insert(
        '',
        tk.END,
        iid=iid,
        values=row.tolist()
    )

The Treeview ID and the business-data ID are now separate concepts.

Detect Treeview Row Selection Top ↑

The Treeview <<TreeviewSelect>> event runs a function whenever the selection changes:

tree.bind(
    '<<TreeviewSelect>>',
    collect_selection
)

The selected Treeview item is obtained with:

selection=tree.selection()

if not selection:
    return

selected_iid=selection[0]

This avoids assuming that a selection always exists.

Display Selected Row Details Top ↑

The row values can be read from the selected Treeview item:

values=tree.item(
    selected_iid,
    'values'
)

The program displays the values in a Label:

selected_var.set(
    'Selected: '+
    ' | '.join(
        map(
            str,
            values
        )
    )
)

The Delete Button remains disabled until a valid row has been selected.

Delete the Selected Row from the DataFrame Top ↑

Deleting selected Pandas DataFrame row from Tkinter Treeview

First use the Treeview item ID to find the source DataFrame index:

source_index=row_map.get(
    selected_iid
)

The selected row is then removed from the working source DataFrame using Pandas drop():

df=df.drop(
    index=source_index
).reset_index(
    drop=True
)

A confirmation dialog is shown before the deletion:

confirmed=messagebox.askyesno(
    'Delete row',
    'Delete the selected row from the working DataFrame?'
)

Why Delete from df Instead of Only filtered_df?

The older application deleted the selected row only from the filtered result:

df2.drop(...)

However, the next search rebuilt df2 from the original df. The deleted row could therefore return.

The revised flow is:

delete from df
     |
     v
run current search again
     |
     v
create new filtered_df
     |
     v
refresh Treeview

The row remains deleted throughout the current application session.

Refresh the Treeview after Deletion Top ↑

After deleting from the source DataFrame, call the search function again:

search_data()

If the current search still matches other rows, they remain visible. If the deleted row was the only match, the Treeview becomes empty and the result count becomes zero.

Save the Current Filtered Result Top ↑

The current filtered DataFrame can be saved using a Tkinter Save As dialog.

if file_path.lower().endswith(
    '.csv'
):
    filtered_df.to_csv(
        file_path,
        index=False
    )
else:
    filtered_df.to_excel(
        file_path,
        index=False
    )

This saves the records currently represented by the filtered DataFrame, including any in-memory deletion already made.

Copy the Current Result to Clipboard Top ↑

Pandas to_clipboard() copies the filtered DataFrame:

filtered_df.to_clipboard(
    index=False
)

A temporary message confirms the operation.

Add Treeview Scrollbars Top ↑

The original page added a vertical scrollbar when more than ten results were available. The revised application uses both directions.

y_scroll=ttk.Scrollbar(
    table_frame,
    orient='vertical',
    command=tree.yview
)

x_scroll=ttk.Scrollbar(
    table_frame,
    orient='horizontal',
    command=tree.xview
)

tree.configure(
    yscrollcommand=y_scroll.set,
    xscrollcommand=x_scroll.set
)

Complete Search, Select and Delete Application Top ↑

Video: Select and Delete a DataFrame Row Top ↑

Selecting and Deleting Row from DataFrame and Showing Result in Treeview

Why We Do Not Use the DataFrame ID as Treeview iid Top ↑

For the sample student data, the id column happens to contain unique values. That made code such as this appear to work:

trv.insert(
    '',
    'end',
    iid=v[0],
    values=v
)

However, Treeview is a display widget and the DataFrame may come from many different sources. The first column should not automatically become the widget's identity.

The revised version maintains:

Treeview iid
     |
     v
row_map
     |
     v
source DataFrame index

This lets the program delete the exact selected row regardless of the actual CSV or Excel column structure.

What Happens after a Row Is Deleted? Top ↑

Suppose the source DataFrame contains:

1  John Deo
2  Max Ruin
3  Arnold
4  Krish Star

A search for:

Max

displays one row. After selecting that row and clicking Delete Selected:

df
 |
 +-- John Deo
 +-- Arnold
 +-- Krish Star

The current search is run again and now finds zero matching records.

Clearing the search displays all remaining working DataFrame rows. The deleted Max row does not return.

The source Excel or CSV file is still unchanged. To create a new file containing the modified result, use the Save Result option.

Frequently Asked Questions Top ↑

Q1: How do I detect a selected Treeview row?

Bind <<TreeviewSelect>> to a function and use tree.selection() to get the currently selected Treeview item.

Q2: How are selected row values displayed?

Use tree.item(selected_iid, 'values') to read the values stored in the selected Treeview row.

Q3: Why not use the first DataFrame column as Treeview iid?

The first column may not be unique or may not be an ID. The revised application creates its own Treeview identifiers and maps them to DataFrame indexes.

Q4: Why delete the row from the source DataFrame instead of only the filtered DataFrame?

The filtered DataFrame is recreated whenever the search changes. Deleting from the source working DataFrame prevents the deleted row from returning during the same application session.

Q5: Does Delete Selected modify the original Excel or CSV file?

No. It modifies only the DataFrame in memory. The original file remains unchanged unless the user explicitly saves modified data to a file.

Q6: Why confirm before deleting?

A confirmation dialog prevents an accidental row-selection click followed by an unintended deletion.

Q7: Can the remaining search result be saved after deletion?

Yes. The current filtered DataFrame can be saved as Excel or CSV or copied to the clipboard.


DataFrame Search Select DataFrame Columns

Insert MySQL Row and Add to Treeview MySQL Records MySQL Pagination Delete MySQL Records

Tkinter Projects Tkinter Pandas Projects


Subscribe to our YouTube Channel here



plus2net.com







Python Video Tutorials
Python SQLite Video Tutorials
Python MySQL Video Tutorials
Python Tkinter Video Tutorials
We use cookies to improve your browsing experience. . Learn more
HTML MySQL PHP JavaScript ASP Photoshop Articles Contact us
©2000-2026   plus2net.com   All rights reserved worldwide Privacy Policy Disclaimer