// The following function assumes that the set of selectable objects
// all rectangles.
void ConnectivityHistCanvas::UpdateSelection(bool shiftdown, bool pointsel)
{
    bool rect_sel = (!pointsel && (brushtype == rectangle));

    std::vector<bool>& hs = highlight_state->GetHighlight();
    std::vector<int>& nh = highlight_state->GetNewlyHighlighted();
    std::vector<int>& nuh = highlight_state->GetNewlyUnhighlighted();
    int total_newly_selected = 0;
    int total_newly_unselected = 0;

    int total_sel_shps = selectable_shps.size();

    wxPoint lower_left;
    wxPoint upper_right;
    if (rect_sel) {
        GenUtils::StandardizeRect(sel1, sel2, lower_left, upper_right);
    }
    if (!shiftdown) {
        bool any_selected = false;
        for (int i=0; i<total_sel_shps; i++) {
            GdaRectangle* rec = (GdaRectangle*) selectable_shps[i];
            if ((pointsel && rec->pointWithin(sel1)) ||
                    (rect_sel &&
                     GenUtils::RectsIntersect(rec->lower_left, rec->upper_right,
                                              lower_left, upper_right))) {
                //LOG_MSG(wxString::Format("ival %d selected", i));
                any_selected = true;
                break;
            } else {
                //LOG_MSG(wxString::Format("ival %d not selected", i));
                //LOG_MSG(wxString::Format(""));
            }
        }
        if (!any_selected) {
            highlight_state->SetEventType(HighlightState::unhighlight_all);
            highlight_state->notifyObservers();
            return;
        }
    }

    for (int i=0; i<total_sel_shps; i++) {
        GdaRectangle* rec = (GdaRectangle*) selectable_shps[i];
        bool selected = ((pointsel && rec->pointWithin(sel1)) ||
                         (rect_sel &&
                          GenUtils::RectsIntersect(rec->lower_left,
                                  rec->upper_right,
                                  lower_left, upper_right)));
        bool all_sel = (ival_obs_cnt[i] == ival_obs_sel_cnt[i]);
        if (pointsel && all_sel && selected) {
            // unselect all in ival
            for (std::list<int>::iterator it=ival_to_obs_ids[i].begin();
                    it != ival_to_obs_ids[i].end(); it++) {
                nuh[total_newly_unselected++] = (*it);
            }
        } else if (!all_sel && selected) {
            // select currently unselected in ival
            for (std::list<int>::iterator it=ival_to_obs_ids[i].begin();
                    it != ival_to_obs_ids[i].end(); it++) {
                if (hs[*it]) continue;
                nh[total_newly_selected++] = (*it);
            }
        } else if (!selected && !shiftdown) {
            // unselect all selected in ival
            for (std::list<int>::iterator it=ival_to_obs_ids[i].begin();
                    it != ival_to_obs_ids[i].end(); it++) {
                if (!hs[*it]) continue;
                nuh[total_newly_unselected++] = (*it);
            }
        }
    }

    if (total_newly_selected > 0 || total_newly_unselected > 0) {
        highlight_state->SetTotalNewlyHighlighted(total_newly_selected);
        highlight_state->SetTotalNewlyUnhighlighted(total_newly_unselected);
        NotifyObservables();
    }
    UpdateStatusBar();
}
// The following function assumes that the set of selectable objects
// are all rectangles.
void ConditionalHistogramCanvas::UpdateSelection(bool shiftdown, bool pointsel)
{
	bool rect_sel = (!pointsel && (brushtype == rectangle));
	
	int t = var_info[HIST_VAR].time;
	std::vector<bool>& hs = highlight_state->GetHighlight();
    bool selection_changed = false;
	
	int total_sel_shps = selectable_shps.size();
	
	wxPoint lower_left;
	wxPoint upper_right;
	if (rect_sel) {
		GenGeomAlgs::StandardizeRect(sel1, sel2, lower_left, upper_right);
	}
	if (!shiftdown) {
		bool any_selected = false;
		for (int i=0; i<total_sel_shps; i++) {
			GdaRectangle* rec = (GdaRectangle*) selectable_shps[i];
			if ((pointsel && rec->pointWithin(sel1)) ||
				(rect_sel &&
				 GenGeomAlgs::RectsIntersect(rec->lower_left, rec->upper_right,
										  lower_left, upper_right)))
			{
				any_selected = true;
				break;
			}
		}
		if (!any_selected) {
			highlight_state->SetEventType(HLStateInt::unhighlight_all);
			highlight_state->notifyObservers();
			return;
		}
	}
	
	for (int i=0; i<total_sel_shps; i++) {
		int r, c, ival;
		sel_shp_to_cell(i, r, c, ival);
		GdaRectangle* rec = (GdaRectangle*) selectable_shps[i];
		bool selected = ((pointsel && rec->pointWithin(sel1)) ||
						 (rect_sel &&
						  GenGeomAlgs::RectsIntersect(rec->lower_left,
												   rec->upper_right,
												   lower_left, upper_right)));
		bool all_sel = (cell_data[t][r][c].ival_obs_cnt[ival] == 
						cell_data[t][r][c].ival_obs_sel_cnt[ival]);
		if (pointsel && all_sel && selected) {
			// unselect all in ival
			for (std::list<int>::iterator it =
					cell_data[t][r][c].ival_to_obs_ids[ival].begin();
				 it != cell_data[t][r][c].ival_to_obs_ids[ival].end(); it++) {
                hs[(*it)]= false;
                selection_changed = true;
			}
		} else if (!all_sel && selected) {
			// select currently unselected in ival
			for (std::list<int>::iterator it =
					cell_data[t][r][c].ival_to_obs_ids[ival].begin();
				 it != cell_data[t][r][c].ival_to_obs_ids[ival].end(); it++) {
				if (hs[*it]) continue;
                hs[(*it)]= true;
                selection_changed = true;
			}
		} else if (!selected && !shiftdown) {
			// unselect all selected in ival
			for (std::list<int>::iterator it =
					cell_data[t][r][c].ival_to_obs_ids[ival].begin();
				 it != cell_data[t][r][c].ival_to_obs_ids[ival].end(); it++) {
				if (!hs[*it]) continue;
                hs[(*it)]= false;
                selection_changed = true;
			}
		}
	}
	
	if ( selection_changed ) {
		highlight_state->SetEventType(HLStateInt::delta);
		highlight_state->notifyObservers();
	}
	UpdateStatusBar();
}