ホームページ  >  記事  >  ウェブフロントエンド  >  Vue コンポーネントを使用してカレンダーを実装する方法 (詳細なチュートリアル)

Vue コンポーネントを使用してカレンダーを実装する方法 (詳細なチュートリアル)

亚连
亚连オリジナル
2018-06-13 10:35:383723ブラウズ

コンポーネントは、Vue を学習する上で必須の部分です。次の記事では、美しいカレンダーを実装するための Vue コンポーネント (コンポーネント) に関する関連情報を、サンプル コードを通じて詳しく紹介します。みんなの学習に役立つ、またはこの作品には一定の参照と学習価値があります。それを必要とする友人は、私をフォローして一緒に学習してください。

コンポーネントは、Vue の最も強力な機能の 1 つです。コンポーネントは、HTML 要素を拡張し、再利用可能なコードをカプセル化し、プロジェクトの要件に応じて一部のコンポーネントを抽象化できます。各コンポーネントには、プレゼンテーション、機能、スタイルが含まれます。各ページは、それぞれのニーズに応じて、異なるコンポーネントを使用してページを接合します。この開発モデルにより、フロントエンドページの拡張が容易で柔軟性が高く、コンポーネント間の分離も実現します。

最近、会社からの依頼で、美しいカレンダー コンポーネント (IOS、Android、PC IE9+ で実行可能) を開発する必要がありました。それを作成した後、それを共有し、皆さんに批判してもらいたいと考えています。

まずスクリーンショットを撮りましょう

コードはhttps://github.com/zhangKunUserGit/vue-componentに共有されています(ローカルダウンロード)

使い方

必要に応じて最初に使用方法を教えてください。それを使用してください (上記は HTML、以下は JS)

<date-picker
 v-if="showDatePicker"
 :date="date"
 :min-date="minDate"
 :max-date="maxDate"
 @confirm="confirm"
 @cancel="cancel"
 ></date-picker>
import DataPicker from &#39;./components/DatePicker.vue&#39;;
import &#39;./style.scss&#39;;
new Vue({
 el: &#39;#app&#39;,
 data() {
 return {
 date: &#39;2017-09-11&#39;,
 minDate: &#39;2000-09-11&#39;,
 maxDate: &#39;2020-09-11&#39;,
 showDatePicker: false,
 selectedDate: &#39;点击选择日期&#39;,
 };
 },
 methods: {
 openDatePicker() {
 this.showDatePicker = true;
 },
 confirm(value) {
 this.showDatePicker = false;
 this.selectedDate = value;
 },
 cancel() {
 this.showDatePicker = false;
 },
 },
 components: {
 DataPicker,
 },
});

最大値、最小値、初期値が提供されます。唯一の欠点は、時刻形式のみであることです。 YYYY-MM-DD (2017-12-12)、github からコードを取得して実行して確認できます (注意深くテストしないとバグやパフォーマンスの問題がある可能性があるため、それらを指摘できれば幸いです)。

(1) まずインターフェイスを描画します

これは重要ではありません、HTML と CSS は非常にシンプルである必要があります。私の CSS を見ると、私の会社というだけで私の名前が長すぎると感じるかもしれません。が使っているので、他のスタイルが気になります 影響を与えます (他にも方法があるかもしれません、神様が指摘してくれることを願っています)

(2) 日付リストを組み立てます

まずコードを見てください:

rows() {
 const { year, month } = this.showDate;
 const months = (new Date(year, month, 0)).getDate();
 const result = [];
 let row = [];
 let weekValue;
 // 按照星期分组
 for (let i = 1; i <= months; i += 1) {
 // 根据日期获取星期,并让开头是1,而非0
 weekValue = (new Date(year, month, i)).getDay() + 1;
 // 判断月第一天在星期几,并填充前面的空白区域
 if (i === 1 && weekValue !== 1) {
 this.addRowEmptyValue(row, weekValue);
 this.addRowDayValue(row, i);
 } else {
 this.addRowDayValue(row, i);
 // 判断月最后一天在星期几,并填充后面的空白区域
 if (i === months && weekValue !== 7) {
 this.addRowEmptyValue(row, (7 - weekValue) + 1);
 }
 }
 // 按照一周分组
 if (weekValue % 7 === 0 || i === months) {
 result.push(row);
 row = [];
 }
 }
 this.showDate.monthStr = monthJson[this.showDate.month];
 return result;
},

私のアイデアは次のとおりです:

(1) 月の日数を取得し、週ごとにグループ化します

(2) 月の最初の日が月曜日でない場合は、前に null を入力します。価値観。同様に、月の最終日が日曜日でない場合は、最後に NULL 値を入力します。これは、ハンディキャップ グループの長さを 7、つまり 1 週間にするためです。このように、フレックス レイアウトを使用して迅速に開発できます

(3) minDate 未満および maxDate を超える、クリックを許可しないなど、いくつかの制限も含まれています。

(3) 月の切り替え

(1)先月

/**
 * 切换到上一个月
 */
prevMonth() {
 if (this.prevMonthClick) {
 return;
 }
 this.prevMonthClick = true;
 setTimeout(() => {
 this.prevMonthClick = false;
 }, 500);
 this.fadeXType = &#39;fadeX_Prev&#39;;
 // 如何当前月份已经小于等于minMonth 就不让其在执行
 if (this.isMinLimitMonth()) {
 return;
 }
 const { year, month } = this.showDate;
 // 判断当前月份,如果已经等于1(1就是一月,而不是二月)
 if (month <= 1) {
 this.showDate.year = year - 1;
 this.showDate.month = 12;
 } else {
 this.showDate.month -= 1;
 }
},

setTimeout()は主にアニメーション表示後に自動で消えるようにしています。 fadeXType はアニメーションタイプです

(2) 来月

/**
 * 切换到下一个月
 */
nextMonth() {
 if (this.nextMonthClick) {
 return;
 }
 this.nextMonthClick = true;
 setTimeout(() => {
 this.nextMonthClick = false;
 }, 500);
 this.fadeXType = &#39;fadeX_Next&#39;;
 // 如何当前月份已经大于等于maxMonth 就不让其在执行
 if (this.isMaxLimitMonth()) {
 return;
 }
 const { year, month } = this.showDate;
 // 判断当前月份,如果已经等于12(12就是十二月)
 if (month >= 12) {
 this.showDate.year = year + 1;
 this.showDate.month = 1;
 } else {
 this.showDate.month += 1;
 }
},

ここでの setTimeout() メソッドと prevMonth メソッドは同じ原理です。

月を切り替える上記の 2 つの関数の主な注意点は次のとおりです:

a. minDate と maxDate があるため、最初に考慮するのはこの制限を超えないことです。

b. 月を切り替えた後の年の変更を考慮する必要があります。月が 12 を超える場合は、年が 1 加算され、月が 1 になります。

(4) 年を選択します

(1) 上の年をクリックして年のリストを表示します

openYearList() {
 if (this.showYear) {
 this.showYear = false;
 return;
 }
 const index = this.yearList.indexOf(this.selectDate.year);
 this.showYear = true;
 // 打开年列表,让其定位到选中的位置上
 setTimeout(() => {
 this.$refs.yearList.scrollTop = (index - 3) * 40;
 });
},

(2) 年を選択します

selectYear(value) {
 this.showYear = false;
 this.showDate.year = value;
 let type;
 // 当日期在最小值之外,月份换成最小值月份 或者 当日期在最大值之外,月份换成最大值月份
 if (this.isMinLimitMonth()) {
 type = &#39;copyMinDate&#39;;
 } else if (this.isMaxLimitMonth()) { // 当日期在最大值之外,月份换成最大值月份
 type = &#39;copyMaxDate&#39;;
 }
 if (type) {
 this.showDate.month = this[type].month;
 this.showDate.day = this[type].day;
 this.resetSelectDate(this.showDate.day);
 return;
 }
 let dayValue = this.selectDate.day;
 // 判断日是最大值,防止另一个月没有这个日期
 if (this.selectDate.day > 28) {
 const months = (new Date(this.showDate.year, this.showDate.month, 0)).getDate();
 // 当前月份没有这么多天,就把当前月份最大值赋值给day
 dayValue = months < dayValue ? months : dayValue;
 }
 this.resetSelectDate(dayValue);
},

以下の点に注意してください年を切り替えるときの側面:

a. minDate と maxDate を考慮します。以前に選択した月が 1 月であるが、制限が 9 月である場合、minDate より大きい年 (2017 年など) には問題はありません。 minDate の特定の年 (2010 など) になる場合、月の最小値は 9 月のみとなり、同じことが maxDate にも当てはまります。

b. 前に選択した日は 31 でした。年を切り替えた後、今月は 30 日しかないため、日を今月の最大値である 30 に変更することを忘れないでください。

(5) 生データの処理

本来であれば、この項目は最初のステップで議論されるべきですが、私の開発習慣に基づいてステップを書きました。通常、最初に関数を作成し、データを作成した後、元のデータ形式や具体的な露出方法などを検討します。これにより、影響を与える何度も変更する必要がなくなります。展開も雰囲気も。

initDatePicker() {
 this.showDate = { ...this.splitDate(this.date, true) };
 this.copyMinDate = { ...this.splitDate(this.minDate) };
 this.copyMaxDate = { ...this.splitDate(this.maxDate) };
 this.selectDate = { ...this.showDate };
},
splitDate(date, addStr) {
 let result = {};
 const splitValue = date.split(&#39;-&#39;);
 try {
 if (!splitValue || splitValue.length < 3) {
 throw new Error(&#39;时间格式不正确&#39;);
 }
 result = {
 year: Number(splitValue[0]),
 month: Number(splitValue[1]),
 day: Number(splitValue[2]),
 };
 if (addStr) {
 result.week = (new Date(result.year, result.month, result.day)).getDay() + 1;
 result.monthStr = monthJson[result.month];
 result.weekStr = weekJson[result.week];
 }
 } catch (error) {
 console.error(error);
 }
 return result;
},

ここでの目的は、

a. 元のデータを処理し、元のデータを確認し、その後の操作と表示を容易にするために json でキャッシュします。 YYYY-MM-DD 形式とのみ互換性があり、他の形式と互換性がない場合は、コードを変更するか、moment.js などの他のライブラリを使用してください。 。

b. 分割形式は次のとおりです:

year: &#39;&#39;,
month: &#39;&#39;,
day: &#39;&#39;,
week: &#39;&#39;,
weekStr: &#39;&#39;,
monthStr: &#39;&#39;,

以上が皆さんの参考になれば幸いです。

関連記事:

requireJS はモジュールローダーをどのように実装しますか?

jsでMVVMフレームワークを実装する(詳細なチュートリアル)

angularjsでのスコープの説明

JavaScriptで高パフォーマンスのロードオーダーを実装する方法

axiosでグローバル登録を実装する方法

以上がVue コンポーネントを使用してカレンダーを実装する方法 (詳細なチュートリアル)の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。