ソースを参照

Merge branch 'next' of https://github.com/jdf2e/nutui into next

yumingming11 5 年 前
コミット
6cb2d029dc

+ 1 - 1
src/config.js

@@ -273,7 +273,7 @@ module.exports = {
         },
         {
           name: 'Rate',
-          sort: 2,
+          sort: 4,
           cName: '评分',
           type: 'component',
           show: true,

+ 20 - 7
src/packages/input/demo.vue

@@ -1,26 +1,27 @@
 <template>
   <div class="demo-nopading">
     <h2>基础用法</h2>
-    <nut-input v-model:value="state.val1" @change="change" label="标题:" />
+    <nut-input v-model:value="state.val1" @change="change" @focus="focus"  @blur="blur" label="标题:" />
 
     <nut-input
       placeholder="请输入文本"
       @change="change"
       v-model:value="state.val0"
-      requireShow="true"
+      :requireShow="true"
       label="标题:"
+     @clear="clear"
     />
     <h2>禁用输入框</h2>
     <nut-input
       v-model:value="state.val2"
       @change="change"
-      disabled="true"
+      :disabled="true"
       label="标题:"
     />
     <nut-input
       v-model:value="state.val3"
       @change="change"
-      readonly="true"
+      :readonly="true"
       label="标题:"
     />
     <h2>限制输入长度</h2>
@@ -54,7 +55,7 @@
     <nut-input
       v-model:value="state.val7"
       @change="change"
-      autosize="true"
+      :autosize="true"
       type="textarea"
       placeholder="文本域"
       label="留言:"
@@ -72,7 +73,7 @@
       v-model:value="state.val8"
       @change="change"
       rows="5"
-      limitShow="true"
+      :limitShow="true"
       maxLength="20"
       type="textarea"
       placeholder="设置输入五行"
@@ -104,9 +105,21 @@ export default createDemo({
     const change = (num: string | number) => {
       console.log('change: ', num);
     };
+    const focus=(num:string|number)=>{
+      console.log("focus:",num)
+    }
+    const blur=(num:string|number)=>{
+      console.log("blur:",num)
+    }
+    const clear=(num:string|number)=>{
+      console.log("clear:",num)
+    }
     return {
       state,
-      change
+      change,
+      blur,
+      clear,
+      focus
     };
   }
 });

+ 63 - 5
src/packages/input/doc.md

@@ -1,3 +1,64 @@
+# Input 输入框组件
+
+### 介绍
+
+
+### 安装
+
+``` javascript
+import { createApp } from 'vue';
+import { input } from '@nutui/nutui';
+
+const app = createApp();
+app.use(input);
+
+```
+## 代码演示
+
+### 基础用法
+
+双向绑定
+
+```html
+<nut-input v-model:value="state.val1" @change="change" label="标题:" />
+
+```
+
+### 禁用和只读
+
+
+```html
+<nut-input v-model:value="state.val2" @change="change"  disabled="true" label="标题:"/>
+<nut-input v-model:value="state.val3" @change="change" readonly="true"  label="标题:"/>
+```
+
+### 限制输入长度
+
+```html
+ <nut-input v-model:value="state.val4" @change="change" maxLength="7" label="限制7:" />
+```
+### 其他类型
+
+```html
+<nut-input v-model:value="state.val0" @change="change" type="password" label="密码:"/>
+<nut-input v-model:value="state.val5" @change="change" type="digit" label="整数:" />
+<nut-input v-model:value="state.val6" @change="change" type="digit" placeholder="支持小数点的输入" label="数字:"/>
+```
+### 文本域
+
+```html
+ <nut-input v-model:value="state.val7" @change="change" autosize="true" type="textarea" placeholder="文本域" label="留言:"/>
+<nut-input v-model:value="state.val7" @change="change" rows="5" type="textarea" placeholder="设置输入五行"  label="留言:"/>
+
+```
+### 文本域字数统计
+
+```html
+ <nut-input v-model:value="state.val8" @change="change" rows="5" limitShow="true" maxLength="20" type="textarea" placeholder="设置输入五行" label="留言:"/>
+
+```
+
+
 | 参数         | 说明                             | 类型   | 默认值           |
 |--------------|----------------------------------|--------|------------------|
 | type         | 类型,可选值为 `text` `textarea` `number`  等 | String |`text`         |
@@ -5,22 +66,19 @@
 | placeholder         | 为空时占位符 | String |       -       |
 | placeholder-style | placeholder 样式     | String | - |
 | label          | 	左侧文案                       | string | -             |
-| has-border          | 	是否有边框                       | booleab | true            |
 | disabled          | 	是否禁用                       | boolean | `false`              |
 | readonly          | 是否只读                        | boolean | `false`               |
 | clear-btn       | 是否带清除按钮(icon)                        | boolean | `true`               |
 | required          | 是否带必填的*号,且blur事件做非空校验                       | boolean | `false`               |
 | maxlength          | 限制最长输入字符                   | string/number | -               |
+| rows          | textarea时高度                   | string/number | 2             |
 | limit-show          | textarea时是否展示输入字符。须设置maxlength                        | boolean | `false`               |
 
-
-事件
-| input          | 输入内容时触发                        | function | -               |
 | change          | 输入内容时触发                        | function | -               |
 | focus          | 聚焦时触发                        | function | -               |
 | blur          | 失焦时触发                        | function | -               |
 | clear          | 点击清空时触发                        | function | -               |
-| error          | 校验错误时触发                        | function | -               |
+
 
 
 

+ 3 - 1
src/packages/input/index.scss

@@ -1,4 +1,5 @@
 .nut-input {
+    position: relative;
   width: 100%;
   padding: 10px 0px 10px 25px;
   display: flex;
@@ -18,7 +19,8 @@
   .nut-textinput-clear {
     width: 16px;
     height: 16px;
-    margin-right: 15px;
+    position: absolute;
+    right: 15px;
   }
   .nut-text {
     flex: 1;

+ 46 - 28
src/packages/input/index.vue

@@ -34,23 +34,23 @@
       :placeholder="placeholder"
       :disabled="disabled"
       :readonly="readonly"
-      v-model="state.curretvalue"
+      :value="state.curretvalue"
       @input="valueChange"
-      @focus="focus"
-      @blur="blur"
+      @focus="valueFocus"
+      @blur="valueBlur"
     />
-    <!-- <view
+    <view
       @click="handleClear"
       class="nut-textinput-clear"
       v-if="!disableClear && !readonly"
-      v-show="type !== 'textarea' && active"
+      v-show="type !== 'textarea'  && active"
     >
       <svg version="1" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 16 16">
         <path
           d="M8 0C3.6 0 0 3.6 0 8s3.6 8 8 8 8-3.6 8-8-3.6-8-8-8zm2.8 9.7c.3.3.3.8 0 1.1s-.8.3-1.1 0L8 9.1l-1.7 1.7c-.3.3-.8.3-1.1 0-.3-.3-.3-.8 0-1.1L6.9 8 5.2 6.3c-.3-.3-.3-.8 0-1.1.3-.3.8-.3 1.1 0L8 6.9l1.7-1.7c.3-.3.8-.3 1.1 0 .3.3.3.8 0 1.1L9.1 8l1.7 1.7z"
         />
       </svg>
-    </view> -->
+    </view>
   </view>
 </template>
 <script lang="ts">
@@ -102,11 +102,11 @@ export default create({
     }
   },
   components: {},
-  emits: ['change', 'update:value', 'blur', 'focus'],
+  emits: ['change', 'update:value', 'blur', 'focus','clear'],
 
   setup(props, { emit }) {
     interface Events {
-      eventName: 'change';
+      eventName: 'change' | 'focus'|'blur';
       params: (string | number | Event)[];
     }
 
@@ -159,9 +159,9 @@ export default create({
       if (props.type == 'number') {
         val = formatNumber(val, false);
       }
-      state.textNum = val.length;
-      input.value = val;
-      state.curretvalue = val;
+       state.textNum = val.length;
+      // input.value = val;
+       //state.curretvalue = val;
       emitChange([
         {
           eventName: 'update:value',
@@ -173,7 +173,7 @@ export default create({
         }
       ]);
     };
-    const focus = (e: Event) => {
+    const valueFocus = (e: Event) => {
       active.value = true;
       const input = e.target as HTMLInputElement;
       let val = input.value;
@@ -189,21 +189,38 @@ export default create({
         }
       ]);
     };
-    const blur = () => {
-      //active.value = false;
-      // const input = e.target as HTMLInputElement;
-      // let val = input.value;
-      // emitChange([
-      //   {
-      //     eventName: 'update:modelValue',
-      //     params: [val]
-      //   },
-      //   {
-      //     eventName: 'focus',
-      //     params: [val]
-      //   }
-      // ]);
+    const valueBlur = (e: Event) => {
+      
+      setTimeout(()=>{
+active.value = false;
+      },400)
+      const input = e.target as HTMLInputElement;
+       let val = input.value;
+      val = String(val);
+      emitChange([
+        {
+          eventName: 'update:value',
+          params: [val]
+        },
+        {
+          eventName: 'blur',
+          params: [val]
+        }
+      ]);
     };
+    const handleClear=()=>{
+      const val="";
+      emitChange([
+        {
+          eventName: 'update:value',
+          params: [val]
+        },
+        {
+          eventName: 'clear',
+          params: [val]
+        }
+      ]);
+    }
     return {
       value,
       requireShow,
@@ -217,8 +234,9 @@ export default create({
       active,
       maxLength,
       valueChange,
-      focus,
-      blur,
+      valueFocus,
+      valueBlur,
+      handleClear,
       emitChange
     };
   }

+ 47 - 5
src/packages/switch/demo.vue

@@ -1,25 +1,67 @@
 <template>
   <div class="demo">
     <h2>基础用法</h2>
-    <nut-cell>
-      开
-      <nut-switch></nut-switch>
+    <nut-cell class="switch-adjust">
+      {{ text }}
+      <nut-switch
+        @switch-change="switchChange"
+        class="switch-decoration"
+      ></nut-switch>
+    </nut-cell>
+
+    <h2>change事件</h2>
+    <nut-cell class="switch-adjust">
+      chane
+      <nut-switch
+        @switch-change="change"
+        class="switch-decoration"
+      ></nut-switch>
+    </nut-cell>
+
+    <h2>自定义颜色</h2>
+    <nut-cell class="switch-adjust">
+      color
+      <nut-switch activeColor="blue" class="switch-decoration"></nut-switch>
     </nut-cell>
   </div>
 </template>
 
 <script lang="ts">
+import { toRefs, reactive } from 'vue';
 import { createComponent } from '@/utils/create';
+import { isObject } from '@vue/shared';
 const { createDemo } = createComponent('switch');
 export default createDemo({
   props: {},
   setup() {
-    return {};
+    const response = reactive({
+      text: '开'
+    });
+    const switchChange = (event: Event, isOpen: boolean) => {
+      response.text = isOpen ? '开' : '关';
+    };
+    const change = (event: Event, isOpen: boolean) => {
+      console.log('触发了change事件,开关状态:', isOpen);
+    };
+
+    return {
+      ...toRefs(response),
+      switchChange,
+      change
+    };
   }
 });
 </script>
 
 <style lang="scss" scoped>
-.nut-temp {
+.switch-adjust {
+  font-size: 18px;
+  color: rgba(102, 102, 102, 1);
+  justify-content: space-between;
+  align-items: center;
+}
+
+.switch-decoration {
+  cursor: pointer;
 }
 </style>

+ 25 - 3
src/packages/switch/doc.md

@@ -25,17 +25,39 @@ app.use(Switch);
 
 ### change事件
 
+``` html
+<nut-switch @switch-change="change"></nut-switch>
+```
+
+``` javascript
+export default {
+  setup() {
+    const change = (event: Event, isOpen: boolean) => {
+      console.log('触发了change事件,开关状态:', isOpen);
+    };
+    
+    return {
+      change
+    };
+  }
+};
+```
+
 ### 自定义颜色
 
+``` html
+<nut-switch activeColor="blue"></nut-switch>
+```
+
 ## API
 
 ### Props
 
 | 参数         | 说明                             | 类型   | 默认值           |
 |--------------|----------------------------------|--------|------------------|
-| checked         | 开关状态               | Boolean | true |
-| activeColor        | 开关打开时的背景颜色  | String | -                |
-| inactiveColor         | 开关关闭时的背景颜色 | String | "#fff"         |
+| status         | 开关状态               | Boolean | true |
+| activeColor        | 开关打开时的背景颜色  | String | rgb(250,63,25,1)                |
+| inactiveColor         | 开关关闭时的背景颜色 | String | rgba(235,235,235,1)         |
 
 
 ### Events

+ 18 - 7
src/packages/switch/index.scss

@@ -3,13 +3,7 @@
   align-items: center;
   width: 72px;
   height: 42px;
-  background-image: linear-gradient(
-    135deg,
-    rgba(250, 44, 25, 1) 0%,
-    rgba(250, 63, 25, 1) 45%,
-    rgba(250, 89, 25, 1) 83%,
-    rgba(250, 100, 25, 1) 100%
-  );
+  background-color: rgb(250, 63, 25, 1);
   border-radius: 25px;
   background-size: 100% 100%;
   background-repeat: no-repeat;
@@ -17,10 +11,27 @@
   flex: 0 0 auto; // 防止被压缩
   .switch-button {
     display: flex;
+    align-items: center;
+    justify-content: center;
     width: 26px;
     height: 26px;
     border-radius: 13px;
     background: rgba(255, 255, 255, 1);
+    transition: transform 0.3s;
+    transform: translateX(30%);
+  }
+}
+.switch-open {
+  .switch-button {
     transform: translateX(146%);
   }
 }
+.switch-close {
+  background-color: rgba(235, 235, 235, 1);
+  .close-line {
+    width: 16px;
+    height: 4px;
+    background: rgba(240, 240, 240, 1);
+    border-radius: 4px;
+  }
+}

+ 51 - 17
src/packages/switch/index.vue

@@ -1,49 +1,83 @@
 <template>
-  <view :style="styles" class="nut-switch">
-    <view class="switch-button" @click="onClick"></view>
+  <view
+    @click="onClick"
+    :style="style"
+    class="nut-switch"
+    :class="[isOpen ? 'switch-open' : 'switch-close']"
+  >
+    <view class="switch-button">
+      <view v-show="!isOpen" class="close-line"></view>
+    </view>
   </view>
 </template>
 
 <script lang="ts">
-import { toRefs, computed } from 'vue';
+import { toRefs, computed, reactive, onMounted } from 'vue';
 import { createComponent } from '@/utils/create';
 const { componentName, create } = createComponent('switch');
 
 export default create({
   props: {
-    checked: {
+    status: {
       type: Boolean,
       default: true
     },
     activeColor: {
       type: String,
-      default:
-        'linear-gradient(135deg, rgba(250,44,25,1) 0%,rgba(250,63,25,1) 45%,rgba(250,89,25,1) 83%,rgba(250,100,25,1) 100%);'
+      default: ''
     },
     inactiveColor: {
       type: String,
-      default: '#fff'
+      default: ''
     }
   },
 
   setup(props, { emit }) {
-    const { checked, activeColor, inactiveColor } = toRefs(props);
+    const { status, activeColor, inactiveColor } = toRefs(props);
+    const actColor = activeColor.value;
+    const inaColor = inactiveColor.value;
 
-    const styles = computed(() => {
-      return {
-        backgroundColor: `${activeColor.value}`
-      };
+    const response = reactive({
+      isOpen: status.value ? status.value : true,
+      style: {}
     });
 
+    const styleCheck = status => {
+      if (status) {
+        if (actColor) {
+          response.style = {
+            backgroundColor: `${actColor}`
+          };
+        } else {
+          response.style = {
+            backgroundColor: 'rgb(250,63,25,1)'
+          };
+        }
+      }
+      if (!status) {
+        if (inaColor) {
+          response.style = {
+            backgroundColor: `${inaColor}`
+          };
+        } else {
+          response.style = {
+            backgroundColor: 'rgba(235,235,235,1)'
+          };
+        }
+      }
+    };
+
+    styleCheck(status.value);
+
     const onClick = () => {
-      checked.value = !checked.value;
-      emit('switch-change', event);
+      response.isOpen = !response.isOpen;
+      styleCheck(response.isOpen);
+      emit('switch-change', event, response.isOpen);
     };
 
     return {
-      styles,
-      onClick,
-      checked
+      ...toRefs(response),
+      onClick
     };
   }
 });