Advertisement
Guest User

Untitled

a guest
Jul 26th, 2017
73
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 16.90 KB | None | 0 0
  1. using UnityEngine;
  2. using System.Collections;
  3.  
  4. public class Cloak : MonoBehaviour {
  5.  
  6.  
  7. //public HumanBuffer humanBuffer;
  8. //
  9. //public GameObject hand1;
  10. //public GameObject hand2;
  11.  
  12. public float Radius;
  13.  
  14. public float StartTime;
  15.  
  16. public Color color;
  17. public float gravity;
  18. public float attractToHand;
  19. public float repelFromHand;
  20.  
  21.  
  22. // How the donut looks
  23. public Shader shader;
  24. public Shader debugShader;
  25.  
  26. // How the donut feels
  27. public ComputeShader constraintPass;
  28. public ComputeShader normalPass;
  29. public ComputeShader forcePass;
  30.  
  31.  
  32. public Texture2D normalMap;
  33. public Cubemap cubeMap;
  34.  
  35. public float clothSize = 1;
  36. public float startingHeight = 1;
  37.  
  38. private Vector3 v1;
  39. private Vector3 v2;
  40. private Vector3 bodyPos;
  41.  
  42.  
  43. public ComputeBuffer _vertBuffer;
  44. public ComputeBuffer _transformBuffer;
  45.  
  46. private ComputeBuffer _upLinkBuffer;
  47. private ComputeBuffer _rightLinkBuffer;
  48. private ComputeBuffer _diagonalDownLinkBuffer;
  49. private ComputeBuffer _diagonalUpLinkBuffer;
  50.  
  51. public Material material;
  52. private Material debugMaterial;
  53.  
  54. private const int threadX = 4;
  55. private const int threadY = 4;
  56. private const int threadZ = 4;
  57.  
  58. private const int strideX = 4;
  59. private const int strideY = 4;
  60. private const int strideZ = 4;
  61.  
  62. private int gridX { get { return threadX * strideX; } }
  63. private int gridY { get { return threadY * strideY; } }
  64. private int gridZ { get { return threadZ * strideZ; } }
  65.  
  66. private int vertexCount { get { return gridX * gridY * gridZ; } }
  67.  
  68.  
  69. public int ribbonWidth = 64;
  70. public int ribbonLength { get { return (int)Mathf.Floor( (float)vertexCount / ribbonWidth ); } }
  71.  
  72.  
  73. private int _kernelforce;
  74. private int _kernelconstraint;
  75. private int _kernelnormal;
  76.  
  77. private float[] inValues;
  78. private float[] transformValues;
  79.  
  80. private float oTime = 0;
  81.  
  82.  
  83. struct Vert{
  84. public Vector3 pos;
  85. public Vector3 oPos;
  86. public Vector3 ogPos;
  87. public Vector3 norm;
  88. public Vector2 uv;
  89. public float mass;
  90. public float[] ids;
  91. public Vector3 debug;
  92. };
  93.  
  94. struct Link{
  95. public float id1;
  96. public float id2;
  97. public float distance;
  98. public float stiffness;
  99. }
  100.  
  101. private int VertStructSize = 3 + 3 + 3 + 3 + 2 + 1 + 8 + 3;
  102. private int LinkStructSize = 1 + 1 + 1 + 1;
  103.  
  104. // private float oTime;
  105.  
  106. // Use this for initialization
  107. void Start () {
  108.  
  109. //HumanBuffer = GameObject.Find("HumanBuffer");
  110.  
  111. //EventManager.OnTriggerDown += OnTriggerDown;
  112.  
  113.  
  114. oTime = Time.time;
  115.  
  116. transformValues = new float[ 16 ];
  117.  
  118. createBuffers();
  119. createMaterial();
  120.  
  121. _kernelforce = forcePass.FindKernel("CSMain");
  122. _kernelnormal = normalPass.FindKernel("CSMain");
  123. _kernelconstraint = constraintPass.FindKernel("CSMain");
  124.  
  125. forcePass.SetInt( "_Reset" , 0 );
  126. forcePass.SetInt( "_Ended" , 0 );
  127.  
  128. // Dispatch();
  129. OnTriggerDown(gameObject);
  130.  
  131. Camera.onPostRender += Render;
  132.  
  133. }
  134.  
  135. public void OnTriggerDown( GameObject g ){
  136.  
  137. forcePass.SetInt( "_Reset" , 1 );
  138. Dispatch();
  139. //Dispatch();
  140. //Dispatch();
  141. forcePass.SetInt( "_Reset" , 0);
  142.  
  143.  
  144. }
  145.  
  146. public void FixedUpdate(){
  147.  
  148. Dispatch();
  149.  
  150. }
  151.  
  152.  
  153. //When this GameObject is disabled we must release the buffers or else Unity complains.
  154. private void OnDisable(){
  155. Camera.onPostRender -= Render;
  156. ReleaseBuffer();
  157. }
  158.  
  159.  
  160. //For some reason I made this method to create a material from the attached shader.
  161. private void createMaterial(){
  162.  
  163. material = new Material( shader );
  164. debugMaterial = new Material( debugShader );
  165.  
  166. }
  167.  
  168.  
  169. //Remember to release buffers and destroy the material when play has been stopped.
  170. void ReleaseBuffer(){
  171.  
  172. _vertBuffer.Release();
  173. _transformBuffer.Release();
  174.  
  175. _upLinkBuffer.Release();
  176. _rightLinkBuffer.Release();
  177. _diagonalUpLinkBuffer.Release();
  178. _diagonalDownLinkBuffer.Release();
  179.  
  180.  
  181. DestroyImmediate( material );
  182. DestroyImmediate( debugMaterial );
  183.  
  184. }
  185.  
  186. //After all rendering is complete we dispatch the compute shader and then set the material before drawing with DrawProcedural
  187. //this just draws the "mesh" as a set of points
  188. public void Render(Camera camera) {
  189.  
  190.  
  191. int numVertsTotal = (ribbonWidth) * 3 * 2 * (ribbonLength-1);
  192.  
  193.  
  194. material.SetPass(0);
  195. material.SetInt("_Large" , 0 );
  196. material.SetBuffer("buf_Points", _vertBuffer);
  197. material.SetColor("_Color", color);
  198. //material.SetBuffer("shapeBuffer", PF.pillows._shapeBuffer);
  199. //
  200. //material.SetInt( "_NumberHands" , PF.handBufferInfo.GetComponent<HandBuffer>().numberHands );
  201. //material.SetBuffer( "handBuffer" , PF.handBufferInfo.GetComponent<HandBuffer>()._handBuffer );
  202.  
  203. //material.SetFloat( "_FullEnd" , PF.fullEnd );
  204. //material.SetFloat("_ClothDown" , PF.clothDown );
  205.  
  206. material.SetInt( "_RibbonWidth" , ribbonWidth );
  207. material.SetInt( "_RibbonLength" , ribbonLength );
  208. material.SetInt( "_TotalVerts" , vertexCount );
  209. //material.SetInt( "_NumShapes" , PF.pillows.Shapes.Length );
  210.  
  211. //material.SetFloat("_Height" , PF.pillows.tallestPoint );
  212. //material.SetFloat("_Width" , PF.pillows.widestPoint );
  213.  
  214. //material.SetFloat("_Special" , PF.special );
  215. material.SetTexture( "_NormalMap" , normalMap);
  216. material.SetTexture( "_CubeMap" , cubeMap );
  217.  
  218. material.SetMatrix("worldMat", transform.localToWorldMatrix);
  219. material.SetMatrix("invWorldMat", transform.worldToLocalMatrix);
  220.  
  221. Graphics.DrawProcedural(MeshTopology.Triangles, numVertsTotal);
  222.  
  223.  
  224. }
  225.  
  226.  
  227. private Vector3 getVertPosition( float col , float row ){
  228. float uvX = col / ribbonWidth;
  229. float uvY = row / ribbonLength;
  230. float angle = uvX * 2 * Mathf.PI;
  231. float radius = (Mathf.Pow( uvY , .5f )+.2f) * Radius;
  232.  
  233. float x = Mathf.Cos( angle ) * radius;
  234. float y = Mathf.Sin( angle ) * radius;
  235.  
  236. return new Vector3( x * clothSize , 0 , y * clothSize );
  237.  
  238. }
  239.  
  240. private void createBuffers() {
  241. _transformBuffer = new ComputeBuffer( 1 , 16* sizeof(float));
  242. _vertBuffer = new ComputeBuffer( vertexCount , VertStructSize * sizeof(float));
  243.  
  244. _upLinkBuffer = new ComputeBuffer( vertexCount / 2 , LinkStructSize * sizeof(float));
  245. _rightLinkBuffer = new ComputeBuffer( vertexCount / 2 , LinkStructSize * sizeof(float));
  246. _diagonalDownLinkBuffer = new ComputeBuffer( vertexCount / 2 , LinkStructSize * sizeof(float));
  247. _diagonalUpLinkBuffer = new ComputeBuffer( vertexCount / 2 , LinkStructSize * sizeof(float));
  248.  
  249. float lRight = clothSize / (float)ribbonWidth;
  250. float lUp = clothSize / (float)ribbonLength;
  251.  
  252.  
  253. Vector2 n = new Vector2( lRight , lUp );
  254.  
  255. float lDia = n.magnitude;
  256.  
  257. inValues = new float[ VertStructSize * vertexCount];
  258.  
  259. float[] upLinkValues = new float[ LinkStructSize * vertexCount / 2 ];
  260. float[] rightLinkValues = new float[ LinkStructSize * vertexCount / 2 ];
  261. float[] diagonalDownLinkValues = new float[ LinkStructSize * vertexCount / 2 ];
  262. float[] diagonalUpLinkValues = new float[ LinkStructSize * vertexCount / 2 ];
  263.  
  264. // Used for assigning to our buffer;
  265. int index = 0;
  266. int indexOG = 0;
  267. int li1= 0;
  268. int li2= 0;
  269. int li3= 0;
  270. int li4= 0;
  271.  
  272.  
  273. /* // second rite up here
  274. u dU x . r
  275. . . // third rite down here
  276. x . r x . r
  277. .
  278. dD
  279.  
  280. */
  281.  
  282. for (int z = 0; z < gridZ; z++) {
  283. for (int y = 0; y < gridY; y++) {
  284. for (int x = 0; x < gridX; x++) {
  285.  
  286. int id = x + y * gridX + z * gridX * gridY;
  287.  
  288. float col = (float)(id % ribbonWidth );
  289. float row = Mathf.Floor( ((float)id +0.01f) / ribbonWidth);
  290.  
  291.  
  292. float uvX = col / ribbonWidth;
  293. float uvY = row / ribbonLength;
  294.  
  295. float stiffness = uvY;
  296.  
  297. Vector3 fVec = getVertPosition( col , row );
  298.  
  299. if( row % 2 == 0 ){
  300.  
  301. Vector3 pos1; Vector3 pos2;
  302.  
  303. pos1 = fVec;
  304. pos2 = getVertPosition( col + 0 , row +1 );
  305.  
  306.  
  307. stiffness = (row + .5f ) / ribbonLength;
  308. upLinkValues[li1++] = id;
  309. upLinkValues[li1++] = convertToID( col + 0 , row + 1 );
  310. upLinkValues[li1++] = ( pos1 - pos2 ).magnitude;
  311. upLinkValues[li1++] = stiffness;
  312.  
  313.  
  314. // Because of the way the right links
  315. // are made, we need to alternate them,
  316. // and flip flop them back and forth
  317. // so they are not writing to the same
  318. // positions during the same path!
  319. float id1 , id2;
  320.  
  321.  
  322. float fDist;
  323.  
  324. if( col % 2 == 0 ){
  325.  
  326. id1 = id;
  327. id2 = convertToID( col + 1 , row + 0 );
  328.  
  329. pos1 = fVec;
  330. pos2 = getVertPosition( col + 1 , row +0 );
  331.  
  332. stiffness = (row + 0 ) / ribbonLength;
  333.  
  334. }else{
  335.  
  336. id1 = convertToID( col + 0 , row + 1 );
  337. id2 = convertToID( col + 1 , row + 1 );
  338.  
  339. pos1 = getVertPosition( col + 0 , row +1 );
  340. pos2 = getVertPosition( col + 1 , row +1 );
  341.  
  342. stiffness = (row+1 ) / ribbonLength;
  343.  
  344. }
  345.  
  346. rightLinkValues[li2++] = id1;
  347. rightLinkValues[li2++] = id2;
  348. rightLinkValues[li2++] = ( pos1 - pos2 ).magnitude;
  349. rightLinkValues[li2++] = stiffness;
  350.  
  351. pos1 = fVec;
  352. pos2 = getVertPosition( col -1 , row -1 );
  353.  
  354. stiffness = (row-.5f) / ribbonLength;
  355.  
  356. diagonalDownLinkValues[li3++] = id;
  357. diagonalDownLinkValues[li3++] = convertToID( col - 1 , row - 1 );
  358. diagonalDownLinkValues[li3++] = ( pos1 - pos2 ).magnitude;
  359. diagonalDownLinkValues[li3++] = stiffness;
  360.  
  361. pos1 = fVec;
  362. pos2 = getVertPosition( col +1 , row +1 );
  363.  
  364. stiffness = (row+.5f) / ribbonLength;
  365.  
  366. diagonalUpLinkValues[li4++] = id;
  367. diagonalUpLinkValues[li4++] = convertToID( col + 1 , row + 1 );
  368. diagonalUpLinkValues[li4++] = ( pos1 - pos2 ).magnitude;
  369. diagonalUpLinkValues[li4++] = stiffness;
  370.  
  371. }
  372.  
  373.  
  374.  
  375.  
  376.  
  377.  
  378.  
  379.  
  380.  
  381. Vert vert = new Vert();
  382.  
  383. float stuck = 0;
  384. if( fVec.magnitude < .2f ){
  385. stuck = 1;
  386. fVec += new Vector3( 0, .2f - fVec.magnitude , 0 );
  387. fVec = fVec.normalized * .2f;
  388. //print( fVec );
  389. }
  390.  
  391.  
  392. vert.pos = fVec * 1.000001f;
  393.  
  394. vert.oPos = fVec- new Vector3( 0 , 0 , 0 );
  395.  
  396.  
  397. vert.ogPos = fVec ;
  398. vert.norm = new Vector3( 0 , 1 , 0 );
  399. vert.uv = new Vector2( uvX , uvY );
  400.  
  401. vert.mass = 0.3f;
  402. if( col == 0 || col == ribbonWidth || row == 0 || row == ribbonLength ){
  403. vert.mass = 2.0f;
  404. }
  405.  
  406.  
  407. vert.ids = new float[8];
  408. vert.ids[0] = convertToID( col + 1 , row + 0 );
  409. vert.ids[1] = convertToID( col + 1 , row - 1 );
  410. vert.ids[2] = convertToID( col + 0 , row - 1 );
  411. vert.ids[3] = convertToID( col - 1 , row - 1 );
  412. vert.ids[4] = convertToID( col - 1 , row - 0 );
  413. vert.ids[5] = convertToID( col - 1 , row + 1 );
  414. vert.ids[6] = convertToID( col - 0 , row + 1 );
  415. vert.ids[7] = convertToID( col + 1 , row + 1 );
  416.  
  417. vert.debug = new Vector3(stuck,1,0);
  418. //Vector2 d = new Vector2(vert.uv.x-.5f,vert.uv.y-.5f);
  419. //
  420. //if(d.magnitude < .02 ){
  421. // vert.debug= new Vector3(1,1,0);
  422. //}
  423.  
  424. inValues[index++] = vert.pos.x;
  425. inValues[index++] = vert.pos.y;
  426. inValues[index++] = vert.pos.z;
  427.  
  428. inValues[index++] = vert.oPos.x;
  429. inValues[index++] = vert.oPos.y;
  430. inValues[index++] = vert.oPos.z;
  431.  
  432. inValues[index++] = vert.ogPos.x;
  433. inValues[index++] = vert.ogPos.y;
  434. inValues[index++] = vert.ogPos.z;
  435.  
  436. inValues[index++] = vert.norm.x;
  437. inValues[index++] = vert.norm.y;
  438. inValues[index++] = vert.norm.z;
  439.  
  440. inValues[index++] = vert.uv.x;
  441. inValues[index++] = vert.uv.y;
  442.  
  443. inValues[index++] = 0;
  444.  
  445. inValues[index++] = vert.ids[0];
  446. inValues[index++] = vert.ids[1];
  447. inValues[index++] = vert.ids[2];
  448. inValues[index++] = vert.ids[3];
  449. inValues[index++] = vert.ids[4];
  450. inValues[index++] = vert.ids[5];
  451. inValues[index++] = vert.ids[6];
  452. inValues[index++] = vert.ids[7];
  453.  
  454. inValues[index++] = vert.debug.x;
  455. inValues[index++] = vert.debug.y;
  456. inValues[index++] = vert.debug.z;
  457.  
  458. }
  459. }
  460. }
  461.  
  462. _vertBuffer.SetData(inValues);
  463.  
  464. _upLinkBuffer.SetData(upLinkValues);
  465. _rightLinkBuffer.SetData(rightLinkValues);
  466. _diagonalUpLinkBuffer.SetData(diagonalUpLinkValues);
  467. _diagonalDownLinkBuffer.SetData(diagonalDownLinkValues);
  468.  
  469.  
  470. }
  471.  
  472.  
  473.  
  474. public float convertToID( float col , float row ){
  475.  
  476. float id;
  477.  
  478. if( col >= ribbonWidth ){ col -= ribbonWidth;}
  479. if( col < 0 ){ col += ribbonWidth; }
  480.  
  481. // Instead of returning negative numbers,
  482. // we are going to connect to other side of cloth
  483. // to make it a tube!
  484. if( row >= ribbonLength ){ return -10; }
  485. if( row < 0 ){ return -20; }
  486.  
  487. id = row * ribbonWidth + col;
  488.  
  489. return id;
  490.  
  491. }
  492.  
  493. private void doConstraint( float v , int offset , ComputeBuffer b ){
  494.  
  495. // Which link in compute are we doing
  496. constraintPass.SetInt("_Offset" , offset );
  497. constraintPass.SetFloat("_Multiplier" , v );
  498. constraintPass.SetBuffer( _kernelconstraint , "linkBuffer" , b );
  499.  
  500. //TODO: only need to dispatch for 1/9th of the buffer size!
  501. constraintPass.Dispatch( _kernelconstraint , strideX / 2 , strideY , strideZ );
  502.  
  503. }
  504.  
  505.  
  506. private void assignTransform(){
  507.  
  508. Matrix4x4 m = transform.localToWorldMatrix;
  509.  
  510. float[] matrixFloats = new float[]
  511. {
  512. m[0,0], m[1, 0], m[2, 0], m[3, 0],
  513. m[0,1], m[1, 1], m[2, 1], m[3, 1],
  514. m[0,2], m[1, 2], m[2, 2], m[3, 2],
  515. m[0,3], m[1, 3], m[2, 3], m[3, 3]
  516. };
  517.  
  518. forcePass.SetFloats("transform", matrixFloats);
  519.  
  520. }
  521.  
  522. private void Dispatch() {
  523.  
  524.  
  525. v1 = transform.TransformPoint(new Vector3( 0 , -.1f , -.2f ));
  526. v2 = new Vector3( 0 , v1.y * .15f , 0 );
  527. v1 = v1 - v2;
  528. bodyPos = v1;//transform.TransformPoint( v1 );
  529.  
  530.  
  531. assignTransform();
  532.  
  533. forcePass.SetFloat( "_DeltaTime" , Time.time - oTime );
  534. forcePass.SetFloat( "_Time" , Time.time + StartTime );
  535. //forcePass.SetFloat( "_Reset" , );
  536.  
  537. //forcePass.SetVector( "_ChestPosition" , bodyPos );
  538. //forcePass.SetVector( "_Hand1" , hand1.transform.position );
  539. //forcePass.SetVector( "_Hand2" , hand2.transform.position );
  540.  
  541. forcePass.SetFloat("_AttractToHand", attractToHand);
  542. forcePass.SetFloat("_RepelFromHand", repelFromHand);
  543. forcePass.SetFloat("_Gravity", gravity);
  544.  
  545. ///oTime = Time.time;
  546.  
  547.  
  548.  
  549. forcePass.SetInt( "_RibbonWidth" , ribbonWidth );
  550. forcePass.SetInt( "_RibbonLength" , ribbonLength );
  551. // print( PF.pillows);
  552. //forcePass.SetInt( "_NumShapes" , PF.pillows.Shapes.Length );
  553. //forcePass.SetInt( "_NumberHands" , PF.handBufferInfo.GetComponent<HandBuffer>().numberHands );
  554.  
  555. //print( HumanBuffer.GetComponent<HumanBuffer>().numberHumans );
  556.  
  557. //forcePass.SetInt( "_NumberHumans" , humanBuffer.numberHumans );
  558. //forcePass.SetBuffer( _kernelforce , "humanBuffer" , humanBuffer._buffer );
  559. forcePass.SetBuffer( _kernelforce , "vertBuffer" , _vertBuffer );
  560. forcePass.SetBuffer( _kernelforce , "transformBuffer" , _transformBuffer );
  561.  
  562. //if( PF.pillows._shapeBuffer != null ){
  563. // forcePass.SetBuffer( _kernelforce , "shapeBuffer" , PF.pillows._shapeBuffer );
  564. //}
  565. //forcePass.SetBuffer( _kernelforce , "handBuffer" , PF.handBufferInfo.GetComponent<HandBuffer>()._handBuffer );
  566.  
  567. forcePass.Dispatch( _kernelforce , strideX , strideY , strideZ );
  568.  
  569.  
  570. constraintPass.SetInt( "_RibbonWidth" , ribbonWidth );
  571. constraintPass.SetInt( "_RibbonLength" , ribbonLength );
  572.  
  573. constraintPass.SetBuffer( _kernelconstraint , "vertBuffer" , _vertBuffer );
  574.  
  575. doConstraint( 1 , 1 , _upLinkBuffer );
  576. doConstraint( 1 , 1 , _rightLinkBuffer );
  577. doConstraint( 1 , 1 , _diagonalDownLinkBuffer );
  578. doConstraint( 1 , 1 , _diagonalUpLinkBuffer );
  579.  
  580. doConstraint( 1 , 0 , _upLinkBuffer );
  581. doConstraint( 1 , 0 , _rightLinkBuffer );
  582. doConstraint( 1 , 0 , _diagonalDownLinkBuffer );
  583. doConstraint( 1 , 0 , _diagonalUpLinkBuffer );
  584.  
  585.  
  586. //calculate our normals
  587. normalPass.SetBuffer( _kernelnormal , "vertBuffer" , _vertBuffer );
  588. normalPass.Dispatch( _kernelnormal , strideX , strideY , strideZ );
  589.  
  590. oTime = Time.time;
  591.  
  592. }
  593.  
  594. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement