*** First of all, see which column fired off this event AEVENTS( laEvents, 0 ) loHeader = laEvents[ 1 ] IF VARTYPE( loHeader ) = 'O' *** First See if a ControlsSource was set for the column WITH loHeader.Parent lcField = '' IF NOT EMPTY( .ControlSource ) *** Cool. Use it to decide how to sort the grid IF NOT EMPTY( .ControlSource ) AND ( '.' $ .ControlSource ) AND NOT( '(' $ .ControlSource ) AND TYPE( This.RecordSource + [.] + lcField ) # [M] lcField = JUSTEXT( .ControlSource ) ENDIF ENDIF ENDWITH *** if we have a field - let's sort IF NOT EMPTY( lcField ) *********************************************************************** *** we have a field - let's see if it already has a sort order set *** if it does, it will have the appropriate picture in the header lcSortOrder = '' IF NOT EMPTY( loHeader.Picture ) lcSortOrder = IIF( LOWER( JUSTFNAME( loHeader.Picture ) ) == 'down.bmp', '', 'DESC' ) ELSE *** See if there is a visual cue on any of the other grid *** column headers and remove it if there is FOR EACH loColumn IN This.Columns FOR EACH loControl IN loColumn.Controls IF LOWER( loControl.BaseClass ) == [header] IF NOT EMPTY( loControl.Picture ) llFoundColumn = .T. loControl.Picture = [] loControl.FontBold = .F. EXIT ENDIF ENDIF ENDFOR IF llFoundColumn EXIT ENDIF ENDFOR ENDIF lcFrom = This.RecordSource + [ ORDER BY ] + This.cSortField + [ ] + This.cSortOrder + [ INTO CURSOR qTmp NOFILTER] SELECT * FROM &lcFrom SELECT ( This.RecordSource ) lnBuffering = CURSORGETPROP( "Buffering" ) IF lnBuffering > 3 TABLEUPDATE( 1, .F., This.RecordSource ) CURSORSETPROP( "Buffering", 3, This.RecordSource ) ENDIF ZAP APPEND FROM DBF( 'qTmp' ) GO TOP IN ( This.RecordSource ) CURSORSETPROP( "Buffering", lnBuffering, This.RecordSource ) USE IN qTmp This.Refresh() This.SetFocus() *** And set the visual cues on the header loHeader.Picture = IIF( EMPTY( lcSortOrder ), [..\graphics\up.bmp], [..\graphics\down.bmp] ) loHeader.FontBold = .T. ENDIF ENDIF