LensFlare.htm 22 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918
  1. <html xmlns:MSHelp="http://msdn.microsoft.com/mshelp" xmlns:msxsl="urn:schemas-microsoft-com:xslt" xmlns:xanx="http://schemas.microsoft.com/developer/xanx/2005"><head><meta http-equiv="Content-Type" content="text/html; charset=utf-8" /><meta name="save" content="history" /><title>Lens Flare Sample</title>
  2. <style><!--
  3. /***********************************************************
  4. * SCRIPT-SUPPORTING STYLES
  5. ***********************************************************/
  6. /* Defines the userData cache persistence mechanism. */
  7. .userDataStyle
  8. {
  9. behavior: url(#default#userData);
  10. }
  11. /* Used to save the scroll bar position when navigating away from a page. */
  12. div.saveHistory
  13. {
  14. behavior: url(#default#saveHistory);
  15. }
  16. /* Formats the expand/collapse images for all collapsible regions. */
  17. img.toggle
  18. {
  19. border: 0;
  20. margin-right: 5;
  21. }
  22. /* Formats the Language filter drop-down image. */
  23. img#languageFilterImage
  24. {
  25. border: 0;
  26. margin-left: 0;
  27. vertical-align: middle;
  28. }
  29. /* Formats the Members Options filter drop-down image. */
  30. img#membersOptionsFilterImage
  31. {
  32. border: 0;
  33. margin-left: 0;
  34. vertical-align: middle;
  35. }
  36. /* Formats the Collapse All/Expand All images. */
  37. img#toggleAllImage
  38. {
  39. margin-left: 0;
  40. vertical-align: middle;
  41. }
  42. /* Supports XLinks */
  43. MSHelp\:link
  44. {
  45. text-decoration: underline;
  46. color: #0000ff;
  47. hoverColor: #3366ff;
  48. filterString: ;
  49. }
  50. body
  51. {
  52. background: #FFFFFF;
  53. color: #000000;
  54. font-family: Verdana;
  55. font-size: medium;
  56. font-style: normal;
  57. font-weight: normal;
  58. margin-top: 0;
  59. margin-bottom: 0;
  60. margin-left: 0;
  61. margin-right: 0;
  62. width: 100%;
  63. /*font-size: 110%;*/
  64. }
  65. div.section
  66. {
  67. margin-left: 15px;
  68. }
  69. div.hxnx5
  70. {
  71. margin-left: 1.5em;
  72. }
  73. /* Font for all headings */
  74. h1, h2, h3, h4, h5, h6
  75. {
  76. font-family: Verdana, Arial, Helvetica, sans-serif;
  77. margin-top: 18;
  78. margin-bottom: 8;
  79. font-weight: bold;
  80. }
  81. h1
  82. {
  83. font-size: 130%;
  84. color: #003399;
  85. }
  86. div#scrollyes h1 /* Changes font size for full-scrolling topic */
  87. {
  88. font-size: 150%;
  89. }
  90. h2
  91. {
  92. font-size: 122%;
  93. }
  94. h3
  95. {
  96. font-size: 115%;
  97. margin-top: 9;
  98. margin-bottom: 4;
  99. }
  100. h4
  101. {
  102. font-size: 115%;
  103. margin-top: 9;
  104. margin-bottom: 4;
  105. }
  106. h5
  107. {
  108. font-size: 100%;
  109. margin-top: 9;
  110. margin-bottom: 4;
  111. }
  112. h6
  113. {
  114. font-size: 100%;
  115. margin-top: 9;
  116. margin-bottom: 4;
  117. }
  118. ul p, ol p, dl p
  119. {
  120. margin-left: 0em;
  121. }
  122. p
  123. {
  124. margin-top: .6em;
  125. margin-bottom: .6em;
  126. }
  127. td p
  128. {
  129. margin-top: 0.0em;
  130. margin-bottom: 0.6em;
  131. }
  132. dd p
  133. {
  134. margin-top: 0.0em;
  135. margin-bottom: 0.6em;
  136. }
  137. .image
  138. {
  139. text-align: center;
  140. }
  141. dl
  142. {
  143. margin-top: 0em;
  144. margin-bottom: 1.3em;
  145. }
  146. dd
  147. {
  148. margin-bottom: 0em;
  149. margin-left: 1.5em;
  150. }
  151. dl.glossary dd
  152. {
  153. margin-bottom: 0em;
  154. margin-left: 1.5em;
  155. }
  156. dt
  157. {
  158. margin-top: .6em;
  159. margin-bottom: 1;
  160. }
  161. ul, ol
  162. {
  163. margin-top: 0.6em;
  164. margin-bottom: 0.6em;
  165. }
  166. ol
  167. {
  168. margin-left: 2.5em;
  169. }
  170. ul
  171. {
  172. list-style-type: disc;
  173. margin-left: 1.9em;
  174. }
  175. li
  176. {
  177. margin-bottom: 0.4em;
  178. }
  179. ul ol, ol ol
  180. {
  181. list-style-type: lower-alpha;
  182. }
  183. pre
  184. {
  185. margin-top: .6em;
  186. margin-bottom: .6em;
  187. font: 105% Lucida, mono;
  188. color: #000066;
  189. }
  190. code
  191. {
  192. font-family: Monospace, Courier New, Courier;
  193. font-size: 105%;
  194. color: #000066;
  195. }
  196. table.userdata td
  197. {
  198. background: #ffffff;
  199. background-color: #F5F5F5;
  200. border-color: #ffffff;
  201. border: none;
  202. }
  203. table.clsWarning
  204. {
  205. background: #ffffff;
  206. padding: 0px;
  207. margin: 0px;
  208. border: none;
  209. }
  210. table.clsWarning td
  211. {
  212. padding: 0px;
  213. margin: 0px;
  214. background: #ffffff;
  215. vertical-align: middle;
  216. font-size: 70%;
  217. }
  218. div#mainSection table
  219. {
  220. width: 95%;
  221. background: #ffffff;
  222. margin-top: 5px;
  223. margin-bottom: 5px;
  224. }
  225. div#mainSection table th
  226. {
  227. padding: 5px 6px;
  228. background: #EFEFF7;
  229. text-align: left;
  230. font-size: 70%;
  231. vertical-align: bottom;
  232. border-bottom: 1px solid #C8CDDE;
  233. }
  234. div#mainSection table td
  235. {
  236. padding: 5px 5px;
  237. background: #F7F7FF;
  238. vertical-align: top;
  239. font-size: 70%;
  240. border-bottom: 1px solid #D5D5D3;
  241. }
  242. div#syntaxCodeBlocks table th
  243. {
  244. padding: 1px 6px;
  245. color: #000066;
  246. }
  247. div#syntaxCodeBlocks table td
  248. {
  249. padding: 1px 5px;
  250. }
  251. /* Applies to the running header text in the first row of the upper table in the
  252. non-scrolling header region. */
  253. span#runningHeaderText
  254. {
  255. color: #003399;
  256. font-size: 90%;
  257. padding-left: 13;
  258. }
  259. /* Applies to the topic title in the second row of the upper table in the
  260. non-scrolling header region. */
  261. span#nsrTitle
  262. {
  263. color: #003399;
  264. font-size: 120%;
  265. font-weight: 600;
  266. padding-left: 13;
  267. }
  268. /* Applies to everything below the non-scrolling header region. */
  269. div#mainSection
  270. {
  271. font-size: 70%;
  272. width: 100%;
  273. }
  274. /* Applies to everything below the non-scrolling header region, minus the footer. */
  275. div#mainBody
  276. {
  277. font-size: 90%;
  278. margin-left: 15;
  279. margin-top: 10;
  280. padding-bottom: 20;
  281. }
  282. /* Adds right padding for all blocks in mainBody */
  283. div#mainBody p, div#mainBody ol, div#mainBody ul, div#mainBody dl
  284. {
  285. padding-right: 5;
  286. }
  287. div#mainBody div.alert, div#mainBody div.code, div#mainBody div.tableSection
  288. {
  289. width:98.9%;
  290. }
  291. div.alert p, div.code p
  292. {
  293. margin-top:5;
  294. margin-bottom:8;
  295. }
  296. /*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Begin Note Styles - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
  297. div#mainSection div.alert table
  298. {
  299. border: 0;
  300. }
  301. div#mainSection div.alert table th
  302. {
  303. padding-top: 0;
  304. padding-bottom: 0;
  305. padding-left: 5;
  306. padding-right: 5;
  307. }
  308. div#mainSection div.alert table td
  309. {
  310. padding-left: 5;
  311. padding-right: 5;
  312. }
  313. img.note
  314. {
  315. border: 0;
  316. margin-left: 0;
  317. margin-right: 3;
  318. }
  319. /*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - End Note Styles - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
  320. /*- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Begin Non-scrolling Header Region Styles - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -*/
  321. /* Applies to the entire non-scrolling header region. */
  322. div#header
  323. {
  324. background-color: #D4DFFF;
  325. padding-top: 0;
  326. padding-bottom: 0;
  327. padding-left: 0;
  328. padding-right: 0;
  329. width: 100%;
  330. }
  331. /* Applies to both tables in the non-scrolling header region. */
  332. div#header table
  333. {
  334. margin-top: 0;
  335. margin-bottom: 0;
  336. border-bottom-color: #C8CDDE;
  337. border-bottom-style: solid;
  338. border-bottom-width: 1;
  339. background: #D4DFFF;
  340. width: 100%;
  341. }
  342. /* Applies to cells in both tables in the non-scrolling header region. */
  343. div#header table td
  344. {
  345. color: #0000FF;
  346. font-size: 70%;
  347. padding-right: 20;
  348. padding-top: 1;
  349. padding-bottom: 1;
  350. border: none;
  351. background: #D4DFFF;
  352. }
  353. /* Applies to the last row in the upper table of the non-scrolling header region. Text
  354. in this row includes See Also, Constructors, Methods, and Properties. */
  355. div#header table tr#headerTableRow3 td
  356. {
  357. padding-bottom: 2;
  358. padding-top: 5;
  359. padding-left: 15;
  360. }
  361. /* Applies to the lower table in the non-scrolling header region. Text in this table
  362. includes Collapse All/Expand All, Language Filter, and Members Options. */
  363. div#header table#bottomTable
  364. {
  365. border-top-color: #FFFFFF;
  366. border-top-style: solid;
  367. border-top-width: 1;
  368. text-align: left;
  369. padding-left: 15;
  370. }
  371. blockquote
  372. {
  373. margin-left: 3.8em;
  374. margin-right: 3.8em;
  375. margin-top: .6em;
  376. margin-bottom: .6em;
  377. }
  378. sup
  379. {
  380. text-decoration: none;
  381. font-size: smaller;
  382. }
  383. a:link
  384. {
  385. color: #0000FF;
  386. /* font-weight: bold */
  387. }
  388. a:visited
  389. {
  390. color: #0000AA;
  391. /* font-weight: bold */
  392. }
  393. a:hover
  394. {
  395. color: #3366FF;
  396. /* font-weight: bold */
  397. }
  398. .label
  399. {
  400. font-weight: bold;
  401. margin-top: 1em;
  402. margin-left: -26px;
  403. }
  404. .tl
  405. {
  406. margin-bottom: .75em;
  407. }
  408. .atl
  409. {
  410. padding-left: 1.5em;
  411. padding-bottom: .75em;
  412. }
  413. .cfe
  414. {
  415. font-weight: bold;
  416. }
  417. .mini
  418. {
  419. font-size: smaller;
  420. }
  421. .dt
  422. {
  423. margin-bottom: -.6em;
  424. }
  425. .indent
  426. {
  427. margin-left: 1.9em;
  428. margin-right: 1.9em;
  429. }
  430. .product
  431. {
  432. text-align: right;
  433. color: #333333;
  434. font-size: smaller;
  435. font-style: italic;
  436. }
  437. .buttonbarshade
  438. {
  439. position: relative;
  440. margin: 0;
  441. left: 0px;
  442. top: 2;
  443. width: 50%;
  444. height: 40px;
  445. }
  446. .buttonbartable
  447. {
  448. position: absolute;
  449. margin: 0;
  450. padding:0;
  451. border:0;
  452. left:0px;
  453. top: 2;
  454. width: 100%;
  455. height: 40px;
  456. }
  457. /* background color, font for header */
  458. table.buttonbartable td, table.buttonbarshade td
  459. {
  460. background: #ffffff; /*#5177B8; #80C615;*/
  461. border-left: 0px solid #80C615;
  462. margin: 0;
  463. padding: 0px 0px 0px 0px;
  464. font-family: Impact, sans-serif;
  465. font-size: 14pt;
  466. }
  467. table.buttonbartable td.button1
  468. {
  469. background: #5177B8; /*#80C615;*/;
  470. padding: 0;
  471. font-weight: bold;
  472. text-align: center;
  473. cursor: hand;
  474. }
  475. table.buttonbartable td.button2
  476. {
  477. background: #5177B8; /*#80C615;*/;
  478. font-weight: bold;
  479. text-align: center;
  480. }
  481. table.buttonbartable td.button3
  482. {
  483. background: #5177B8; /*#80C615;*/;
  484. font-weight: bold;
  485. text-align: center;
  486. }
  487. table.buttonbartable td.runninghead
  488. {
  489. padding-left: 0px;
  490. font-style: italic;
  491. text-align: left;
  492. }
  493. .version
  494. {
  495. text-align: left;
  496. color: #000000;
  497. margin-top: 3em;
  498. margin-left: -26px;
  499. font-size: smaller;
  500. font-style: italic;
  501. }
  502. .lang, .ilang
  503. {
  504. color: #0000ff;
  505. font: normal 7pt Arial, Helvetica, sans-serif;
  506. }
  507. div.langMenu
  508. {
  509. position: absolute;
  510. z-index: 1;
  511. width: 96pt;
  512. padding: 8pt;
  513. visibility: hidden;
  514. border: 1px solid #000000;
  515. background: #ffffd0;
  516. }
  517. div.langMenu ul
  518. {
  519. padding-left: 2em;
  520. margin-left: 0;
  521. }
  522. div.filtered
  523. {
  524. margin: 4pt 0 8pt -26px;
  525. padding: 4px 4px 8px 26px;
  526. width: 100%;
  527. border: 2px solid #aaaacc;
  528. background: #ffffff;
  529. }
  530. div.filtered2
  531. {
  532. margin: 4pt 0 8pt -26px;
  533. padding: 4px 4px 8px 26px;
  534. width: 100%;
  535. border: none;
  536. background: #ffffff;
  537. }
  538. div.filtered h1, div.filtered h2, div.filtered h3, div.filtered h4
  539. {
  540. margin-left: -22px;
  541. }
  542. div.filtered span.lang
  543. {
  544. position: relative;
  545. left: -22px;
  546. }
  547. div.reftip
  548. {
  549. position: absolute;
  550. z-index: 1;
  551. padding: 8pt;
  552. visibility: hidden;
  553. border: 1px solid #000000;
  554. background: #ffffd0;
  555. }
  556. a.synParam
  557. {
  558. color: #0000FF;
  559. /*color: #3F7800;*/
  560. /*color: #8DC54F;*/
  561. text-decoration: none;
  562. font-weight: normal;
  563. }
  564. a.synParam:hover
  565. {
  566. text-decoration: underline;
  567. font-weight: normal;
  568. }
  569. div.sapop
  570. {
  571. position: absolute;
  572. z-index: 1;
  573. left: 26px;
  574. width: 100%;
  575. padding: 10px 10px 10px 36px;
  576. visibility: hidden;
  577. border: 1px solid #000000;
  578. background: #ffffd0;
  579. }
  580. div.footer
  581. {
  582. width: 100%;
  583. border: none;
  584. background: #ffffff;
  585. margin-top: 18pt;
  586. padding-bottom: 12pt;
  587. color: #0000FF;
  588. /*color: #228B22; */
  589. text-align: center;
  590. font-size: 76%;
  591. }
  592. div.preliminary
  593. {
  594. margin-top: 8pt;
  595. padding-bottom: 12pt;
  596. color: #A0A0A0;
  597. }
  598. /* A procedure section. eg. 'To create a file', 'To add a value' */
  599. div.proc
  600. {
  601. margin-left: 0.5em;
  602. }
  603. /* The title of a 'procedure' section. */
  604. div.proc h3
  605. {
  606. font-family: Verdana, Arial, Helvetica, sans-serif;
  607. font-weight: bold;
  608. font-size: 115%;
  609. margin-top: 1em;
  610. margin-bottom: 0.4em;
  611. margin-left: -0.5em;
  612. color: #003399;
  613. }
  614. div.proc ul
  615. {
  616. margin-left: 1.5em;
  617. }
  618. div.proc ol
  619. {
  620. margin-left: 2.0em;
  621. }
  622. .note
  623. {
  624. margin-left: 14pt;
  625. margin-right: 12pt;
  626. }
  627. .indent1
  628. {
  629. margin-left: 12pt;
  630. }
  631. .indent2
  632. {
  633. margin-left: 24pt;
  634. }
  635. .indent3
  636. {
  637. margin-left: 36pt;
  638. }
  639. p.proch
  640. {
  641. padding-left: 16px;
  642. }
  643. p.proch img
  644. {
  645. position: relative;
  646. vertical-align: top;
  647. left: -18px;
  648. margin-right: -14px;
  649. margin-bottom: -18px;
  650. }
  651. div.clsPlatSpec
  652. {
  653. background-color:#FFF8DC;
  654. border-style:solid;
  655. border-width:1pt 0pt 0pt 1pt;
  656. border-color:#ffE4C4;
  657. margin-top:0.6em;
  658. width:100%;
  659. }
  660. /* Applies to the language labels in the Language Filter drop-down list. */
  661. .languageFilter
  662. {
  663. color: #0000FF;
  664. cursor:hand;
  665. text-decoration:underline;
  666. padding-bottom:4;
  667. }
  668. /* Dropdown areas */
  669. #languageSpan {
  670. position: absolute;
  671. visibility: hidden;
  672. border-style: solid;
  673. border-width: 1px;
  674. border-color: #C8CDDE;
  675. background: #d4dfff;
  676. padding: 4px;
  677. font-size: 70%;
  678. }
  679. #membersOptionsSpan {
  680. position: absolute;
  681. visibility: hidden;
  682. border-style: solid;
  683. border-width: 1px;
  684. border-color: #C8CDDE;
  685. background: #d4dfff;
  686. padding: 4px;
  687. font-size: 70%;
  688. }
  689. --></style>
  690. <xml>
  691. <MSHelp:TOCTitle Title="Lens Flare Sample" />
  692. <MSHelp:RLTitle Title="Lens Flare Sample" />
  693. <MSHelp:Keyword Index="A" Term="O:Microsoft.Xna.LensFlare" />
  694. <MSHelp:Keyword Index="A" Term="fe380a9e-b56f-88d5-e4d6-6bcda683d1ab" />
  695. <MSHelp:Keyword Index="K" Term="Lens Flare Sample" />
  696. <MSHelp:Attr Name="AssetID" Value="fe380a9e-b56f-88d5-e4d6-6bcda683d1ab" />
  697. <MSHelp:Attr Name="Locale" Value="en-us" />
  698. <MSHelp:Attr Name="CommunityContent" Value="1" />
  699. <MSHelp:Attr Name="TopicType" Value="kbOrient" />
  700. </xml>
  701. </head><body><div id="mainSection"><div id="mainBody">
  702. <h1>Lens Flare Sample</h1>
  703. This sample shows you how to implement a lens flare effect by using occlusion queries to detect when the sun is hidden behind the landscape.
  704. <a id="ID2EK" name="ID2EK"> </a><h1 class="heading">Sample Overview</h1><div id="ID2EK" class="hxnx1">
  705. <p>Lens flare tries to simulate how bright lights behave when they shine into a film camera. Computer games often have a hard time conveying an impression of brightness because monitors and televisions have only a limited range. After all, it is impossible to have a pixel brighter than white. How can you show the difference between a character wearing a white t-shirt, which is not very bright, and the sun, which is very bright indeed? The solution is to emulate what happens when a movie director points a camera directly at a bright light source. The excess light bounces around inside the camera. This excess light overloads the lens and creates strange glows and flares in places other than where the light is supposed to be shining directly. Most movie directors try to avoid these effects. However, some directors use them for artistic effect. Games can do the same thing. Games can emulate the flares that would be produced inside a physical camera. The flares provide a visual cue that indicates the brightness of the light.</p>
  706. <p>The lens flare effect in this sample is formed of two components: a large, soft glow, and a row of smaller circular flare shapes.</p>
  707. <p>The sample uses hardware occlusion queries to efficiently detect when the sun is hidden behind the landscape. This enables you to fade out the lens flare effect when the sun is not visible.</p>
  708. <a id="ID2EU" name="ID2EU"> </a><h2 class="subHeading">Sample Controls</h2><div id="ID2EU" class="hxnx2">
  709. <p>This sample uses the following keyboard and gamepad controls.</p>
  710. <table>
  711. <tr>
  712. <th>Action</th>
  713. <th>Keyboard control</th>
  714. <th>Gamepad control</th>
  715. </tr>
  716. <tr>
  717. <td>Rotate the camera</td>
  718. <td>UP ARROW, DOWN ARROW, LEFT ARROW, and RIGHT ARROW</td>
  719. <td>Right thumb stick</td>
  720. </tr>
  721. <tr>
  722. <td>Move the camera</td>
  723. <td>W, S, A, D</td>
  724. <td>Left thumb stick</td>
  725. </tr>
  726. <tr>
  727. <td>Reset the camera position</td>
  728. <td>R</td>
  729. <td>Right thumb stick press</td>
  730. </tr>
  731. <tr>
  732. <td>Exit the sample</td>
  733. <td>ESC or ALT+F4</td>
  734. <td>
  735. <b>BACK</b>
  736. </td>
  737. </tr>
  738. </table>
  739. </div>
  740. </div>
  741. <a id="ID2EPC" name="ID2EPC"> </a><h1 class="heading">How the Sample Works</h1><div id="ID2EPC" class="hxnx1">
  742. <p>The lens flare is built up out of two different effects. First, the sample draws a large, soft circular glow, which is centered on the sun. The glow is white in the center. It fades to transparent at the edge of the circle. These screenshots show the glow effect in isolation. The screen shot on the left shows the glow over a black background; the one on the right shows the glow over a terrain mesh.</p>
  743. <img src="Glow.png" />
  744. <p>Second, a number of flare sprites are positioned at arbitrary points along a 2D line. Three slightly different circular sprite textures are used to draw the flares. Each one is given a different scale and tint. You calculate flare positions by projecting the position of the sun on the 2D screen, then laying out each sprite along a line that runs from the sun through the center of the screen. This causes the flares to move position depending on the location of the sun. When the sun is near the middle of the screen, the flares will all be bunched up near the center. On the other hand, the flares will have a wider spacing when the sun is near the edge.</p>
  745. <p>The following screenshots show the flare effect in isolation. The image on the left shows the glow over a black background; the image on the right shows the glow over a terrain mesh.</p>
  746. <img src="Flares.png" />
  747. <p>Finally, these screenshots show both the glow and flare effects combined.</p>
  748. <img src="Final.png" />
  749. <p>If you move the camera around so the sun is hidden behind a hill, you will notice that the lens flare gradually fades out. This is an important part of making a convincing effect. It would not look very realistic if you could see the sun right through other pieces of scenery! The depth buffer on the graphics card usually handles this kind of sorting automatically. The depth buffer ensures that objects farther away will never be drawn over the top of closer objects. However, the hardware depth buffer does not work for lens flares. The flare is a 2D shape drawn over the top of the 3D scene. This means it cannot be depth sorted in the usual way. For example, you might have a flare in the lower-left corner of the screen, which is caused by the sun at the top right, and you want that flare to be visible because there is no scenery blocking the upper-right corner of the screen, even if the lower left where you have placed that flare is covered up by the terrain.</p>
  750. <p>The solution is to use a hardware occlusion query to make your own visibility determination. An occlusion query enables us mark a section of our drawing code. Later, you can ask the graphics card how many pixels it rendered. This works as follows:</p>
  751. <ol>
  752. <li>Draw the terrain mesh.</li>
  753. <li>Begin an occlusion query.</li>
  754. <li>
  755. Draw a small test 2D rectangle, centered on the sun, and placed at the largest possible Z depth. You can turn off color writes while you do this—the test rectangle will never show up on the screen. The graphics card will draw pixels only if they are not covered up by the terrain.
  756. </li>
  757. <li>End the occlusion query.</li>
  758. <li>Ask the occlusion query how many test pixels were drawn. This tells you what percentage of the sun is visible.</li>
  759. <li>Draw your flare effect, using the sun visibility to control the alpha.</li>
  760. </ol>
  761. <p>
  762. This works well, but it is inefficient, because the graphics card does not actually carry out a command as soon as you give the command. To speed things along, the graphics card runs in parallel with your CPU. When you call a drawing method, this writes a command into a buffer. At some later time, the graphics card will examine that buffer and carry out the command. So you cannot ask it questions like, "Draw this triangle. OK, how many pixels did you just draw?" because at the point where the CPU asks "how many pixels?," the GPU will not yet have noticed your original "Draw this triangle" request. You could wait for it to catch up enough to provide the occlusion result by going into a loop and testing the <b>OcclusionQuery.IsComplete</b> property until it becomes <b>true</b>, but that would be a waste of CPU time. You have better things to do with your CPU than just sit around waiting for the GPU!
  763. </p>
  764. <p>To keep the CPU and GPU running smoothly in parallel, you must delay your occlusion queries by one frame. Each time around the game loop, your query is now inverted: "How many query pixels did you draw during the previous frame? OK, now draw this triangle and remember the result for later." This way the GPU has plenty of time to get around to processing the command buffer before you ask it for the query result. The downside is that you are now a frame late in reading your occlusion information. Thus, you are choosing your flare alpha based on how much of the sun was visible during the previous frame, rather than on the latest camera position. This sounds bad, but in practice the camera tends to move quite slowly. The flare fades smoothly in and out as the sun goes behind the scenery. This means the off-by-one-frame timing error tends to be small and is hard to notice. You can see it most clearly when the sample first starts up. No lens flare is drawn during the first frame. While the sun is supposed to be visible, the GPU has not yet had a chance to finish your first occlusion query.</p>
  765. <p>
  766. To display the occlusion query test rectangle on your screen, comment out the line where <b>LensFlareComponent.UpdateOcclusion</b> sets <b>GraphicsDevice.BlendState</b> to <b>ColorWriteDisable</b>.
  767. </p>
  768. <p>
  769. The lens flare is implemented as a <b>DrawableGameComponent</b>, so it can easily be reused in your own games. Just add a <b>LensFlareComponent</b> to your <b>Game.Components</b> collection, and make sure you set its <b>View</b>, <b>Projection</b>, and <b>LightDirection</b>.
  770. </p>
  771. </div>
  772. <a id="ID2E3E" name="ID2E3E"> </a><h1 class="heading">Extending the Sample</h1><div id="ID2E3E" class="hxnx1">
  773. <p>
  774. You can easily change the size, color, and position of the flare sprites by altering the declaration of the <b>LensFlareComponent.flares</b> array.
  775. </p>
  776. <p>Try adding rays as lines (or thin triangles) that fan out from the sun toward the edge of the screen.</p>
  777. <p>
  778. Try combining this lens flare effect with the bloom post-processing technique from the <b>Bloom Sample</b>.
  779. </p>
  780. <p>This sample draws a single lens flare centered on the sun. However, a game with more than one light source (perhaps drawing a night scene with car headlamps, or a game set in space) might want to tone down the effect, and then apply it to each of its many lights.</p>
  781. </div>
  782. </div><div class="footer" id="footer"><p>© 2010 Microsoft Corporation. All rights reserved.<br />Send feedback to <a href="mailto:[email protected]?subject=Documentation Feedback: Lens Flare Sample">[email protected]</a>.</p></div></div></body></html>