1##-***************************************************************************** 2## 3## Copyright (c) 2009-2011, 4## Sony Pictures Imageworks, Inc. and 5## Industrial Light & Magic, a division of Lucasfilm Entertainment Company Ltd. 6## 7## All rights reserved. 8## 9## Redistribution and use in source and binary forms, with or without 10## modification, are permitted provided that the following conditions are 11## met: 12## * Redistributions of source code must retain the above copyright 13## notice, this list of conditions and the following disclaimer. 14## * Redistributions in binary form must reproduce the above 15## copyright notice, this list of conditions and the following disclaimer 16## in the documentation and/or other materials provided with the 17## distribution. 18## * Neither the name of Sony Pictures Imageworks, nor 19## Industrial Light & Magic nor the names of their contributors may be used 20## to endorse or promote products derived from this software without specific 21## prior written permission. 22## 23## THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24## "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25## LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26## A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27## OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28## SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 29## LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 30## DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 31## THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 32## (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 33## OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34## 35##-***************************************************************************** 36 37from maya import cmds as MayaCmds 38import maya.OpenMaya as OpenMaya 39import os 40import math 41 42# adds the current working directory so tools don't get confused about where we 43# are storing files 44def expandFileName(name): 45 return os.getcwd() + os.path.sep + name 46 47# compare the two floating point values 48def floatDiff(val1, val2, tolerance): 49 diff = math.fabs(val1 - val2) 50 if diff < math.pow(10, -tolerance): 51 return True 52 return False 53 54# function that returns a node object given a name 55def getObjFromName(nodeName): 56 selectionList = OpenMaya.MSelectionList() 57 selectionList.add( nodeName ) 58 obj = OpenMaya.MObject() 59 selectionList.getDependNode(0, obj) 60 return obj 61 62# function that finds a plug given a node object and plug name 63def getPlugFromName(attrName, nodeObj): 64 fnDepNode = OpenMaya.MFnDependencyNode(nodeObj) 65 attrObj = fnDepNode.attribute(attrName) 66 plug = OpenMaya.MPlug(nodeObj, attrObj) 67 return plug 68 69# meaning of return value: 70# 0 if array1 = array2 71# 1 if array1 and array2 are of the same length, array1[i] == array2[i] for 0<=i<m<len, and array1[m] < array2[m] 72# -1 if array1 and array2 are of the same length, array1[i] == array2[i] for 0<=i<m<len, and array1[m] > array2[m] 73# 2 if array1.length() < array2.length() 74# -2 if array1.length() > array2.length() 75def compareArray(array1, array2): 76 len1 = array1.length() 77 len2 = array2.length() 78 if len1 > len2 : return -2 79 if len1 < len2 : return 2 80 for i in range(0, len1): 81 if array1[i] < array2[i] : 82 return 1 83 if array1[i] > array2[i] : 84 return -1 85 return 0 86 87# return True if the two point arrays are exactly the same 88def comparePointArray(array1, array2): 89 len1 = array1.length() 90 len2 = array2.length() 91 if len1 != len2 : 92 return False 93 for i in range(0, len1): 94 if not array1[i].isEquivalent(array2[i], 1e-6): 95 return False 96 return True 97 98# return True if the two meshes are identical 99def compareMesh( nodeName1, nodeName2 ): 100 101 # basic error checking 102 obj1 = getObjFromName(nodeName1) 103 if not obj1.hasFn(OpenMaya.MFn.kMesh): 104 return False 105 obj2 = getObjFromName(nodeName2) 106 if not obj2.hasFn(OpenMaya.MFn.kMesh): 107 return False 108 109 polyIt1 = OpenMaya.MItMeshPolygon( obj1 ) 110 polyIt2 = OpenMaya.MItMeshPolygon( obj2 ) 111 112 if polyIt1.count() != polyIt2.count(): 113 return False 114 115 if polyIt1.polygonVertexCount() != polyIt2.polygonVertexCount(): 116 return False 117 118 vertices1 = OpenMaya.MIntArray() 119 vertices2 = OpenMaya.MIntArray() 120 pointArray1 = OpenMaya.MPointArray() 121 pointArray2 = OpenMaya.MPointArray() 122 123 while polyIt1.isDone()==False and polyIt2.isDone()==False : 124 125 # compare vertex indices 126 polyIt1.getVertices(vertices1) 127 polyIt2.getVertices(vertices2) 128 if compareArray(vertices1, vertices2) != 0: 129 return False 130 131 # compare vertex positions 132 polyIt1.getPoints(pointArray1) 133 polyIt2.getPoints(pointArray2) 134 if not comparePointArray( pointArray1, pointArray2 ): 135 return False 136 137 polyIt1.next() 138 polyIt2.next() 139 140 if polyIt1.isDone() and polyIt2.isDone() : 141 return True 142 143 return False 144 145# return True if the two Nurbs Surfaces are identical 146def compareNurbsSurface(nodeName1, nodeName2): 147 148 # basic error checking 149 obj1 = getObjFromName(nodeName1) 150 if not obj1.hasFn(OpenMaya.MFn.kNurbsSurface): 151 return False 152 obj2 = getObjFromName(nodeName2) 153 if not obj2.hasFn(OpenMaya.MFn.kNurbsSurface): 154 return False 155 156 fn1 = OpenMaya.MFnNurbsSurface(obj1) 157 fn2 = OpenMaya.MFnNurbsSurface(obj2) 158 159 # degree 160 if fn1.degreeU() != fn2.degreeU(): 161 return False 162 if fn1.degreeV() != fn2.degreeV(): 163 return False 164 165 # span 166 if fn1.numSpansInU() != fn2.numSpansInU(): 167 return False 168 if fn1.numSpansInV() != fn2.numSpansInV(): 169 return False 170 171 # form 172 if fn1.formInU() != fn2.formInU(): 173 return False 174 if fn1.formInV() != fn2.formInV(): 175 return False 176 177 # control points 178 if fn1.numCVsInU() != fn2.numCVsInU(): 179 return False 180 if fn1.numCVsInV() != fn2.numCVsInV(): 181 return False 182 183 cv1 = OpenMaya.MPointArray() 184 fn1.getCVs(cv1) 185 cv2 = OpenMaya.MPointArray() 186 fn2.getCVs(cv2) 187 if not comparePointArray(cv1, cv2): 188 return False 189 190 # knots 191 if fn1.numKnotsInU() != fn2.numKnotsInU(): 192 return False 193 if fn1.numKnotsInV() != fn2.numKnotsInV(): 194 return False 195 196 knotsU1 = OpenMaya.MDoubleArray() 197 fn1.getKnotsInU(knotsU1) 198 knotsV1 = OpenMaya.MDoubleArray() 199 fn1.getKnotsInV(knotsV1) 200 knotsU2 = OpenMaya.MDoubleArray() 201 fn2.getKnotsInU(knotsU2) 202 knotsV2 = OpenMaya.MDoubleArray() 203 fn2.getKnotsInV(knotsV2) 204 205 if compareArray( knotsU1, knotsU2 ) != 0: 206 return False 207 208 if compareArray( knotsV1, knotsV2 ) != 0: 209 return False 210 211 # trim curves 212 if fn1.isTrimmedSurface() != fn2.isTrimmedSurface(): 213 return False 214 215 # may need to add more trim checks 216 217 return True 218 219 220# return True if the two locators are idential 221def compareLocator(nodeName1, nodeName2): 222 223 # basic error checking 224 obj1 = getObjFromName(nodeName1) 225 if not obj1.hasFn(OpenMaya.MFn.kLocator): 226 return False 227 228 obj2 = getObjFromName(nodeName2) 229 if not obj2.hasFn(OpenMaya.MFn.kLocator): 230 return False 231 232 if not floatDiff(MayaCmds.getAttr(nodeName1+'.localPositionX'), 233 MayaCmds.getAttr(nodeName2+'.localPositionX'), 4): 234 return False 235 236 if not floatDiff(MayaCmds.getAttr(nodeName1+'.localPositionY'), 237 MayaCmds.getAttr(nodeName2+'.localPositionY'), 4): 238 return False 239 240 if not floatDiff(MayaCmds.getAttr(nodeName1+'.localPositionZ'), 241 MayaCmds.getAttr(nodeName2+'.localPositionZ'), 4): 242 return False 243 244 if not floatDiff(MayaCmds.getAttr(nodeName1+'.localScaleX'), 245 MayaCmds.getAttr(nodeName2+'.localScaleX'), 4): 246 return False 247 248 if not floatDiff(MayaCmds.getAttr(nodeName1+'.localScaleY'), 249 MayaCmds.getAttr(nodeName2+'.localScaleY'), 4): 250 return False 251 252 if not floatDiff(MayaCmds.getAttr(nodeName1+'.localScaleZ'), 253 MayaCmds.getAttr(nodeName2+'.localScaleZ'), 4): 254 return False 255 256 return True 257 258 259# return True if the two cameras are identical 260def compareCamera( nodeName1, nodeName2 ): 261 262 # basic error checking 263 obj1 = getObjFromName(nodeName1) 264 if not obj1.hasFn(OpenMaya.MFn.kCamera): 265 return False 266 267 obj2 = getObjFromName(nodeName2) 268 if not obj2.hasFn(OpenMaya.MFn.kCamera): 269 return False 270 271 fn1 = OpenMaya.MFnCamera( obj1 ) 272 fn2 = OpenMaya.MFnCamera( obj2 ) 273 274 if fn1.filmFit() != fn2.filmFit(): 275 print "differ in filmFit" 276 return False 277 278 if not floatDiff(fn1.filmFitOffset(), fn2.filmFitOffset(), 4): 279 print "differ in filmFitOffset" 280 return False 281 282 if fn1.isOrtho() != fn2.isOrtho(): 283 print "differ in isOrtho" 284 return False 285 286 if not floatDiff(fn1.orthoWidth(), fn2.orthoWidth(), 4): 287 print "differ in orthoWidth" 288 return False 289 290 if not floatDiff(fn1.focalLength(), fn2.focalLength(), 4): 291 print "differ in focalLength" 292 return False 293 294 if not floatDiff(fn1.lensSqueezeRatio(), fn2.lensSqueezeRatio(), 4): 295 print "differ in lensSqueezeRatio" 296 return False 297 298 if not floatDiff(fn1.cameraScale(), fn2.cameraScale(), 4): 299 print "differ in cameraScale" 300 return False 301 302 if not floatDiff(fn1.horizontalFilmAperture(), 303 fn2.horizontalFilmAperture(), 4): 304 print "differ in horizontalFilmAperture" 305 return False 306 307 if not floatDiff(fn1.verticalFilmAperture(), fn2.verticalFilmAperture(), 4): 308 print "differ in verticalFilmAperture" 309 return False 310 311 if not floatDiff(fn1.horizontalFilmOffset(), fn2.horizontalFilmOffset(), 4): 312 print "differ in horizontalFilmOffset" 313 return False 314 315 if not floatDiff(fn1.verticalFilmOffset(), fn2.verticalFilmOffset(), 4): 316 print "differ in verticalFilmOffset" 317 return False 318 319 if not floatDiff(fn1.overscan(), fn2.overscan(), 4): 320 print "differ in overscan" 321 return False 322 323 if not floatDiff(fn1.nearClippingPlane(), fn2.nearClippingPlane(), 4): 324 print "differ in nearClippingPlane" 325 return False 326 327 if not floatDiff(fn1.farClippingPlane(), fn2.farClippingPlane(), 4): 328 print "differ in farClippingPlane" 329 return False 330 331 if not floatDiff(fn1.preScale(), fn2.preScale(), 4): 332 print "differ in preScale" 333 return False 334 335 if not floatDiff(fn1.postScale(), fn2.postScale(), 4): 336 print "differ in postScale" 337 return False 338 339 if not floatDiff(fn1.filmTranslateH(), fn2.filmTranslateH(), 4): 340 print "differ in filmTranslateH" 341 return False 342 343 if not floatDiff(fn1.filmTranslateV(), fn2.filmTranslateV(), 4): 344 print "differ in filmTranslateV" 345 return False 346 347 if not floatDiff(fn1.horizontalRollPivot(), fn2.horizontalRollPivot(), 4): 348 print "differ in horizontalRollPivot" 349 return False 350 351 if not floatDiff(fn1.verticalRollPivot(), fn2.verticalRollPivot(), 4): 352 print "differ in verticalRollPivot" 353 return False 354 355 if fn1.filmRollOrder() != fn2.filmRollOrder(): 356 print "differ in filmRollOrder" 357 return False 358 359 if not floatDiff(fn1.filmRollValue(), fn2.filmRollValue(), 4): 360 print "differ in filmRollValue" 361 return False 362 363 if not floatDiff(fn1.fStop(), fn2.fStop(), 4): 364 print "differ in fStop" 365 return False 366 367 if not floatDiff(fn1.focusDistance(), fn2.focusDistance(), 4,): 368 print "differ in focusDistance" 369 return False 370 371 if not floatDiff(fn1.shutterAngle(), fn2.shutterAngle(), 4): 372 print "differ in shutterAngle" 373 return False 374 375 if fn1.usePivotAsLocalSpace() != fn2.usePivotAsLocalSpace(): 376 print "differ in usePivotAsLocalSpace" 377 return False 378 379 if fn1.tumblePivot() != fn2.tumblePivot(): 380 print "differ in tumblePivot" 381 return False 382 383 return True 384 385# return True if the two Nurbs curves are identical 386def compareNurbsCurve(nodeName1, nodeName2): 387 # basic error checking 388 obj1 = getObjFromName(nodeName1) 389 if not obj1.hasFn(OpenMaya.MFn.kNurbsCurve): 390 print nodeName1, "not a curve." 391 return False 392 393 obj2 = getObjFromName(nodeName2) 394 if not obj2.hasFn(OpenMaya.MFn.kNurbsCurve): 395 print nodeName2, "not a curve." 396 return False 397 398 fn1 = OpenMaya.MFnNurbsCurve(obj1) 399 fn2 = OpenMaya.MFnNurbsCurve(obj2) 400 401 if fn1.degree() != fn2.degree(): 402 print nodeName1, nodeName2, "degrees differ." 403 return False 404 405 if fn1.numCVs() != fn2.numCVs(): 406 print nodeName1, nodeName2, "numCVs differ." 407 return False 408 409 if fn1.numSpans() != fn2.numSpans(): 410 print nodeName1, nodeName2, "spans differ." 411 return False 412 413 if fn1.numKnots() != fn2.numKnots(): 414 print nodeName1, nodeName2, "numKnots differ." 415 return False 416 417 if fn1.form() != fn2.form(): 418 print nodeName1, nodeName2, "form differ." 419 return False 420 421 cv1 = OpenMaya.MPointArray() 422 fn1.getCVs(cv1) 423 cv2 = OpenMaya.MPointArray() 424 fn2.getCVs(cv2) 425 426 if not comparePointArray(cv1, cv2): 427 print nodeName1, nodeName2, "points differ." 428 return False 429 430 # we do not need to compare knots, since they aren't stored in Alembic 431 # and are currently recreated as uniformly distributed between 0 and 1 432 433 return True 434