[gnumeric] new cmd_area_set_array_expr (with cmd_generic at its core)



commit eca0dca572eb1c149374e13004b02b5593b1fde0
Author: Andreas J Guelzow <aguelzow pyrshep ca>
Date:   Sun Jun 27 18:03:05 2010 -0600

    new cmd_area_set_array_expr (with cmd_generic at its core)
    
    2010-06-27  Andreas J. Guelzow <aguelzow pyrshep ca>
    
    	* src/cell.h (gnm_cell_set_array_formula_undo): new
    	* src/cell.c (gnm_cell_set_array_formula_undo): new
    	(gnm_cell_set_array_formula_cb): new
    	* src/commands.h (cmd_cell_range_is_locked_effective): new
    	(cmd_selection_is_locked_effective): new
    	(cmd_area_set_array_expr): new
    	* src/commands.c (cmd_cell_range_is_locked_effective): publish
    	(cmd_selection_is_locked_effective): publish
    	(cmd_area_set_array_expr): new
    	* src/wbc-gtk-edit.c (wbcg_edit_finish): check whether the range
    	  is locked; call cmd_area_set_array_expr when appropriate

 ChangeLog          |   14 +++++++++
 src/cell.c         |   24 ++++++++++++++++
 src/cell.h         |    2 +
 src/commands.c     |   46 +++++++++++++++++++++++++++++-
 src/commands.h     |   10 ++++++
 src/wbc-gtk-edit.c |   79 ++++++++++++++++++++++++++++++++++++++++++----------
 6 files changed, 158 insertions(+), 17 deletions(-)
---
diff --git a/ChangeLog b/ChangeLog
index 50eca4b..b055fa7 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,17 @@
+2010-06-27  Andreas J. Guelzow <aguelzow pyrshep ca>
+
+	* src/cell.h (gnm_cell_set_array_formula_undo): new
+	* src/cell.c (gnm_cell_set_array_formula_undo): new
+	(gnm_cell_set_array_formula_cb): new
+	* src/commands.h (cmd_cell_range_is_locked_effective): new
+	(cmd_selection_is_locked_effective): new
+	(cmd_area_set_array_expr): new
+	* src/commands.c (cmd_cell_range_is_locked_effective): publish
+	(cmd_selection_is_locked_effective): publish
+	(cmd_area_set_array_expr): new
+	* src/wbc-gtk-edit.c (wbcg_edit_finish): check whether the range 
+	  is locked; call cmd_area_set_array_expr when appropriate
+	
 2010-06-25  Andreas J. Guelzow <aguelzow pyrshep ca>
 
 	* src/wbc-gtk-edit.c (wbcg_edit_finish): don't hide a varaible by 
diff --git a/src/cell.c b/src/cell.c
index 05f6bda..049d497 100644
--- a/src/cell.c
+++ b/src/cell.c
@@ -321,6 +321,30 @@ gnm_cell_set_array_formula (Sheet *sheet,
 	dependent_link (GNM_CELL_TO_DEP (corner));
 }
 
+static void
+gnm_cell_set_array_formula_cb (GnmSheetRange const *sr, GnmExprTop const  *texpr)
+{
+	sheet_region_queue_recalc (sr->sheet, &sr->range);
+	gnm_expr_top_ref (texpr);
+	gnm_cell_set_array_formula (sr->sheet,
+				    sr->range.start.col, sr->range.start.row, 
+				    sr->range.end.col,   sr->range.end.row,
+				    texpr);
+	sheet_region_queue_recalc (sr->sheet, &sr->range);
+	sheet_flag_status_update_range (sr->sheet, &sr->range);
+	sheet_queue_respan (sr->sheet, sr->range.start.row, sr->range.end.row);
+} 
+
+GOUndo *
+gnm_cell_set_array_formula_undo (GnmSheetRange *sr, GnmExprTop const  *texpr)
+{
+	gnm_expr_top_ref (texpr);
+	return go_undo_binary_new (sr, (gpointer)texpr, 
+				   (GOUndoBinaryFunc) gnm_cell_set_array_formula_cb, 
+				   (GFreeFunc) gnm_sheet_range_free, 
+				   (GFreeFunc) gnm_expr_top_unref);
+}
+
 /***************************************************************************/
 
 /**
diff --git a/src/cell.h b/src/cell.h
index 7ebf8f3..426ea99 100644
--- a/src/cell.h
+++ b/src/cell.h
@@ -71,6 +71,8 @@ void gnm_cell_set_expr_unsafe	(GnmCell *cell, GnmExprTop const *texpr);
 void gnm_cell_set_array_formula	(Sheet *sheet,
 				 int cola, int rowa, int colb, int rowb,
 				 GnmExprTop const *texpr);
+GOUndo *gnm_cell_set_array_formula_undo (GnmSheetRange *sr, 
+					 GnmExprTop const  *texpr);
 void gnm_cell_cleanout		(GnmCell *cell);
 void gnm_cell_convert_expr_to_value	(GnmCell *cell);
 
diff --git a/src/commands.c b/src/commands.c
index cea0233..a2251c7 100644
--- a/src/commands.c
+++ b/src/commands.c
@@ -182,7 +182,7 @@ gnm_cmd_trunc_descriptor (GString *src, gboolean *truncated)
  * Do not use this function unless the sheet is part of the
  * workbook with the given wbc (otherwise the results may be strange)
  */
-static gboolean
+gboolean
 cmd_cell_range_is_locked_effective (Sheet *sheet, GnmRange *range,
 				    WorkbookControl *wbc, char const *cmd_name)
 {
@@ -239,7 +239,7 @@ cmd_dao_is_locked_effective (data_analysis_output_t  *dao,
  * workbook with the given wbcg (otherwise the results may be strange)
  *
  */
-static gboolean
+gboolean
 cmd_selection_is_locked_effective (Sheet *sheet, GSList *selection,
 				   WorkbookControl *wbc, char const *cmd_name)
 {
@@ -1141,6 +1141,48 @@ cmd_area_set_text (WorkbookControl *wbc, SheetView *sv,
 	return gnm_command_push_undo (wbc, G_OBJECT (me));
 }
 
+/*
+ * cmd_area_set_array_expr
+ *
+ * the caller is expected to have ensured:
+ *
+ * 1) that no array is being split
+ * 2) that the selection consists of a single range
+ * 3) that the range is not locked.
+ *
+ */
+
+gboolean
+cmd_area_set_array_expr (WorkbookControl *wbc, SheetView *sv,
+			 GnmExprTop const  *texpr)
+{
+	GSList	*selection = selection_get_ranges (sv, FALSE);
+	GOUndo *undo = NULL;
+	GOUndo *redo = NULL;
+	gboolean result;
+	Sheet *sheet = sv_sheet (sv);
+	char *name;
+	char *text;
+	GnmSheetRange *sr;
+	
+	g_return_val_if_fail (selection != NULL , TRUE);
+	g_return_val_if_fail (selection->next == NULL , TRUE);
+
+	name = undo_range_list_name (sheet, selection);
+	text = g_strdup_printf (_("Inserting array expression in \"%s\""), name);
+	g_free (name);
+
+	undo = clipboard_copy_range_undo (sheet, selection->data);
+
+	sr = gnm_sheet_range_new (sheet, selection->data);
+	redo = gnm_cell_set_array_formula_undo (sr, texpr);
+
+	range_fragment_free (selection);
+	result = cmd_generic (wbc, text, undo, redo);
+	g_free (text);
+	return result;
+}
+
 gboolean
 cmd_create_data_table (WorkbookControl *wbc, Sheet *sheet, GnmRange const *r,
 		       char const *col_input, char const *row_input)
diff --git a/src/commands.h b/src/commands.h
index f3371f2..80d15b6 100644
--- a/src/commands.h
+++ b/src/commands.h
@@ -16,6 +16,12 @@ void command_list_release	(GSList *cmds);
 /* utility functions */
 
 GString *gnm_cmd_trunc_descriptor (GString *src, gboolean *truncated);
+gboolean cmd_cell_range_is_locked_effective (Sheet *sheet, GnmRange *range,
+					     WorkbookControl *wbc, 
+					     char const *cmd_name);
+gboolean cmd_selection_is_locked_effective (Sheet *sheet, GSList *selection,
+					    WorkbookControl *wbc, 
+					    char const *cmd_name);
 
 /* Commands: note that any extensions should ideally use cmd_generic* */
 
@@ -31,6 +37,10 @@ gboolean cmd_set_text		(WorkbookControl *wbc, Sheet *sheet,
 
 gboolean cmd_area_set_text	(WorkbookControl *wbc, SheetView *sv,
 				 char const *text, gboolean as_array);
+
+gboolean cmd_area_set_array_expr (WorkbookControl *wbc, SheetView *sv,
+				  GnmExprTop const  *new_texpr);
+
 gboolean cmd_create_data_table	(WorkbookControl *wbc,
 				 Sheet *sheet, GnmRange const *r,
 				 char const *col_input, char const *row_input);
diff --git a/src/wbc-gtk-edit.c b/src/wbc-gtk-edit.c
index 7a722d8..32609a0 100644
--- a/src/wbc-gtk-edit.c
+++ b/src/wbc-gtk-edit.c
@@ -178,11 +178,43 @@ wbcg_edit_finish (WBCGtk *wbcg, WBCEditResult result,
 			break;
 		}
 
+
+		/******* Check whether the range is locked ********/
+		
+		switch (result) {
+		case (WBC_EDIT_ACCEPT_RANGE):
+		case (WBC_EDIT_ACCEPT_ARRAY): {
+			if (cmd_selection_is_locked_effective (sheet, selection, wbc,
+							       _("Set Text"))) {
+				range_fragment_free (selection);
+				*showed_dialog = TRUE;
+				return FALSE;
+			}
+			break;
+		}
+		case (WBC_EDIT_ACCEPT): {
+			GnmRange r;
+			r.end = r.start = pp.eval;
+
+			if (cmd_selection_is_locked_effective (sheet, selection, wbc,
+							       _("Set Text"))) {
+				range_fragment_free (selection);
+				*showed_dialog = TRUE;
+				return FALSE;
+			}
+			break;
+		}
+		case (WBC_EDIT_REJECT):
+		default:
+			/* We should not be able to get here! */
+			break;
+		}
 		/*****************************************************/
 
 		txt = wbcg_edit_get_display_text (wbcg);
 		mstyle = sheet_style_get (sheet, sv->edit_pos.col, sv->edit_pos.row);
-		fmt = gnm_cell_get_format (sheet_cell_fetch (sheet, sv->edit_pos.col, sv->edit_pos.row));
+		fmt = gnm_cell_get_format (sheet_cell_fetch (sheet, sv->edit_pos.col,
+							     sv->edit_pos.row));
 
 		value = format_match (txt, fmt,
 				      workbook_date_conv (sheet->workbook));
@@ -267,11 +299,19 @@ wbcg_edit_finish (WBCGtk *wbcg, WBCEditResult result,
 
 		if (result == WBC_EDIT_ACCEPT_ARRAY) {
 			if (expr_txt == NULL ||
-			    selection == NULL || selection->next != NULL ||
-			    (texpr = gnm_expr_parse_str
-			     (expr_txt, &pp, GNM_EXPR_PARSE_DEFAULT,
-			      sheet_get_conventions (sheet), NULL)) == NULL)
-				result = WBC_EDIT_ACCEPT_RANGE;	
+			    selection == NULL || selection->next != NULL)
+				result = WBC_EDIT_ACCEPT_RANGE;
+			else {
+				GnmParsePos    pp_array;
+				GnmRange *r = selection->data;
+				
+				parse_pos_init (&pp_array, sheet->workbook, sheet, r->start.col, r->start.row);
+					
+				if ((texpr = gnm_expr_parse_str
+				     (expr_txt, &pp_array, GNM_EXPR_PARSE_DEFAULT,
+				      sheet_get_conventions (sheet), NULL)) == NULL)
+					result = WBC_EDIT_ACCEPT_RANGE;	
+			}
 		}
 
 		/* We need to save the information that we will temporarily overwrite */
@@ -302,6 +342,7 @@ wbcg_edit_finish (WBCGtk *wbcg, WBCEditResult result,
 
 			u = go_undo_combine (u,  clipboard_copy_range_undo (sheet, r));
 			if (texpr) {
+				gnm_expr_top_ref (texpr); 
 				gnm_cell_set_array_formula (sheet,
 							    r->start.col, r->start.row,
 							    r->end.col, r->end.row,
@@ -347,19 +388,27 @@ wbcg_edit_finish (WBCGtk *wbcg, WBCEditResult result,
 				gtk_window_set_focus (wbcg_toplevel (wbcg),
 					(GtkWidget *) wbcg_get_entry (wbcg));
 				g_free (free_txt);
+				if (texpr != NULL)
+					gnm_expr_top_unref (texpr); 
 				return FALSE;
 			}
 		} else {
-			if (result == WBC_EDIT_ACCEPT) {
-				PangoAttrList *res_markup = wbcg->edit_line.markup
-					? pango_attr_list_copy (wbcg->edit_line.markup)
-					: NULL;
-				cmd_set_text (wbc, sheet, &sv->edit_pos, txt, res_markup);
-				if (res_markup) pango_attr_list_unref (res_markup);
-			} else
-				cmd_area_set_text (wbc, sv, txt,
-						   result == WBC_EDIT_ACCEPT_ARRAY);
+			if (result == WBC_EDIT_ACCEPT_ARRAY) {
+				cmd_area_set_array_expr (wbc, sv, texpr);
+
+			} else {
+				if (result == WBC_EDIT_ACCEPT) {
+					PangoAttrList *res_markup = wbcg->edit_line.markup
+						? pango_attr_list_copy (wbcg->edit_line.markup)
+						: NULL;
+					cmd_set_text (wbc, sheet, &sv->edit_pos, txt, res_markup);
+					if (res_markup) pango_attr_list_unref (res_markup);
+				} else
+					cmd_area_set_text (wbc, sv, txt, FALSE);
+			}
 		}
+		if (texpr != NULL)
+			gnm_expr_top_unref (texpr); 
 		g_free (free_txt);
 	} else {
 		if (sv == wb_control_cur_sheet_view (wbc)) {



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]