广告位联系
返回顶部
分享到

花瓣漫天飞舞js特效,简单浪漫

JavaScript 来源:互联网 作者:佚名 发布时间:2023-01-03 21:10:54 人浏览
摘要

《黛玉葬花》是文学名著《红楼梦》中的经典片段。林黛玉最怜惜花,觉得花落以后埋在土里(文中指出的是花冢)最干净,说明她对美有独特的见解。她写了《葬花吟》,以花比喻自

《黛玉葬花》是文学名著《红楼梦》中的经典片段。林黛玉最怜惜花,觉得花落以后埋在土里(文中指出的是“花冢”)最干净,说明她对美有独特的见解。她写了《葬花吟》,以花比喻自己,在《红楼梦》中是最美丽的诗歌之一。

现代社会结婚、走红毯等很多时候会撒花瓣,满天花瓣和赏烟花一样,人们都觉得那一瞬间好美丽好浪漫。就像昙花一现,美好的事物总是很短暂,提醒人们去珍惜。这篇文章主要介绍了花瓣漫天飞舞js特效,简单浪漫,程序猿们可以跟女朋友一起欣赏

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

84

85

86

87

88

89

90

91

92

93

94

95

96

97

98

99

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121

122

123

124

125

126

127

128

129

130

131

132

133

134

135

136

137

138

139

140

141

142

143

144

145

146

147

148

149

150

151

152

153

154

155

156

157

158

159

160

161

162

163

164

165

166

167

168

169

170

171

172

173

174

175

176

177

178

179

180

181

182

183

184

185

186

187

188

189

190

191

192

193

194

195

196

197

198

199

200

201

202

203

204

205

206

207

208

209

210

211

212

213

214

215

216

217

218

219

220

221

222

223

224

225

226

227

228

229

230

231

232

233

234

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">

<HTML>

<HEAD>

    <TITLE>花瓣漫天飞舞入流水</TITLE>

    <META NAME="Generator" CONTENT="EditPlus">

    <META NAME="Author" CONTENT="">

    <META NAME="Keywords" CONTENT="">

    <META NAME="Description" CONTENT="">

    <style>

        html, body{

            width: 100%;

            height: 100%;

            margin: 0;

            padding: 0;

            overflow: hidden;

        }

        .container{

            width: 100%;

            height: 100%;

            margin: 0;

            padding: 0;

            background-color: #000000;

        }

    </style>

    <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

</HEAD>

  

<BODY>

  

<div id="jsi-cherry-container" class="container"></div>

<script>

    var RENDERER = {

        INIT_CHERRY_BLOSSOM_COUNT : 30,

        MAX_ADDING_INTERVAL : 10,

  

        init : function(){

            this.setParameters();

            this.reconstructMethods();

            this.createCherries();

            this.render();

        },

        setParameters : function(){

            this.$container = $('#jsi-cherry-container');

            this.width = this.$container.width();

            this.height = this.$container.height();

            this.context = $('<canvas />').attr({width : this.width, height : this.height}).appendTo(this.$container).get(0).getContext('2d');

            this.cherries = [];

            this.maxAddingInterval = Math.round(this.MAX_ADDING_INTERVAL * 1000 / this.width);

            this.addingInterval = this.maxAddingInterval;

        },

        reconstructMethods : function(){

            this.render = this.render.bind(this);

        },

        createCherries : function(){

            for(var i = 0, length = Math.round(this.INIT_CHERRY_BLOSSOM_COUNT * this.width / 1000); i < length; i++){

                this.cherries.push(new CHERRY_BLOSSOM(this, true));

            }

        },

        render : function(){

            requestAnimationFrame(this.render);

            this.context.clearRect(0, 0, this.width, this.height);

  

            this.cherries.sort(function(cherry1, cherry2){

                return cherry1.z - cherry2.z;

            });

            for(var i = this.cherries.length - 1; i >= 0; i--){

                if(!this.cherries[i].render(this.context)){

                    this.cherries.splice(i, 1);

                }

            }

            if(--this.addingInterval == 0){

                this.addingInterval = this.maxAddingInterval;

                this.cherries.push(new CHERRY_BLOSSOM(this, false));

            }

        }

    };

    var CHERRY_BLOSSOM = function(renderer, isRandom){

        this.renderer = renderer;

        this.init(isRandom);

    };

    CHERRY_BLOSSOM.prototype = {

        FOCUS_POSITION : 300,

        FAR_LIMIT : 600,

        MAX_RIPPLE_COUNT : 100,

        RIPPLE_RADIUS : 100,

        SURFACE_RATE : 0.5,

        SINK_OFFSET : 20,

  

        init : function(isRandom){

            this.x = this.getRandomValue(-this.renderer.width, this.renderer.width);

            this.y = isRandom ? this.getRandomValue(0, this.renderer.height) : this.renderer.height * 1.5;

            this.z = this.getRandomValue(0, this.FAR_LIMIT);

            this.vx = this.getRandomValue(-2, 2);

            this.vy = -2;

            this.theta = this.getRandomValue(0, Math.PI * 2);

            this.phi = this.getRandomValue(0, Math.PI * 2);

            this.psi = 0;

            this.dpsi = this.getRandomValue(Math.PI / 600, Math.PI / 300);

            this.opacity = 0;

            this.endTheta = false;

            this.endPhi = false;

            this.rippleCount = 0;

  

            var axis = this.getAxis(),

                theta = this.theta + Math.ceil(-(this.y + this.renderer.height * this.SURFACE_RATE) / this.vy) * Math.PI / 500;

            theta %= Math.PI * 2;

  

            this.offsetY = 40 * ((theta <= Math.PI / 2 || theta >= Math.PI * 3 / 2) ? -1 : 1);

            this.thresholdY = this.renderer.height / 2 + this.renderer.height * this.SURFACE_RATE * axis.rate;

            this.entityColor = this.renderer.context.createRadialGradient(0, 40, 0, 0, 40, 80);

            this.entityColor.addColorStop(0, 'hsl(330, 70%, ' + 50 * (0.3 + axis.rate) + '%)');

            this.entityColor.addColorStop(0.05, 'hsl(330, 40%,' + 55 * (0.3 + axis.rate) + '%)');

            this.entityColor.addColorStop(1, 'hsl(330, 20%, ' + 70 * (0.3 + axis.rate) + '%)');

            this.shadowColor = this.renderer.context.createRadialGradient(0, 40, 0, 0, 40, 80);

            this.shadowColor.addColorStop(0, 'hsl(330, 40%, ' + 30 * (0.3 + axis.rate) + '%)');

            this.shadowColor.addColorStop(0.05, 'hsl(330, 40%,' + 30 * (0.3 + axis.rate) + '%)');

            this.shadowColor.addColorStop(1, 'hsl(330, 20%, ' + 40 * (0.3 + axis.rate) + '%)');

        },

        getRandomValue : function(min, max){

            return min + (max - min) * Math.random();

        },

        getAxis : function(){

            var rate = this.FOCUS_POSITION / (this.z + this.FOCUS_POSITION),

                x = this.renderer.width / 2 + this.x * rate,

                y = this.renderer.height / 2 - this.y * rate;

            return {rate : rate, x : x, y : y};

        },

        renderCherry : function(context, axis){

            context.beginPath();

            context.moveTo(0, 40);

            context.bezierCurveTo(-60, 20, -10, -60, 0, -20);

            context.bezierCurveTo(10, -60, 60, 20, 0, 40);

            context.fill();

  

            for(var i = -4; i < 4; i++){

                context.beginPath();

                context.moveTo(0, 40);

                context.quadraticCurveTo(i * 12, 10, i * 4, -24 + Math.abs(i) * 2);

                context.stroke();

            }

        },

        render : function(context){

            var axis = this.getAxis();

  

            if(axis.y == this.thresholdY && this.rippleCount < this.MAX_RIPPLE_COUNT){

                context.save();

                context.lineWidth = 2;

                context.strokeStyle = 'hsla(0, 0%, 100%, ' + (this.MAX_RIPPLE_COUNT - this.rippleCount) / this.MAX_RIPPLE_COUNT + ')';

                context.translate(axis.x + this.offsetY * axis.rate * (this.theta <= Math.PI ? -1 : 1), axis.y);

                context.scale(1, 0.3);

                context.beginPath();

                context.arc(0, 0, this.rippleCount / this.MAX_RIPPLE_COUNT * this.RIPPLE_RADIUS * axis.rate, 0, Math.PI * 2, false);

                context.stroke();

                context.restore();

                this.rippleCount++;

            }

            if(axis.y < this.thresholdY || (!this.endTheta || !this.endPhi)){

                if(this.y <= 0){

                    this.opacity = Math.min(this.opacity + 0.01, 1);

                }

                context.save();

                context.globalAlpha = this.opacity;

                context.fillStyle = this.shadowColor;

                context.strokeStyle = 'hsl(330, 30%,' + 40 * (0.3 + axis.rate) + '%)';

                context.translate(axis.x, Math.max(axis.y, this.thresholdY + this.thresholdY - axis.y));

                context.rotate(Math.PI - this.theta);

                context.scale(axis.rate * -Math.sin(this.phi), axis.rate);

                context.translate(0, this.offsetY);

                this.renderCherry(context, axis);

                context.restore();

            }

            context.save();

            context.fillStyle = this.entityColor;

            context.strokeStyle = 'hsl(330, 40%,' + 70 * (0.3 + axis.rate) + '%)';

            context.translate(axis.x, axis.y + Math.abs(this.SINK_OFFSET * Math.sin(this.psi) * axis.rate));

            context.rotate(this.theta);

            context.scale(axis.rate * Math.sin(this.phi), axis.rate);

            context.translate(0, this.offsetY);

            this.renderCherry(context, axis);

            context.restore();

  

            if(this.y <= -this.renderer.height / 4){

                if(!this.endTheta){

                    for(var theta = Math.PI / 2, end = Math.PI * 3 / 2; theta <= end; theta += Math.PI){

                        if(this.theta < theta && this.theta + Math.PI / 200 > theta){

                            this.theta = theta;

                            this.endTheta = true;

                            break;

                        }

                    }

                }

                if(!this.endPhi){

                    for(var phi = Math.PI / 8, end = Math.PI * 7 / 8; phi <= end; phi += Math.PI * 3 / 4){

                        if(this.phi < phi && this.phi + Math.PI / 200 > phi){

                            this.phi = Math.PI / 8;

                            this.endPhi = true;

                            break;

                        }

                    }

                }

            }

            if(!this.endTheta){

                if(axis.y == this.thresholdY){

                    this.theta += Math.PI / 200 * ((this.theta < Math.PI / 2 || (this.theta >= Math.PI && this.theta < Math.PI * 3 / 2)) ? 1 : -1);

                }else{

                    this.theta += Math.PI / 500;

                }

                this.theta %= Math.PI * 2;

            }

            if(this.endPhi){

                if(this.rippleCount == this.MAX_RIPPLE_COUNT){

                    this.psi += this.dpsi;

                    this.psi %= Math.PI * 2;

                }

            }else{

                this.phi += Math.PI / ((axis.y == this.thresholdY) ? 200 : 500);

                this.phi %= Math.PI;

            }

            if(this.y <= -this.renderer.height * this.SURFACE_RATE){

                this.x += 2;

                this.y = -this.renderer.height * this.SURFACE_RATE;

            }else{

                this.x += this.vx;

                this.y += this.vy;

            }

            return this.z > -this.FOCUS_POSITION && this.z < this.FAR_LIMIT && this.x < this.renderer.width * 1.5;

        }

    };

    $(function(){

        RENDERER.init();

    });

</script>

</BODY>

</HTML>


版权声明 : 本文内容来源于互联网或用户自行发布贡献,该文观点仅代表原作者本人。本站仅提供信息存储空间服务和不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权, 违法违规的内容, 请发送邮件至2530232025#qq.cn(#换@)举报,一经查实,本站将立刻删除。
原文链接 :
相关文章
  • react后台系统最佳实践介绍
    本文主要讲三块内容:中后台系统的技术栈选型、hooks时代状态管理库的选型以及hooks的使用问题与解决方案。 1. 要做什么 我们的目标是搭
  • 花瓣漫天飞舞js特效,简单浪漫
    《黛玉葬花》是文学名著《红楼梦》中的经典片段。林黛玉最怜惜花,觉得花落以后埋在土里(文中指出的是花冢)最干净,说明她对美有
  • JavaScript实现雪花飘落效果特效
    没有雪的冬天失去了冬天的美景,不见了千里冰封,万里雪飘的北国之美,诗人无从写雪,画家画不出雪景,摄影师拍不到冬天的美丽。雪,是冬天
  • Typescript是必须要学习吗?如何学习TS全栈开发
    Typescript目前在前端,网站,小程序中的位置基本无可替代,同时也可以构建完美的CLI应用。在移动,桌面,后端方面,性能不是要求很高的
  • 解读Vue实例的属性及模板渲染

    解读Vue实例的属性及模板渲染
    1 概述 Vue.js是通过new Vue({...})来声明一个实例的,在这个实例中包含了当前页面的HTML结构、数据和事件。 Vue实例是MVVM模式中的ViewModel,实现
  • JavaScript中字符串的常用方法总结
    1.字符串长度 length属性返回字符串的长度: 1 2 var str = 字符串常用方法总结-东东吖; str.length; //13 2.查找字符串中的位置 有三种查找字符串中
  • 解决React报错Expected `onClick` listener to be a function

    解决React报错Expected `onClick` listener to be a function
    当我们为元素的onClick属性传递一个值,但是该值却不是函数时,会产生ExpectedonClicklistener to be a function报错。为了解决该报错,请确保只为元
  • ESLint规范TypeScript代码使用方法
    ESLint 是一种 JavaScript linter,可以用来规范 JavaScript 或 TypeScript 代码,本文教你怎么在项目中快速把 ESLint 安排上。 怎么写出优雅的代码是一
  • Vue屏幕自适应三种实现方法介绍
    使用 scale-box 组件 属性: width宽度 默认1920 height高度 默认1080 bgc背景颜色 默认transparent delay自适应缩放防抖延迟时间(ms) 默认100 vue2版本:
  • 在web worker中使用fetch实例介绍
    1.Web Worker意义 由于 JS 是单线程的,费时的 JS 操作将会导致整个页面的阻塞。Web Worker 提供了创建多线程的方法,将一些耗时且 UI 无关的工
  • 本站所有内容来源于互联网或用户自行发布,本站仅提供信息存储空间服务,不拥有版权,不承担法律责任。如有侵犯您的权益,请您联系站长处理!
  • Copyright © 2017-2022 F11.CN All Rights Reserved. F11站长开发者网 版权所有 | 苏ICP备2022031554号-1 | 51LA统计