HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
namespaceEditor.h
Go to the documentation of this file.
1 //
2 // Copyright 2023 Pixar
3 //
4 // Licensed under the Apache License, Version 2.0 (the "Apache License")
5 // with the following modification; you may not use this file except in
6 // compliance with the Apache License and the following modification to it:
7 // Section 6. Trademarks. is deleted and replaced with:
8 //
9 // 6. Trademarks. This License does not grant permission to use the trade
10 // names, trademarks, service marks, or product names of the Licensor
11 // and its affiliates, except as required to comply with Section 4(c) of
12 // the License and to reproduce the content of the NOTICE file.
13 //
14 // You may obtain a copy of the Apache License at
15 //
16 // http://www.apache.org/licenses/LICENSE-2.0
17 //
18 // Unless required by applicable law or agreed to in writing, software
19 // distributed under the Apache License with the above modification is
20 // distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
21 // KIND, either express or implied. See the Apache License for the specific
22 // language governing permissions and limitations under the Apache License.
23 //
24 #ifndef PXR_USD_USD_NAMESPACE_EDITOR_H
25 #define PXR_USD_USD_NAMESPACE_EDITOR_H
26 
27 /// \file usd/namespaceEditor.h
28 
29 #include "pxr/pxr.h"
30 #include "pxr/usd/usd/api.h"
31 #include "pxr/usd/usd/common.h"
32 #include "pxr/usd/usd/stage.h"
34 
35 
37 
38 /// @warning
39 /// This code is a work in progress and should not be used in production
40 /// scenarios. It is currently not feature-complete and subject to change.
41 ///
42 /// Provides namespace editing operations
44 {
45 public:
46  USD_API
47  explicit UsdNamespaceEditor(const UsdStageRefPtr &stage);
48 
49  /// Adds an edit operation to delete the composed prim at the given \p path
50  /// from this namespace editor's stage.
51  ///
52  /// Returns true if the path is a valid possible composed prim path; returns
53  /// false and emits a coding error if not.
54  USD_API
55  bool DeletePrimAtPath(
56  const SdfPath &path);
57 
58  /// Adds an edit operation to move the composed prim at the given \p path
59  /// on this namespace editor's stage to instead be at the path \p newPath.
60  ///
61  /// Returns true if both paths are valid possible composed prim path;
62  /// returns false and emits a coding error if not.
63  USD_API
64  bool MovePrimAtPath(
65  const SdfPath &path,
66  const SdfPath &newPath);
67 
68  /// Adds an edit operation to delete the composed prim at the path of
69  /// \p prim from this namespace editor's stage. This is equivalent to
70  /// calling DeletePrimAtPath(prim.GetPath())
71  ///
72  /// Returns true if the prim provides a valid possible composed prim path;
73  /// returns false and emits a coding error if not.
74  USD_API
75  bool DeletePrim(
76  const UsdPrim &prim);
77 
78  /// Adds an edit operation to rename the composed prim at the path of
79  /// \p prim on this namespace editor's stage to instead have the name
80  /// \p newName.
81  ///
82  /// Returns true if the prim provides a valid possible composed prim path
83  /// and the new name is a valid possible prim name; returns false and emits
84  /// a coding error if not.
85  USD_API
86  bool RenamePrim(
87  const UsdPrim &prim,
88  const TfToken &newName);
89 
90  /// Adds an edit operation to reparent the composed prim at the path of
91  /// \p prim on this namespace editor's stage to instead be a namespace
92  /// child of the composed prim at the path of \p newParent.
93  ///
94  /// Returns true if the both the prim and the new parent prim provide a
95  /// valid possible composed prim paths; returns false and emits a coding
96  /// error if not.
97  USD_API
98  bool ReparentPrim(
99  const UsdPrim &prim,
100  const UsdPrim &newParent);
101 
102  /// Adds an edit operation to reparent the composed prim at the path of
103  /// \p prim on this namespace editor's stage to instead be a prim named
104  /// \p newName that is a namespace child of the composed prim at the
105  /// path of \p newParent.
106  ///
107  /// Returns true if the both the prim and the new parent prim provide a
108  /// valid possible composed prim paths and the new name is a valid prim
109  /// name; returns false and emits a coding error if not.
110  USD_API
111  bool ReparentPrim(
112  const UsdPrim &prim,
113  const UsdPrim &newParent,
114  const TfToken &newName);
115 
116  /// Adds an edit operation to delete the composed property at the given
117  /// \p path from this namespace editor's stage.
118  ///
119  /// Returns true if the path is a valid possible composed property path;
120  /// returns false and emits a coding error if not.
121  USD_API
123  const SdfPath &path);
124 
125  /// Adds an edit operation to move the composed property at the given
126  /// \p path on this namespace editor's stage to instead be at the path
127  /// \p newPath.
128  ///
129  /// Returns true if both paths are valid possible composed property path;
130  /// returns false and emits a coding error if not.
131  USD_API
132  bool MovePropertyAtPath(
133  const SdfPath &path,
134  const SdfPath &newPath);
135 
136  /// Adds an edit operation to delete the composed property at the path of
137  /// \p property from this namespace editor's stage. This is equivalent to
138  /// calling DeletePropertyAtPath(property.GetPath())
139  ///
140  /// Returns true if the property provides a valid possible composed property
141  /// path; returns false and emits a coding error if not.
142  USD_API
143  bool DeleteProperty(
144  const UsdProperty &property);
145 
146  /// Adds an edit operation to rename the composed property at the path of
147  /// \p property on this namespace editor's stage to instead have the name
148  /// \p newName.
149  ///
150  /// Returns true if the property provides a valid possible composed property
151  /// path and the new name is a valid possible property name; returns false
152  /// and emits a coding error if not.
153  USD_API
154  bool RenameProperty(
155  const UsdProperty &property,
156  const TfToken &newName);
157 
158  /// Adds an edit operation to reparent the composed property at the path of
159  /// \p property on this namespace editor's stage to instead be a namespace
160  /// child of the composed property at the path of \p newParent.
161  ///
162  /// Returns true if the both the property and the new parent prim provide a
163  /// valid possible composed paths; returns false and emits a coding
164  /// error if not.
165  USD_API
166  bool ReparentProperty(
167  const UsdProperty &property,
168  const UsdPrim &newParent);
169 
170  /// Adds an edit operation to reparent the composed property at the path of
171  /// \p property on this namespace editor's stage to instead be a property
172  /// named \p newName that is a namespace child of the composed prim at the
173  /// path of \p newParent.
174  ///
175  /// Returns true if the both the property and the new parent prim provide a
176  /// valid possible composed paths and the new name is a valid property
177  /// name; returns false and emits a coding error if not.
178  USD_API
179  bool ReparentProperty(
180  const UsdProperty &property,
181  const UsdPrim &newParent,
182  const TfToken &newName);
183 
184  /// Applies all the added namespace edits stored in this to namespace editor
185  /// to its stage by authoring all scene description in the layer stack of
186  /// the current edit target necessary to move or delete the composed
187  /// objects that the edit paths refer to..
188  ///
189  /// Returns true if all the necessary edits are successfully performed;
190  /// returns false and emits a coding error otherwise.
191  USD_API
192  bool ApplyEdits();
193 
194  /// Returns whether all the added namespace edits stored in this to
195  /// namespace editor can be applied to its stage.
196  ///
197  /// In other words, this returns whether ApplyEdits should be successful if
198  /// it were called right now. If this would return false and \p whyNot is
199  /// provided, the reasons ApplyEdits would fail will be copied to whyNot.
200  USD_API
201  bool CanApplyEdits(std::string *whyNot = nullptr) const;
202 
203 private:
204 
205  // The type of edit that an edit description is describing.
206  enum class _EditType {
207  Invalid,
208 
209  Delete,
210  Rename,
211  Reparent
212  };
213 
214  // Description of an edit added to this namespace editor.
215  struct _EditDescription {
216  // Path to the existing object.
217  SdfPath oldPath;
218  // New path of the object after the edit is performed. An empty path
219  // indicates that the edit operation will delete the object.
220  SdfPath newPath;
221 
222  // Type of the edit as determined by the oldPath and the newPath.
223  _EditType editType = _EditType::Invalid;
224 
225  // Whether this describes a property edit or, otherwise, a prim edit.
226  bool IsPropertyEdit() const { return oldPath.IsPrimPropertyPath(); }
227  };
228 
229  // Struct representing the Sdf layer edits necessary to apply an edit
230  // description to the stage. We need this to gather all the information we
231  // can about what layer edits need to be performed before we start editing
232  // any specs so that we can avoid partial edits when a composed stage level
233  // namespace would fail.
234  struct _ProcessedEdit
235  {
236  // List of errors encountered that would prevent the overall namespace
237  // edit of the composed stage object from being completed successfully.
238  std::vector<std::string> errors;
239 
240  // The Sdf batch namespace edit that needs to be applied to each layer
241  // with specs.
242  SdfBatchNamespaceEdit edits;
243 
244  // The list of layers that have specs that need to have the Sdf
245  // namespace edit applied.
246  SdfLayerHandleVector layersToEdit;
247 
248  // Layer edits that need to be performed to update connection and
249  // relationship targets of other properties in order to keep them
250  // targeting the same object after applying this processed edit.
252  // Property spec to author the new targets value to. Note that we
253  // store the spec handle for the property as the property spec's
254  // path could change if the property is moved or deleted by the
255  // primary namespace edit.
256  SdfPropertySpecHandle propertySpec;
257 
258  // Name of the field that holds the path targets for the property
259  // which differs for attributes vs relationships.
261 
262  // Updated list op value to set for the property spec.
264  };
265  std::vector<TargetPathListOpEdit> targetPathListOpEdits;
266 
267  // List of errors encountered that would prevent connection and
268  // relationship target edits from being performed in response to the
269  // namespace edits.
270  std::vector<std::string> targetPathListOpErrors;
271 
272  // Reparent edits may require overs to be created for the new parent if
273  // a layer doesn't have any specs for the parent yet. This specifies the
274  // path of the parent specs to create if need.
275  SdfPath createParentSpecIfNeededPath;
276 
277  // Some edits want to remove inert ancestor overs after a prim is
278  // removed from its parent spec in a layer.
279  bool removeInertAncestorOvers = false;
280 
281  // Whether the edit would require relocates (or deactivation for delete)
282  bool requiresRelocates = false;
283 
284  // Applies this processed edit, performing the individual edits
285  // necessary to each layer that needs to be updated.
286  bool Apply();
287 
288  // Returns whether this processed edit can be applied.
289  bool CanApply(std::string *whyNot) const;
290  };
291 
292  // Adds an edit description for a prim delete operation.
293  bool _AddPrimDelete(const SdfPath &oldPath);
294 
295  // Adds an edit description for a prim rename or reparent operation.
296  bool _AddPrimMove(const SdfPath &oldPath, const SdfPath &newPath);
297 
298  // Adds an edit description for a property delete operation.
299  bool _AddPropertyDelete(const SdfPath &oldPath);
300 
301  // Adds an edit description for a property rename or reparent operation.
302  bool _AddPropertyMove(const SdfPath &oldPath, const SdfPath &newPath);
303 
304  // Clears the current procesed edits.
305  void _ClearProcessedEdits();
306 
307  // Processes and caches the layer edits necessary for the current edit
308  // operation if there is no cached processecd edit.
309  void _ProcessEditsIfNeeded() const;
310 
311  // Helper class for _ProcessEditsIfNeeded. Defined entirely in
312  // implementation. Declared here for private access to the editor
313  // structures.
314  class _EditProcessor;
315 
316  UsdStageRefPtr _stage;
317  _EditDescription _editDescription;
318  mutable std::optional<_ProcessedEdit> _processedEdit;
319 };
320 
322 
323 #endif // PXR_USD_USD_NAMESPACE_EDITOR_H
324 
#define USD_API
Definition: api.h:40
GLsizei const GLchar *const * string
Definition: glcorearb.h:814
GLsizei const GLchar *const * path
Definition: glcorearb.h:3341
class SdfListOp< class SdfPath > SdfPathListOp
Definition: listOp.h:329
Definition: token.h:87
USD_API bool MovePrimAtPath(const SdfPath &path, const SdfPath &newPath)
USD_API bool CanApplyEdits(std::string *whyNot=nullptr) const
USD_API bool RenamePrim(const UsdPrim &prim, const TfToken &newName)
USD_API bool DeletePrim(const UsdPrim &prim)
USD_API bool RenameProperty(const UsdProperty &property, const TfToken &newName)
Definition: prim.h:133
Definition: path.h:290
USD_API bool DeletePropertyAtPath(const SdfPath &path)
USD_API bool MovePropertyAtPath(const SdfPath &path, const SdfPath &newPath)
PXR_NAMESPACE_CLOSE_SCOPE PXR_NAMESPACE_OPEN_SCOPE
Definition: path.h:1432
USD_API bool ReparentPrim(const UsdPrim &prim, const UsdPrim &newParent)
#define PXR_NAMESPACE_CLOSE_SCOPE
Definition: pxr.h:91
USD_API bool DeleteProperty(const UsdProperty &property)
USD_API UsdNamespaceEditor(const UsdStageRefPtr &stage)
USD_API bool ReparentProperty(const UsdProperty &property, const UsdPrim &newParent)
USD_API bool DeletePrimAtPath(const SdfPath &path)
USD_API bool ApplyEdits()