HarmonyOS 鸿蒙Next--自定义日历组件

发布于 1周前 作者 phonegap100 来自 鸿蒙OS

HarmonyOS 鸿蒙Next–自定义日历组件

0、自定义日历组件,滑动切换月、双箭头切换年, 我这里用来记录每个月的打卡状况,可自定义修改

cke_702.png

1、获取日历列表数据

import { DateUtil } from @pura/harmony-utils’;
import { CalendarInfoBean } from ‘…/viewmodel/work/types’;

const SATURDAY = 6 // 日历表上周六对应的序列号,从周日开始算起,取值0~6

export function getMonthDate(specifiedMonth: number, specifiedYear: number) { let currentFirstWeekDay: number = 0; // 初始化指定月的第一天是周几 let currentLastWeekDay: number = 0; // 初始化指定月的最后一天是周几 let currentAllDay: CalendarInfoBean[] = []; // 初始化指定月的日期排列数组 let totalDays = new Date(specifiedYear, specifiedMonth, 0).getDate(); // 初始化指定月总天数 let lastDays = new Date(specifiedYear, specifiedMonth - 1, 0).getDate(); // 初始化上月总天数 currentFirstWeekDay = new Date(specifiedYear, specifiedMonth - 1, 1).getDay() // 获取指定月的第一天是周几 currentLastWeekDay = new Date(specifiedYear, specifiedMonth - 1, totalDays).getDay() // 获取指定月的最后一天是周几

let currentDay = Number.parseInt(DateUtil.getTodayStr().substring(8, 10)); // 今天是几号

// 将月份中显示上个月日期的内容补全 for (let item = lastDays - currentFirstWeekDay + 1; item <= lastDays; item++) { currentAllDay.push(new CalendarInfoBean(specifiedYear + “”, specifiedMonth + “”, item + “”, 0, false, false)); } // 将本月日期内容存入数组 for (let item = 1; item <= totalDays; item++) { if (item === currentDay) { currentAllDay.push(new CalendarInfoBean(specifiedYear + “”, specifiedMonth + “”, item + “”, 1, true, true)); } else { currentAllDay.push(new CalendarInfoBean(specifiedYear + “”, specifiedMonth + “”, item + “”, 1, false, false)); } } // 将月份中显示下个月日期的内容补全 for (let item = 1; item < SATURDAY - currentLastWeekDay + 1; item++) { currentAllDay.push(new CalendarInfoBean(specifiedYear + “”, specifiedMonth + “”, item + “”, 2, false, false)); } return currentAllDay; } <button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 8px; right: 8px; font-size: 14px;">复制</button>

1.1、CalendarInfoBean日历实体,可自定义添加需要的数据

@ObservedV2
export class CalendarInfoBean {
year?: string;
month?: string;
day?: string;
isCurrent?: number; // 0:上月,1:当月,2:下月
isCurrentDay?: boolean; // 是否是今天
@Trace isSelect?: boolean; // 是否选中
@Trace state?: string; // 打卡状态,0:一次未打卡,1:打了一次卡,2:打了两次卡

constructor(year: string, month: string, day: string, isCurrent: number, isCurrentDay: boolean, isSelect: boolean) { this.year = year; this.month = month; this.day = day; this.isCurrent = isCurrent; this.isCurrentDay = isCurrentDay; this.isSelect = isSelect; } }<button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 8px; right: 8px; font-size: 14px;">复制</button>

2、日历组件:用Swiper实现左右切换一页的功能

import { R } from @ohos/res’;
import { DateUtil } from @pura/harmony-utils’
import { Constants } from ‘…/…/constants/Constants’;
import { HttpUrl } from ‘…/…/constants/HttpUrl’;
import { getMonthDate } from ‘…/…/utils/CalendarUtils’
import { HttpUtils } from ‘…/…/utils/HttUtils’;
import { HttpData, ParamsModel } from ‘…/…/viewmodel/types’;
import { CalendarInfoBean, CalendarListBean, ClockListDTO, SignInTotalBean } from ‘…/…/viewmodel/work/types’;
import {
Image35,
Text16fp3F8CFF,
Text16fp838A8F,
Text16fpBlack,
Text16fpWhite,
Text18fpBlack
} from ‘…/styles/BaseExtend’;

@Component export struct CalendarView { private weeks: string[] = [“日”, “一”, “二”, “三”, “四”, “五”, “六”]; @State currentYear: number = 0 @State currentMonth: number = 0 @State clockList: ClockListDTO[] = [] @State countdownTime: number = 10; @State calendarMonth: CalendarInfoBean[] = []; @State calendarList: CalendarListBean[] = []; private swiperController: SwiperController = new SwiperController(); @State currentIndex: number = 0;

getSignInTotal() { let params: ParamsModel = { param: { “months”: this.currentYear + this.currentMonth, } } HttpUtils.post(HttpUrl.CLOCK_MONTH_INFO, params) .then((res) => { let c = JSON.parse(res) as HttpData<SignInTotalBean> if (c.code === 200) { this.clockList = c.data?.clockList as ClockListDTO[]; } }) }

aboutToAppear(): void { let toDay = DateUtil.getTodayStr() this.currentYear = Number.parseInt(toDay.substring(0, 4)) this.currentMonth = Number.parseInt(toDay.substring(5, 7))

<span class="hljs-keyword"><span class="hljs-keyword">for</span></span> (<span class="hljs-keyword"><span class="hljs-keyword">let</span></span> year = <span class="hljs-number"><span class="hljs-number">2023</span></span>; year &lt;= <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentYear; year++) {
  <span class="hljs-keyword"><span class="hljs-keyword">let</span></span> month = <span class="hljs-number"><span class="hljs-number">13</span></span>;
  <span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (year === <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentYear) {
    month = <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentMonth
  }
  <span class="hljs-keyword"><span class="hljs-keyword">for</span></span> (<span class="hljs-keyword"><span class="hljs-keyword">let</span></span> index = <span class="hljs-number"><span class="hljs-number">1</span></span>; index &lt; month; index++) {
    <span class="hljs-keyword"><span class="hljs-keyword">let</span></span> month = getMonthDate(index, year) as CalendarInfoBean[]
    <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.calendarList.push(<span class="hljs-keyword"><span class="hljs-keyword">new</span></span> CalendarListBean(year, index, month))
  }
}

<span class="hljs-keyword"><span class="hljs-keyword">let</span></span> current = getMonthDate(<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentMonth, <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentYear)
<span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.clockList !== <span class="hljs-literal"><span class="hljs-literal">null</span></span> &amp;&amp; <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.clockList !== <span class="hljs-literal"><span class="hljs-literal">undefined</span></span>) {
  <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.clockList.forEach((element, index) =&gt; {
    <span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (element.dayTime !== <span class="hljs-literal"><span class="hljs-literal">null</span></span> &amp;&amp; element.dayTime !== <span class="hljs-literal"><span class="hljs-literal">undefined</span></span>) {
      <span class="hljs-keyword"><span class="hljs-keyword">let</span></span> day = <span class="hljs-built_in"><span class="hljs-built_in">Number</span></span>.parseInt(element.dayTime.split(<span class="hljs-string"><span class="hljs-string">"-"</span></span>)[<span class="hljs-number"><span class="hljs-number">2</span></span>])
      <span class="hljs-keyword"><span class="hljs-keyword">let</span></span> currentDay = current.find(obj =&gt; obj.day === day + <span class="hljs-string"><span class="hljs-string">""</span></span>) as CalendarInfoBean
      <span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (currentDay !== <span class="hljs-literal"><span class="hljs-literal">null</span></span> &amp;&amp; currentDay !== <span class="hljs-literal"><span class="hljs-literal">undefined</span></span>) {
        currentDay.state = element.satate
      }
    }
  });
}
<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.calendarList.push(<span class="hljs-keyword"><span class="hljs-keyword">new</span></span> CalendarListBean(<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentYear, <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentMonth, current))

<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentIndex = <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.calendarList.length - <span class="hljs-number"><span class="hljs-number">1</span></span>

}

build() { Column() { Row() { Image(R.media.ic_arrow_left_double) .attributeModifier(new Image35()) .padding(R.float.vp10) .margin({ left: R.float.vp15 }) .onClick(() => { this.swiperController.changeIndex(this.currentIndex - 12) }) Image(R.media.ic_arrow_left) .attributeModifier(new Image35()) .padding(R.float.vp10) .onClick(() => { this.swiperController.showPrevious() }) Text(this.currentYear + “年” + this.currentMonth + “月”) .attributeModifier(new Text18fpBlack()) .layoutWeight(1) Image(R.media.ic_arrow_right) .attributeModifier(new Image35()) .padding(R.float.vp10) .onClick(() => { this.swiperController.showNext() }) Image(R.media.ic_arrow_right_double) .attributeModifier(new Image35()) .padding(R.float.vp10) .margin({ right: R.float.vp15 }) .onClick(() => { this.swiperController.changeIndex(this.currentIndex + 12) }) } .margin({ top: R.float.vp10, bottom: R.float.vp10 }) .width(Constants.FULL_PARENT)

  Grid() {
    ForEach(<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.weeks, (week: string) =&gt; {
      GridItem() {
        Text(week).attributeModifier(<span class="hljs-keyword"><span class="hljs-keyword">new</span></span> Text16fpBlack())
      }
    })
  }.columnsTemplate(<span class="hljs-string"><span class="hljs-string">'1fr 1fr 1fr 1fr 1fr 1fr 1fr'</span></span>)
  .height(<span class="hljs-string"><span class="hljs-string">"20vp"</span></span>)
  .margin({
    left: R.float.vp5,
    right: R.float.vp5
  })

  Swiper(<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.swiperController) {
    ForEach(<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.calendarList, (gridItem: CalendarListBean) =&gt; {
      ListItem() {
        Grid() {
          ForEach(gridItem.item, (item: CalendarInfoBean, index: number) =&gt; {
            GridItem() {
              RelativeContainer() {
                Text(item.day)
                  .attributeModifier(item.isCurrent === <span class="hljs-number"><span class="hljs-number">1</span></span> ?
                    (item.isCurrentDay ? (item.isSelect ? <span class="hljs-keyword"><span class="hljs-keyword">new</span></span> Text16fpWhite() : <span class="hljs-keyword"><span class="hljs-keyword">new</span></span> Text16fp3F8CFF()) :
                      <span class="hljs-keyword"><span class="hljs-keyword">new</span></span> Text16fpBlack()) :
                    <span class="hljs-keyword"><span class="hljs-keyword">new</span></span> Text16fp838A8F())
                  .alignRules({
                    middle: { anchor: <span class="hljs-string"><span class="hljs-string">"__container__"</span></span>, align: HorizontalAlign.Center },
                    center: { anchor: <span class="hljs-string"><span class="hljs-string">"__container__"</span></span>, align: VerticalAlign.Center }
                  })
                  .id(<span class="hljs-string"><span class="hljs-string">"tv_day"</span></span>)
                Row() {
                }
                .visibility(item.state !== <span class="hljs-literal"><span class="hljs-literal">undefined</span></span> ? Visibility.Visible : Visibility.None)
                .width(R.float.vp5)
                .height(R.float.vp5)
                .borderRadius(R.float.vp5)
                .alignRules({
                  middle: { anchor: <span class="hljs-string"><span class="hljs-string">"__container__"</span></span>, align: HorizontalAlign.Center },
                  center: { anchor: <span class="hljs-string"><span class="hljs-string">"tv_day"</span></span>, align: VerticalAlign.Bottom }
                })
                .margin({
                  top: R.float.vp2
                })
                .backgroundColor(item.state !== <span class="hljs-literal"><span class="hljs-literal">undefined</span></span> ?
                  (item.state === <span class="hljs-string"><span class="hljs-string">"1"</span></span> ? R.color.color_00B578 :
                    item.state === <span class="hljs-string"><span class="hljs-string">"2"</span></span> ? R.color.color_FF8F1F : R.color.color_838A8F) :
                Color.Transparent)
                .id(<span class="hljs-string"><span class="hljs-string">"tv_dot"</span></span>)
              }
              .width(R.float.vp40)
              .height(R.float.vp40)
              .borderRadius(R.float.vp20)
              .onClick(() =&gt; {
                gridItem.item.forEach(element =&gt; {
                  element.isSelect = <span class="hljs-literal"><span class="hljs-literal">false</span></span>
                });
                item.isSelect = <span class="hljs-literal"><span class="hljs-literal">true</span></span>
              })
              .borderColor((item.isSelect &amp;&amp; !item.isCurrentDay) ? R.color.color_838A8F : Color.Transparent)
              .borderWidth(R.float.vp1)
              .backgroundColor((item.isCurrentDay &amp;&amp; item.isSelect) ? R.color.color_3F8CFF : Color.Transparent)
            }
          })
        }
        .columnsTemplate(<span class="hljs-string"><span class="hljs-string">'1fr 1fr 1fr 1fr 1fr 1fr 1fr'</span></span>)
        .rowsTemplate(gridItem.item.length === <span class="hljs-number"><span class="hljs-number">35</span></span> ? <span class="hljs-string"><span class="hljs-string">'1fr 1fr 1fr 1fr 1fr'</span></span> : <span class="hljs-string"><span class="hljs-string">'1fr 1fr 1fr 1fr 1fr 1fr'</span></span>)
        .height(<span class="hljs-string"><span class="hljs-string">"290vp"</span></span>)
        .margin({
          left: R.float.vp5,
          right: R.float.vp5
        })
      }
      .width(Constants.FULL_PARENT
      )
    })
  }
  .autoPlay(<span class="hljs-literal"><span class="hljs-literal">false</span></span>)
  .indicator(<span class="hljs-literal"><span class="hljs-literal">false</span></span>)
  .loop(<span class="hljs-literal"><span class="hljs-literal">false</span></span>)
  .index(<span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.calendarList.length - <span class="hljs-number"><span class="hljs-number">1</span></span>)
  .onChange((index: number) =&gt; {
    <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentIndex = index
    <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentYear = <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.calendarList[index].year
    <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.currentMonth = <span class="hljs-keyword"><span class="hljs-keyword">this</span></span>.calendarList[index].month
  })

}.width(Constants.FULL_PARENT)

} }<button style="position: absolute; padding: 4px 8px 0px; cursor: pointer; top: 8px; right: 8px; font-size: 14px;">复制</button>



关于HarmonyOS 鸿蒙Next–自定义日历组件的问题,您也可以访问:https://www.itying.com/category-93-b0.html 联系官网客服。

5 回复

你好,源码方便发一下学习一下吗

这里就是全部源码了呀,还有什么地方有问题吗

好的,刚没看清楚

希望HarmonyOS能继续加强与其他应用的兼容性,让用户体验更加完美。

…/…/constants/HttpUrl 但是跑不了代码,里面有很多这种你项目里的。我这并没有

回到顶部