Titanium JIRA Archive
Titanium SDK/CLI (TIMOB)

[TIMOB-15932] iOS: Editable TableView loses correct index when using swipe-delete gesture then .deleteRow()

GitHub Issuen/a
TypeBug
PriorityHigh
StatusClosed
ResolutionFixed
Resolution Date2014-02-05T18:18:04.000+0000
Affected Version/sn/a
Fix Version/s2014 Sprint 03, 2014 Sprint 03 API, Release 3.3.0
ComponentsiOS
LabelsdeleteRow, editable, index, ios, module_tableview, qe-closed-3.3.0, qe-testadded, swipe, tableview, triage
ReporterEric Wieber
AssigneeSabil Rahim
Created2013-11-28T08:19:11.000+0000
Updated2014-08-01T04:31:07.000+0000

Description

The following tableview displays 20 numbered rows. The tableview is set as "editable:true", so the swipe-to-delete gesture is enabled in iOS. The tableview also has a click event handler, so any row clicked on, will be deleted as well with the TableView.deleteRow() method. The idea is that a user can swipe-to-delete any row, or simply click any row to delete it. Problem: Swipe-deleting a row, then calling .deleteRow() on a later row causes the display to remove the incorrect row. Seems like Swipe-to-delete is causing an indexing problem with the rows. For example; 1. Load the app. 2. Click on "Row 1" to delete it. This works fine. 3. Swipe-to-delete "Row 2" and delete it. This works fine. 3. Click on "Row 3" to delete it. This fails, and "Row 4" gets deleted instead of "Row 3". Anytime you swipe-delete a row, any other rows below that one which are deleted with TableView.deleteRow() miss the correct index, instead deleting something farther below their index. The more swipe-deletes you do, the more the index is offset incorrectly when calling .deleteRow(). Using $.tv.deleteRow(e.index) or $.tv.deleteRow(e.row) does not make a difference. Here's the code: index.xml:
<Alloy>
  <NavigationWindow>
    <Window>
      <TableView id="tv" editable="true" onClick="tv_onClick">	
      </TableView>
    </Window>
  </NavigationWindow>
</Alloy>	
index.js:
var tableData = [];

for (var i=1; i<21; i++) {
  tableData.push({ title: 'Row ' + i });
}

$.tv.setData(tableData);
$.index.open();

function tv_onClick(e) {	
  $.tv.deleteRow(e.index);
}

Comments

  1. Ed 2013-12-09

    I see this has been assigned to Alloy, but this is not an Alloy issue. The same problem can be reproduced under Classic Ti. Create a new classic project, with the 'Single Window Application' template, and replace the code in /common/FirstView.js for the code below. Test deleting by swiping and clicking as shown above.
       //FirstView Component Constructor
       function FirstView() {
       	//create object instance, a parasitic subclass of Observable
       	var self = Ti.UI.createView();
       	
       	var tv = Ti.UI.createTableView({
       		editable: true
       	});
       	
       	self.add(tv);
       	
       	tv.addEventListener('click', function(e) {
       		tv.deleteRow(e.index);
       	});
       	
       	var tableData = [];
        
       	for (var i=1; i<21; i++) {
         		tableData.push({ title: 'Row ' + i });
       	}
        
       	tv.setData(tableData);
       	
       	return self;
       }
       
       module.exports = FirstView;
       
  2. Ed 2014-02-04

    I know this has not been fixed, but any timeline for a fix or a workaround? This bug breaks the tableview functionality.
  3. Sabil Rahim 2014-02-04

    master PR : https://github.com/appcelerator/titanium_mobile/pull/5319
  4. Vishal Duggal 2014-02-05

    CR + FR
  5. Neha Mittal 2014-04-28

    Verified fix with below environment: Appc Studio: 3.3.0.201404251359 SDK build: 3.3.0.v20140425191906 acs: 1.0.14 npm: 1.3.2 alloy: 1.4.0-dev CLI: titanium-3.3.0-dev titanium-code-processor:1.1.1-beta1 Xcode: 5.1.1 Osx: Mavericks(10.9.2) Device: iPhone 5 (7.1) Now swipe-to-delete is causing correct indexing with the rows. Verified with the alloy code provided in the description. Hence closing the issue.

JSON Source