1 /****************************************************************************
  2  Copyright (c) 2008-2010 Ricardo Quesada
  3  Copyright (c) 2011-2012 cocos2d-x.org
  4  Copyright (c) 2013-2014 Chukong Technologies Inc.
  5 
  6  http://www.cocos2d-x.org
  7 
  8  Permission is hereby granted, free of charge, to any person obtaining a copy
  9  of this software and associated documentation files (the "Software"), to deal
 10  in the Software without restriction, including without limitation the rights
 11  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 12  copies of the Software, and to permit persons to whom the Software is
 13  furnished to do so, subject to the following conditions:
 14 
 15  The above copyright notice and this permission notice shall be included in
 16  all copies or substantial portions of the Software.
 17 
 18  THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 19  IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 20  FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 21  AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 22  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 23  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 24  THE SOFTWARE.
 25  ****************************************************************************/
 26 
 27 /**
 28  * @constant
 29  * @type Number
 30  */
 31 cc.INVALID_INDEX = -1;
 32 
 33 /**
 34  * PI is the ratio of a circle's circumference to its diameter.
 35  * @constant
 36  * @type Number
 37  */
 38 cc.PI = Math.PI;
 39 
 40 /**
 41  * @constant
 42  * @type Number
 43  */
 44 cc.FLT_MAX = parseFloat('3.402823466e+38F');
 45 
 46 /**
 47  * @constant
 48  * @type Number
 49  */
 50 cc.FLT_MIN = parseFloat("1.175494351e-38F");
 51 
 52 /**
 53  * @constant
 54  * @type Number
 55  */
 56 cc.RAD = cc.PI / 180;
 57 
 58 /**
 59  * @constant
 60  * @type Number
 61  */
 62 cc.DEG = 180 / cc.PI;
 63 
 64 /**
 65  * maximum unsigned int value
 66  * @constant
 67  * @type Number
 68  */
 69 cc.UINT_MAX = 0xffffffff;
 70 
 71 /**
 72  * <p>
 73  * simple macro that swaps 2 variables<br/>
 74  *  modified from c++ macro, you need to pass in the x and y variables names in string, <br/>
 75  *  and then a reference to the whole object as third variable
 76  * </p>
 77  * @param {String} x
 78  * @param {String} y
 79  * @param {Object} ref
 80  * @function
 81  * @deprecated since v3.0
 82  */
 83 cc.swap = function (x, y, ref) {
 84     if (cc.isObject(ref) && !cc.isUndefined(ref.x) && !cc.isUndefined(ref.y)) {
 85         var tmp = ref[x];
 86         ref[x] = ref[y];
 87         ref[y] = tmp;
 88     } else
 89         cc.log(cc._LogInfos.swap);
 90 };
 91 
 92 /**
 93  * <p>
 94  *     Linear interpolation between 2 numbers, the ratio sets how much it is biased to each end
 95  * </p>
 96  * @param {Number} a number A
 97  * @param {Number} b number B
 98  * @param {Number} r ratio between 0 and 1
 99  * @function
100  * @example
101  * cc.lerp(2,10,0.5)//returns 6<br/>
102  * cc.lerp(2,10,0.2)//returns 3.6
103  */
104 cc.lerp = function (a, b, r) {
105     return a + (b - a) * r;
106 };
107 
108 /**
109  * get a random number from 0 to 0xffffff
110  * @function
111  * @returns {number}
112  */
113 cc.rand = function () {
114 	return Math.random() * 0xffffff;
115 };
116 
117 /**
118  * returns a random float between -1 and 1
119  * @return {Number}
120  * @function
121  */
122 cc.randomMinus1To1 = function () {
123     return (Math.random() - 0.5) * 2;
124 };
125 
126 /**
127  * returns a random float between 0 and 1
128  * @return {Number}
129  * @function
130  */
131 cc.random0To1 = Math.random;
132 
133 /**
134  * converts degrees to radians
135  * @param {Number} angle
136  * @return {Number}
137  * @function
138  */
139 cc.degreesToRadians = function (angle) {
140     return angle * cc.RAD;
141 };
142 
143 /**
144  * converts radians to degrees
145  * @param {Number} angle
146  * @return {Number}
147  * @function
148  */
149 cc.radiansToDegrees = function (angle) {
150     return angle * cc.DEG;
151 };
152 /**
153  * converts radians to degrees
154  * @param {Number} angle
155  * @return {Number}
156  * @function
157  */
158 cc.radiansToDegress = function (angle) {
159     cc.log(cc._LogInfos.radiansToDegress);
160     return angle * cc.DEG;
161 };
162 
163 /**
164  * @constant
165  * @type Number
166  */
167 cc.REPEAT_FOREVER = Number.MAX_VALUE - 1;
168 
169 /**
170  * Helpful macro that setups the GL server state, the correct GL program and sets the Model View Projection matrix
171  * @param {cc.Node} node setup node
172  * @function
173  */
174 cc.nodeDrawSetup = function (node) {
175     //cc.glEnable(node._glServerState);
176     if (node._shaderProgram) {
177         //cc._renderContext.useProgram(node._shaderProgram._programObj);
178         node._shaderProgram.use();
179         node._shaderProgram.setUniformForModelViewAndProjectionMatrixWithMat4();
180     }
181 };
182 
183 /**
184  * <p>
185  *     GL states that are enabled:<br/>
186  *       - GL_TEXTURE_2D<br/>
187  *       - GL_VERTEX_ARRAY<br/>
188  *       - GL_TEXTURE_COORD_ARRAY<br/>
189  *       - GL_COLOR_ARRAY<br/>
190  * </p>
191  * @function
192  */
193 cc.enableDefaultGLStates = function () {
194     //TODO OPENGL STUFF
195     /*
196      glEnableClientState(GL_VERTEX_ARRAY);
197      glEnableClientState(GL_COLOR_ARRAY);
198      glEnableClientState(GL_TEXTURE_COORD_ARRAY);
199      glEnable(GL_TEXTURE_2D);*/
200 };
201 
202 /**
203  * <p>
204  *   Disable default GL states:<br/>
205  *     - GL_TEXTURE_2D<br/>
206  *     - GL_TEXTURE_COORD_ARRAY<br/>
207  *     - GL_COLOR_ARRAY<br/>
208  * </p>
209  * @function
210  */
211 cc.disableDefaultGLStates = function () {
212     //TODO OPENGL
213     /*
214      glDisable(GL_TEXTURE_2D);
215      glDisableClientState(GL_COLOR_ARRAY);
216      glDisableClientState(GL_TEXTURE_COORD_ARRAY);
217      glDisableClientState(GL_VERTEX_ARRAY);
218      */
219 };
220 
221 /**
222  * <p>
223  *  Increments the GL Draws counts by one.<br/>
224  *  The number of calls per frame are displayed on the screen when the CCDirector's stats are enabled.<br/>
225  * </p>
226  * @param {Number} addNumber
227  * @function
228  */
229 cc.incrementGLDraws = function (addNumber) {
230     cc.g_NumberOfDraws += addNumber;
231 };
232 
233 /**
234  * @constant
235  * @type Number
236  */
237 cc.FLT_EPSILON = 0.0000001192092896;
238 
239 /**
240  * <p>
241  *     On Mac it returns 1;<br/>
242  *     On iPhone it returns 2 if RetinaDisplay is On. Otherwise it returns 1
243  * </p>
244  * @return {Number}
245  * @function
246  */
247 cc.contentScaleFactor = cc.IS_RETINA_DISPLAY_SUPPORTED ? function () {
248     return cc.director.getContentScaleFactor();
249 } : function () {
250     return 1;
251 };
252 
253 /**
254  * Converts a Point in points to pixels
255  * @param {cc.Point} points
256  * @return {cc.Point}
257  * @function
258  */
259 cc.pointPointsToPixels = function (points) {
260     var scale = cc.contentScaleFactor();
261     return cc.p(points.x * scale, points.y * scale);
262 };
263 
264 /**
265  * Converts a Point in pixels to points
266  * @param {cc.Rect} pixels
267  * @return {cc.Point}
268  * @function
269  */
270 cc.pointPixelsToPoints = function (pixels) {
271 	var scale = cc.contentScaleFactor();
272 	return cc.p(pixels.x / scale, pixels.y / scale);
273 };
274 
275 cc._pointPixelsToPointsOut = function(pixels, outPoint){
276 	var scale = cc.contentScaleFactor();
277 	outPoint.x = pixels.x / scale;
278 	outPoint.y = pixels.y / scale;
279 };
280 
281 /**
282  * Converts a Size in points to pixels
283  * @param {cc.Size} sizeInPoints
284  * @return {cc.Size}
285  * @function
286  */
287 cc.sizePointsToPixels = function (sizeInPoints) {
288     var scale = cc.contentScaleFactor();
289     return cc.size(sizeInPoints.width * scale, sizeInPoints.height * scale);
290 };
291 
292 /**
293  * Converts a size in pixels to points
294  * @param {cc.Size} sizeInPixels
295  * @return {cc.Size}
296  * @function
297  */
298 cc.sizePixelsToPoints = function (sizeInPixels) {
299     var scale = cc.contentScaleFactor();
300     return cc.size(sizeInPixels.width / scale, sizeInPixels.height / scale);
301 };
302 
303 cc._sizePixelsToPointsOut = function (sizeInPixels, outSize) {
304     var scale = cc.contentScaleFactor();
305     outSize.width = sizeInPixels.width / scale;
306     outSize.height = sizeInPixels.height / scale;
307 };
308 
309 /**
310  * Converts a rect in pixels to points
311  * @param {cc.Rect} pixel
312  * @return {cc.Rect}
313  * @function
314  */
315 cc.rectPixelsToPoints = cc.IS_RETINA_DISPLAY_SUPPORTED ? function (pixel) {
316     var scale = cc.contentScaleFactor();
317     return cc.rect(pixel.x / scale, pixel.y / scale,
318         pixel.width / scale, pixel.height / scale);
319 } : function (p) {
320     return p;
321 };
322 
323 /**
324  * Converts a rect in points to pixels
325  * @param {cc.Rect} point
326  * @return {cc.Rect}
327  * @function
328  */
329 cc.rectPointsToPixels = cc.IS_RETINA_DISPLAY_SUPPORTED ? function (point) {
330    var scale = cc.contentScaleFactor();
331     return cc.rect(point.x * scale, point.y * scale,
332         point.width * scale, point.height * scale);
333 } : function (p) {
334     return p;
335 };
336 
337 //some gl constant variable
338 /**
339  * @constant
340  * @type Number
341  */
342 cc.ONE = 1;
343 
344 /**
345  * @constant
346  * @type Number
347  */
348 cc.ZERO = 0;
349 
350 /**
351  * @constant
352  * @type Number
353  */
354 cc.SRC_ALPHA = 0x0302;
355 
356 /**
357  * @constant
358  * @type Number
359  */
360 cc.SRC_ALPHA_SATURATE = 0x308;
361 
362 /**
363  * @constant
364  * @type Number
365  */
366 cc.SRC_COLOR = 0x300;
367 
368 /**
369  * @constant
370  * @type Number
371  */
372 cc.DST_ALPHA = 0x304;
373 
374 /**
375  * @constant
376  * @type Number
377  */
378 cc.DST_COLOR = 0x306;
379 
380 /**
381  * @constant
382  * @type Number
383  */
384 cc.ONE_MINUS_SRC_ALPHA = 0x0303;
385 
386 /**
387  * @constant
388  * @type Number
389  */
390 cc.ONE_MINUS_SRC_COLOR = 0x301;
391 
392 /**
393  * @constant
394  * @type Number
395  */
396 cc.ONE_MINUS_DST_ALPHA = 0x305;
397 
398 /**
399  * @constant
400  * @type Number
401  */
402 cc.ONE_MINUS_DST_COLOR = 0x0307;
403 
404 /**
405  * @constant
406  * @type Number
407  */
408 cc.ONE_MINUS_CONSTANT_ALPHA	= 0x8004;
409 
410 /**
411  * @constant
412  * @type Number
413  */
414 cc.ONE_MINUS_CONSTANT_COLOR	= 0x8002;
415 
416 /**
417  * the constant variable equals gl.LINEAR for texture
418  * @constant
419  * @type Number
420  */
421 cc.LINEAR	= 0x2601;
422 
423 /**
424  * the constant variable equals gl.REPEAT for texture
425  * @constant
426  * @type Number
427  */
428 cc.REPEAT	= 0x2901;
429 
430 /**
431  * the constant variable equals gl.CLAMP_TO_EDGE for texture
432  * @constant
433  * @type Number
434  */
435 cc.CLAMP_TO_EDGE	= 0x812f;
436 
437 /**
438  * the constant variable equals gl.MIRRORED_REPEAT for texture
439  * @constant
440  * @type Number
441  */
442 cc.MIRRORED_REPEAT   = 0x8370;
443 
444 /**
445  * default gl blend src function. Compatible with premultiplied alpha images.
446  * @constant
447  * @name cc.BLEND_SRC
448  * @type Number
449  */
450 cc.BLEND_SRC = cc.SRC_ALPHA;
451 cc.game.addEventListener(cc.game.EVENT_RENDERER_INITED, function () {
452     if (cc._renderType === cc.game.RENDER_TYPE_WEBGL
453          && cc.OPTIMIZE_BLEND_FUNC_FOR_PREMULTIPLIED_ALPHA) {
454         cc.BLEND_SRC = cc.ONE;
455     }
456 });
457 
458 /**
459  * default gl blend dst function. Compatible with premultiplied alpha images.
460  * @constant
461  * @type Number
462  */
463 cc.BLEND_DST = cc.ONE_MINUS_SRC_ALPHA;
464 
465 /**
466  * Check webgl error.Error will be shown in console if exists.
467  * @function
468  */
469 cc.checkGLErrorDebug = function () {
470     if (cc.renderMode === cc.game.RENDER_TYPE_WEBGL) {
471         var _error = cc._renderContext.getError();
472         if (_error) {
473             cc.log(cc._LogInfos.checkGLErrorDebug, _error);
474         }
475     }
476 };
477 
478 //Possible device orientations
479 /**
480  * Device oriented vertically, home button on the bottom (UIDeviceOrientationPortrait)
481  * @constant
482  * @type Number
483  */
484 cc.DEVICE_ORIENTATION_PORTRAIT = 0;
485 
486 /**
487  * Device oriented horizontally, home button on the right (UIDeviceOrientationLandscapeLeft)
488  * @constant
489  * @type Number
490  */
491 cc.DEVICE_ORIENTATION_LANDSCAPE_LEFT = 1;
492 
493 /**
494  * Device oriented vertically, home button on the top (UIDeviceOrientationPortraitUpsideDown)
495  * @constant
496  * @type Number
497  */
498 cc.DEVICE_ORIENTATION_PORTRAIT_UPSIDE_DOWN = 2;
499 
500 /**
501  * Device oriented horizontally, home button on the left (UIDeviceOrientationLandscapeRight)
502  * @constant
503  * @type Number
504  */
505 cc.DEVICE_ORIENTATION_LANDSCAPE_RIGHT = 3;
506 
507 /**
508  * In browsers, we only support 2 orientations by change window size.
509  * @constant
510  * @type Number
511  */
512 cc.DEVICE_MAX_ORIENTATIONS = 2;
513 
514 
515 // ------------------- vertex attrib flags -----------------------------
516 /**
517  * @constant
518  * @type {Number}
519  */
520 cc.VERTEX_ATTRIB_FLAG_NONE = 0;
521 /**
522  * @constant
523  * @type {Number}
524  */
525 cc.VERTEX_ATTRIB_FLAG_POSITION = 1 << 0;
526 /**
527  * @constant
528  * @type {Number}
529  */
530 cc.VERTEX_ATTRIB_FLAG_COLOR = 1 << 1;
531 /**
532  * @constant
533  * @type {Number}
534  */
535 cc.VERTEX_ATTRIB_FLAG_TEX_COORDS = 1 << 2;
536 /**
537  * @constant
538  * @type {Number}
539  */
540 cc.VERTEX_ATTRIB_FLAG_POS_COLOR_TEX = ( cc.VERTEX_ATTRIB_FLAG_POSITION | cc.VERTEX_ATTRIB_FLAG_COLOR | cc.VERTEX_ATTRIB_FLAG_TEX_COORDS );
541 
542 /**
543  * GL server side states
544  * @constant
545  * @type {Number}
546  */
547 cc.GL_ALL = 0;
548 
549 //-------------Vertex Attributes-----------
550 /**
551  * @constant
552  * @type {Number}
553  */
554 cc.VERTEX_ATTRIB_POSITION = 0;
555 /**
556  * @constant
557  * @type {Number}
558  */
559 cc.VERTEX_ATTRIB_COLOR = 1;
560 /**
561  * @constant
562  * @type {Number}
563  */
564 cc.VERTEX_ATTRIB_TEX_COORDS = 2;
565 /**
566  * @constant
567  * @type {Number}
568  */
569 cc.VERTEX_ATTRIB_MAX = 3;
570 
571 //------------Uniforms------------------
572 /**
573  * @constant
574  * @type {Number}
575  */
576 cc.UNIFORM_PMATRIX = 0;
577 /**
578  * @constant
579  * @type {Number}
580  */
581 cc.UNIFORM_MVMATRIX = 1;
582 /**
583  * @constant
584  * @type {Number}
585  */
586 cc.UNIFORM_MVPMATRIX = 2;
587 /**
588  * @constant
589  * @type {Number}
590  */
591 cc.UNIFORM_TIME = 3;
592 /**
593  * @constant
594  * @type {Number}
595  */
596 cc.UNIFORM_SINTIME = 4;
597 /**
598  * @constant
599  * @type {Number}
600  */
601 cc.UNIFORM_COSTIME = 5;
602 /**
603  * @constant
604  * @type {Number}
605  */
606 cc.UNIFORM_RANDOM01 = 6;
607 /**
608  * @constant
609  * @type {Number}
610  */
611 cc.UNIFORM_SAMPLER = 7;
612 /**
613  * @constant
614  * @type {Number}
615  */
616 cc.UNIFORM_MAX = 8;
617 
618 //------------Shader Name---------------
619 /**
620  * @constant
621  * @type {String}
622  */
623 cc.SHADER_POSITION_TEXTURECOLOR = "ShaderPositionTextureColor";
624 /**
625  * @constant
626  * @type {String}
627  */
628 cc.SHADER_POSITION_TEXTURECOLORALPHATEST = "ShaderPositionTextureColorAlphaTest";
629 /**
630  * @constant
631  * @type {String}
632  */
633 cc.SHADER_POSITION_COLOR = "ShaderPositionColor";
634 /**
635  * @constant
636  * @type {String}
637  */
638 cc.SHADER_POSITION_TEXTURE = "ShaderPositionTexture";
639 /**
640  * @constant
641  * @type {String}
642  */
643 cc.SHADER_POSITION_TEXTURE_UCOLOR = "ShaderPositionTexture_uColor";
644 /**
645  * @constant
646  * @type {String}
647  */
648 cc.SHADER_POSITION_TEXTUREA8COLOR = "ShaderPositionTextureA8Color";
649 /**
650  * @constant
651  * @type {String}
652  */
653 cc.SHADER_POSITION_UCOLOR = "ShaderPosition_uColor";
654 /**
655  * @constant
656  * @type {String}
657  */
658 cc.SHADER_POSITION_LENGTHTEXTURECOLOR = "ShaderPositionLengthTextureColor";
659 
660 //------------uniform names----------------
661 /**
662  * @constant
663  * @type {String}
664  */
665 cc.UNIFORM_PMATRIX_S = "CC_PMatrix";
666 /**
667  * @constant
668  * @type {String}
669  */
670 cc.UNIFORM_MVMATRIX_S = "CC_MVMatrix";
671 /**
672  * @constant
673  * @type {String}
674  */
675 cc.UNIFORM_MVPMATRIX_S = "CC_MVPMatrix";
676 /**
677  * @constant
678  * @type {String}
679  */
680 cc.UNIFORM_TIME_S = "CC_Time";
681 /**
682  * @constant
683  * @type {String}
684  */
685 cc.UNIFORM_SINTIME_S = "CC_SinTime";
686 /**
687  * @constant
688  * @type {String}
689  */
690 cc.UNIFORM_COSTIME_S = "CC_CosTime";
691 /**
692  * @constant
693  * @type {String}
694  */
695 cc.UNIFORM_RANDOM01_S = "CC_Random01";
696 /**
697  * @constant
698  * @type {String}
699  */
700 cc.UNIFORM_SAMPLER_S = "CC_Texture0";
701 /**
702  * @constant
703  * @type {String}
704  */
705 cc.UNIFORM_ALPHA_TEST_VALUE_S = "CC_alpha_value";
706 
707 //------------Attribute names--------------
708 /**
709  * @constant
710  * @type {String}
711  */
712 cc.ATTRIBUTE_NAME_COLOR = "a_color";
713 /**
714  * @constant
715  * @type {String}
716  */
717 cc.ATTRIBUTE_NAME_POSITION = "a_position";
718 /**
719  * @constant
720  * @type {String}
721  */
722 cc.ATTRIBUTE_NAME_TEX_COORD = "a_texCoord";
723 
724 
725 /**
726  * default size for font size
727  * @constant
728  * @type Number
729  */
730 cc.ITEM_SIZE = 32;
731 
732 /**
733  * default tag for current item
734  * @constant
735  * @type Number
736  */
737 cc.CURRENT_ITEM = 0xc0c05001;
738 /**
739  * default tag for zoom action tag
740  * @constant
741  * @type Number
742  */
743 cc.ZOOM_ACTION_TAG = 0xc0c05002;
744 /**
745  * default tag for normal
746  * @constant
747  * @type Number
748  */
749 cc.NORMAL_TAG = 8801;
750 
751 /**
752  * default selected tag
753  * @constant
754  * @type Number
755  */
756 cc.SELECTED_TAG = 8802;
757 
758 /**
759  * default disabled tag
760  * @constant
761  * @type Number
762  */
763 cc.DISABLE_TAG = 8803;
764 
765 
766 // Array utils
767 
768 /**
769  * Verify Array's Type
770  * @param {Array} arr
771  * @param {function} type
772  * @return {Boolean}
773  * @function
774  */
775 cc.arrayVerifyType = function (arr, type) {
776     if (arr && arr.length > 0) {
777         for (var i = 0; i < arr.length; i++) {
778             if (!(arr[i] instanceof  type)) {
779                 cc.log("element type is wrong!");
780                 return false;
781             }
782         }
783     }
784     return true;
785 };
786 
787 /**
788  * Searches for the first occurance of object and removes it. If object is not found the function has no effect.
789  * @function
790  * @param {Array} arr Source Array
791  * @param {*} delObj  remove object
792  */
793 cc.arrayRemoveObject = function (arr, delObj) {
794     for (var i = 0, l = arr.length; i < l; i++) {
795         if (arr[i] === delObj) {
796             arr.splice(i, 1);
797             break;
798         }
799     }
800 };
801 
802 /**
803  * Removes from arr all values in minusArr. For each Value in minusArr, the first matching instance in arr will be removed.
804  * @function
805  * @param {Array} arr Source Array
806  * @param {Array} minusArr minus Array
807  */
808 cc.arrayRemoveArray = function (arr, minusArr) {
809     for (var i = 0, l = minusArr.length; i < l; i++) {
810         cc.arrayRemoveObject(arr, minusArr[i]);
811     }
812 };
813 
814 /**
815  * Inserts some objects at index
816  * @function
817  * @param {Array} arr
818  * @param {Array} addObjs
819  * @param {Number} index
820  * @return {Array}
821  */
822 cc.arrayAppendObjectsToIndex = function(arr, addObjs,index){
823     arr.splice.apply(arr, [index, 0].concat(addObjs));
824     return arr;
825 };
826 
827 /**
828  * Copy an array's item to a new array (its performance is better than Array.slice)
829  * @param {Array} arr
830  * @return {Array}
831  */
832 cc.copyArray = function(arr){
833     var i, len = arr.length, arr_clone = new Array(len);
834     for (i = 0; i < len; i += 1)
835         arr_clone[i] = arr[i];
836     return arr_clone;
837 };
838