home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / x / volume19 / xfig / part05 / e_deletept.c < prev    next >
Encoding:
C/C++ Source or Header  |  1993-05-27  |  5.9 KB  |  203 lines

  1. /*
  2.  * FIG : Facility for Interactive Generation of figures
  3.  * Copyright (c) 1985 by Supoj Sutanthavibul
  4.  *
  5.  * "Permission to use, copy, modify, distribute, and sell this software and its
  6.  * documentation for any purpose is hereby granted without fee, provided that
  7.  * the above copyright notice appear in all copies and that both the copyright
  8.  * notice and this permission notice appear in supporting documentation. 
  9.  * No representations are made about the suitability of this software for 
  10.  * any purpose.  It is provided "as is" without express or implied warranty."
  11.  */
  12.  
  13. #include "fig.h"
  14. #include "resources.h"
  15. #include "mode.h"
  16. #include "object.h"
  17. #include "paintop.h"
  18. #include "u_search.h"
  19. #include "w_canvas.h"
  20. #include "w_mousefun.h"
  21.  
  22. static int    init_delete_point();
  23.  
  24. delete_point_selected()
  25. {
  26.     set_mousefun("delete point", "", "");
  27.     canvas_kbd_proc = null_proc;
  28.     canvas_locmove_proc = null_proc;
  29.     init_searchproc_left(init_delete_point);
  30.     canvas_leftbut_proc = point_search_left;
  31.     canvas_middlebut_proc = null_proc;
  32.     canvas_rightbut_proc = null_proc;
  33.     set_cursor(pick9_cursor);
  34. }
  35.  
  36. static
  37. init_delete_point(obj, type, x, y, p, q)
  38.     char       *obj;
  39.     int            type, x, y;
  40.     F_point       *p, *q;
  41. {
  42.     int            n;
  43.  
  44.     switch (type) {
  45.     case O_POLYLINE:
  46.     cur_l = (F_line *) obj;
  47.     /* the search routine will ensure we don't have a box */
  48.     n = num_points(cur_l->points);
  49.     if (cur_l->type == T_POLYGON) {
  50.         if (n <= 4) {    /* count first pt twice for closed object */
  51.         put_msg("A polygon cannot have less than 3 points");
  52.         return;
  53.         }
  54.     } else if (n <= 1) {
  55.         /* alternative would be to remove the dot altogether */
  56.         put_msg("A dot must have at least 1 point");
  57.         return;
  58.     }
  59.     linepoint_deleting(cur_l, p, q);
  60.     break;
  61.     case O_SPLINE:
  62.     cur_s = (F_spline *) obj;
  63.     n = num_points(cur_s->points);
  64.     if (closed_spline(cur_s)) {
  65.         if (n <= 4) {    /* count first pt twice for closed object */
  66.         put_msg("A closed spline cannot have less than 3 points");
  67.         return;
  68.         }
  69.     } else if (normal_spline(cur_s)) {
  70.         if (n <= 2) {
  71.         put_msg("A spline cannot have less than 2 points");
  72.         return;
  73.         }
  74.     } else if (n <= 3) {    /* it must be an open interpolated spline */
  75.         put_msg("An interpolated spline cannot have less than 3 points");
  76.         return;
  77.     }
  78.     splinepoint_deleting(cur_s, p, q);
  79.     break;
  80.     default:
  81.     return;
  82.     }
  83. }
  84.  
  85. /**************************  spline  *******************************/
  86.  
  87. splinepoint_deleting(spline, prev_point, selected_point)
  88.     F_spline       *spline;
  89.     F_point       *prev_point, *selected_point;
  90. {
  91.     F_point       *p, *next_point;
  92.  
  93.     next_point = selected_point->next;
  94.     set_temp_cursor(wait_cursor);
  95.     if (closed_spline(spline)) {
  96.     mask_toggle_splinemarker(spline);
  97.     draw_spline(spline, ERASE);    /* erase the spline */
  98.     if (prev_point == NULL) {
  99.         /* The deleted point is the first point */
  100.         spline->points = next_point;
  101.         for (prev_point = next_point, p = prev_point->next;
  102.          p->next != NULL;
  103.          prev_point = p, p = p->next);
  104.         /*
  105.          * prev_point now points at next to last point (the last point is
  106.          * a copy of the first).
  107.          */
  108.         p->x = spline->points->x;
  109.         p->y = spline->points->y;
  110.         next_point = p;
  111.         /*
  112.          * next_point becomes the last point.  If this operation (point
  113.          * deletion) is reversed (undo), the selected_point will not be
  114.          * inserted into it original place, but will be between
  115.          * prev_point and next_point.
  116.          */
  117.     } else
  118.         prev_point->next = next_point;
  119.     } else {            /* open spline */
  120.     mask_toggle_splinemarker(spline);
  121.     draw_spline(spline, ERASE);    /* erase the spline */
  122.     if (prev_point == NULL)
  123.         spline->points = next_point;
  124.     else
  125.         prev_point->next = next_point;
  126.     }
  127.     if (int_spline(spline)) {
  128.     F_control      *c;
  129.  
  130.     c = spline->controls;
  131.     spline->controls = c->next;
  132.     c->next = NULL;
  133.     free((char *) c);
  134.     remake_control_points(spline);
  135.     }
  136.     draw_spline(spline, PAINT);
  137.     mask_toggle_splinemarker(spline);
  138.     clean_up();
  139.     set_action_object(F_DELETE_POINT, O_SPLINE);
  140.     set_latestspline(spline);
  141.     set_last_prevpoint(prev_point);
  142.     set_last_selectedpoint(selected_point);
  143.     set_last_nextpoint(next_point);
  144.     set_modifiedflag();
  145.     reset_cursor();
  146. }
  147.  
  148. /***************************  line  ********************************/
  149.  
  150. /*
  151.  * In deleting a point selected_point, linepoint_deleting uses prev_point and
  152.  * next_point of the point. The relationship between the three points is:
  153.  * prev_point->selected_point->next_point except when selected_point is the
  154.  * first point in the list, in which case prev_point will be NULL.
  155.  */
  156. linepoint_deleting(line, prev_point, selected_point)
  157.     F_line       *line;
  158.     F_point       *prev_point, *selected_point;
  159. {
  160.     F_point       *p, *next_point;
  161.  
  162.     next_point = selected_point->next;
  163.     mask_toggle_linemarker(line);
  164.     draw_line(line, ERASE);    /* erase the line */
  165.     if (line->type == T_POLYGON) {
  166.     if (prev_point == NULL) {
  167.         /* The deleted point is the first point */
  168.         line->points = next_point;
  169.         for (prev_point = next_point, p = prev_point->next;
  170.          p->next != NULL;
  171.          prev_point = p, p = p->next);
  172.         /*
  173.          * prev_point now points at next to last point (the last point is
  174.          * a copy of the first).
  175.          */
  176.         p->x = next_point->x;
  177.         p->y = next_point->y;
  178.         next_point = p;
  179.         /*
  180.          * next_point becomes the last point.  If this operation (point
  181.          * deletion) is reversed (undo), the selected_point will not be
  182.          * inserted into it original place, but will be between
  183.          * prev_point and next_point.
  184.          */
  185.     } else
  186.         prev_point->next = next_point;
  187.     } else {            /* polyline */
  188.     if (prev_point == NULL)
  189.         line->points = next_point;
  190.     else
  191.         prev_point->next = next_point;
  192.     }
  193.     draw_line(line, PAINT);
  194.     mask_toggle_linemarker(line);
  195.     clean_up();
  196.     set_modifiedflag();
  197.     set_action_object(F_DELETE_POINT, O_POLYLINE);
  198.     set_latestline(line);
  199.     set_last_prevpoint(prev_point);
  200.     set_last_selectedpoint(selected_point);
  201.     set_last_nextpoint(next_point);
  202. }
  203.