/*
 *                            COPYRIGHT
 *
 *  cschem - modular/flexible schematics editor - sch-rnd (executable)
 *  Copyright (C) 2020 Tibor 'Igor2' Palinkas
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Lesser General Public
 *  License as published by the Free Software Foundation; either
 *  version 2.1 of the License, or (at your option) any later version.*
 *
 *  This library is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *  Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public
 *  License along with this library; if not, write to the Free Software
 *  Foundation, Inc., 31 Milk Street, # 960789 Boston, MA 02196 USA
 *
 *  Contact:
 *    Project page: http://repo.hu/projects/sch-rnd
 *    contact lead developer: http://www.repo.hu/projects/sch-rnd/contact.html
 *    mailing list: http://www.repo.hu/projects/sch-rnd/contact.html
 */

#include <libcschem/concrete.h>

typedef struct csch_search_obj_first_s csch_search_obj_first_t;

/* Called for any input object, return non-zero to ignore object */
typedef int (*csch_search_obj_ignore_cb_t)(csch_search_obj_first_t *ctx, csch_chdr_t *obj);

csch_rtree_dir_t csch_search(csch_sheet_t *sheet, csch_rtree_box_t *query, csch_rtree_cb_t *found_obj, void *ctx);

/* Find object with highest click-priority in query box.
   Return group instead of the child object if group lock applies.
   The masked version narrows search to object types matching the mask.
   The filter version calls an user function for filtering out results. */
csch_chdr_t *csch_search_first_gui(csch_sheet_t *sheet, csch_rtree_box_t *query);
csch_chdr_t *csch_search_first_mask(csch_sheet_t *sheet, csch_rtree_box_t *query, csch_cmask_t mask);
csch_chdr_t *csch_search_first_gui_filter(csch_sheet_t *sheet, csch_rtree_box_t *query, csch_search_obj_ignore_cb_t ignore);

/* Same as csch_search_first_gui() but allows a few special cases, like
   picking non-floater terminals.
   The filter version calls an user function for filtering out results. */
csch_chdr_t *csch_search_first_gui_inspect(csch_sheet_t *sheet, csch_rtree_box_t *query);
csch_chdr_t *csch_search_first_gui_inspect_filter(csch_sheet_t *sheet, csch_rtree_box_t *query, csch_search_obj_ignore_cb_t ignore);

/* Same as csch_search_first() and csch_search_first_gui(), except these
   will find the first locked object. Useful for implementing the lock tool. */
csch_chdr_t *csch_search_first_locked(csch_sheet_t *sheet, csch_rtree_box_t *query);
csch_chdr_t *csch_search_first_locked_gui(csch_sheet_t *sheet, csch_rtree_box_t *query);

/* List all objects that are selected under src group; if src is NULL, list
   under sheet. Listing means appending object ptr to dst. If recursive is
   non-zero, recurse to group objects */
long csch_search_all_selected(csch_sheet_t *sheet, csch_cgrp_t *src, vtp0_t *dst, int recursive);



/*** Low level API ***/


struct csch_search_obj_first_s {
	csch_chdr_t *res;
	long score;
	csch_rtree_box_t *query;
	csch_search_obj_ignore_cb_t ignore;/* if not NULL: called for any input object, return non-zero to ignore object */
	csch_cmask_t mask;                 /* if not 0, ignore objects not matching this mask */
	unsigned explicitly_locked_only:1; /* if 1, search only explicitly locked objects */
	unsigned ignore_wirenet_grp:1;     /* if 1, do not return wirenet groups (i.e. when clicked at empty space within bbox) */
	unsigned allow_term:1;             /* when 1, allow picking up terminals bypassing symbol lock */

	void *user_ctx;
};

csch_rtree_dir_t csch_search_obj_first_cb(void *ctx_, void *obj_, const csch_rtree_box_t *box);
