443a1d0cdd374c7ed5ce6db609d4f8c4842586b0
[blender.git] / source / blender / editors / space_clip / clip_utils.c
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version. 
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * The Original Code is Copyright (C) 2011 Blender Foundation.
19  * All rights reserved.
20  *
21  *
22  * Contributor(s): Blender Foundation,
23  *                 Sergey Sharybin
24  *
25  * ***** END GPL LICENSE BLOCK *****
26  */
27
28 /** \file blender/editors/space_clip/clip_utils.c
29  *  \ingroup spclip
30  */
31
32 #include "DNA_object_types.h"   /* SELECT */
33
34 #include "MEM_guardedalloc.h"
35
36 #include "BLI_utildefines.h"
37 #include "BLI_math.h"
38 #include "BLI_listbase.h"
39
40 #include "BKE_context.h"
41 #include "BKE_movieclip.h"
42 #include "BKE_tracking.h"
43 #include "BKE_depsgraph.h"
44
45 #include "WM_api.h"
46 #include "WM_types.h"
47
48 #include "ED_screen.h"
49 #include "ED_clip.h"
50
51 #include "UI_interface.h"
52
53 #include "RNA_access.h"
54 #include "RNA_define.h"
55
56 #include "UI_view2d.h"
57
58 #include "clip_intern.h"        // own include
59
60 void clip_graph_tracking_values_iterate_track(SpaceClip *sc, MovieTrackingTrack *track, void *userdata,
61                         void (*func) (void *userdata, MovieTrackingTrack *track, MovieTrackingMarker *marker, int coord, float val),
62                         void (*segment_start) (void *userdata, MovieTrackingTrack *track, int coord),
63                         void (*segment_end) (void *userdata))
64 {
65         MovieClip *clip = ED_space_clip(sc);
66         int width, height, coord;
67
68         BKE_movieclip_get_size(clip, &sc->user, &width, &height);
69
70         for (coord = 0; coord < 2; coord++) {
71                 int i, open = FALSE, prevfra = 0;
72                 float prevval = 0.0f;
73
74                 for (i = 0; i < track->markersnr; i++) {
75                         MovieTrackingMarker *marker = &track->markers[i];
76                         float val;
77
78                         if (marker->flag & MARKER_DISABLED) {
79                                 if (open) {
80                                         if (segment_end)
81                                                 segment_end(userdata);
82
83                                         open = FALSE;
84                                 }
85
86                                 continue;
87                         }
88
89                         if (!open) {
90                                 if (segment_start)
91                                         segment_start(userdata, track, coord);
92
93                                 open = TRUE;
94                                 prevval = marker->pos[coord];
95                         }
96
97                         /* value is a pixels per frame speed */
98                         val = (marker->pos[coord] - prevval) * ((coord == 0) ? (width) : (height));
99                         val /= marker->framenr - prevfra;
100
101                         if (func)
102                                 func(userdata, track, marker, coord, val);
103
104                         prevval = marker->pos[coord];
105                         prevfra = marker->framenr;
106                 }
107
108                 if (open) {
109                         if (segment_end)
110                                 segment_end(userdata);
111                 }
112         }
113 }
114
115 void clip_graph_tracking_values_iterate(SpaceClip *sc, void *userdata,
116                         void (*func) (void *userdata, MovieTrackingTrack *track, MovieTrackingMarker *marker, int coord, float val),
117                         void (*segment_start) (void *userdata, MovieTrackingTrack *track, int coord),
118                         void (*segment_end) (void *userdata))
119 {
120         MovieClip *clip = ED_space_clip(sc);
121         MovieTracking *tracking = &clip->tracking;
122         ListBase *tracksbase = BKE_tracking_get_tracks(tracking);
123         MovieTrackingTrack *track;
124
125         track = tracksbase->first;
126         while (track) {
127                 if (TRACK_VIEW_SELECTED(sc, track)) {
128                         clip_graph_tracking_values_iterate_track(sc, track, userdata, func, segment_start, segment_end);
129                 }
130
131                 track = track->next;
132         }
133 }
134
135 void clip_graph_tracking_iterate(SpaceClip *sc, void *userdata,
136                         void (*func) (void *userdata, MovieTrackingMarker *marker))
137 {
138         MovieClip *clip = ED_space_clip(sc);
139         MovieTracking *tracking = &clip->tracking;
140         ListBase *tracksbase = BKE_tracking_get_tracks(tracking);
141         MovieTrackingTrack *track;
142
143         track = tracksbase->first;
144         while (track) {
145                 if (TRACK_VIEW_SELECTED(sc, track)) {
146                         int i;
147
148                         for (i = 0; i < track->markersnr; i++) {
149                                 MovieTrackingMarker *marker = &track->markers[i];
150
151                                 if (marker->flag & MARKER_DISABLED)
152                                         continue;
153
154                                 if (func)
155                                         func(userdata, marker);
156                         }
157                 }
158
159                 track = track->next;
160         }
161 }
162
163 void clip_delete_track(bContext *C, MovieClip *clip, ListBase *tracksbase, MovieTrackingTrack *track)
164 {
165         MovieTracking *tracking = &clip->tracking;
166         MovieTrackingStabilization *stab = &tracking->stabilization;
167         MovieTrackingTrack *act_track = BKE_tracking_active_track(tracking);
168
169         int has_bundle = FALSE, update_stab = FALSE;
170
171         if (track==act_track)
172                 tracking->act_track = NULL;
173
174         if (track == stab->rot_track) {
175                 stab->rot_track = NULL;
176
177                 update_stab = TRUE;
178         }
179
180         /* handle reconstruction display in 3d viewport */
181         if (track->flag & TRACK_HAS_BUNDLE)
182                 has_bundle = TRUE;
183
184         BKE_tracking_free_track(track);
185         BLI_freelinkN(tracksbase, track);
186
187         WM_event_add_notifier(C, NC_MOVIECLIP|NA_EDITED, clip);
188
189         if (update_stab) {
190                 tracking->stabilization.ok = FALSE;
191
192                 DAG_id_tag_update(&clip->id, 0);
193                 WM_event_add_notifier(C, NC_MOVIECLIP|ND_DISPLAY, clip);
194         }
195
196         if (has_bundle)
197                 WM_event_add_notifier(C, NC_SPACE|ND_SPACE_VIEW3D, NULL);
198 }
199
200 void clip_delete_marker(bContext *C, MovieClip *clip, ListBase *tracksbase, MovieTrackingTrack *track, MovieTrackingMarker *marker)
201 {
202         if (track->markersnr == 1) {
203                 clip_delete_track(C, clip, tracksbase, track);
204         }
205         else {
206                 BKE_tracking_delete_marker(track, marker->framenr);
207
208                 WM_event_add_notifier(C, NC_MOVIECLIP|NA_EDITED, clip);
209         }
210 }
211
212 void clip_view_center_to_point(SpaceClip *sc, float x, float y)
213 {
214         int width, height;
215         float aspx, aspy;
216
217         ED_space_clip_size(sc, &width, &height);
218         ED_space_clip_aspect(sc, &aspx, &aspy);
219
220         sc->xof = (x - 0.5f) * width * aspx;
221         sc->yof = (y - 0.5f) * height * aspy;
222 }