Vue 组件封装之 Content 列表(处理多行输入框 textarea)
处理多行输入框 textarea 自适应高度。
·
Vue 组件封装之 Content 列表
一、Content 列表
组件说明:
实现 Content 列表布局排版。
效果展示:
实现的功能:
- 在一个 List 中实现文本和输入框(单行/多行)的上下布局;
- 上面为文本 label 标签,纯文字展示。可通过 require 字段来判断是否必填,必填项则前面会有红色的 *。
- 下面为输入值 input/textarea 标签。
二、使用案例
<template>
<div>
<el-context
:list="contentList"
:result="contentItem"
/>
</div>
</template>
<script>
export default {
data(){
return {
contentList:[
{title:"工作内容",require:true,field:"content",placeholder:'请输入工作内容。如休假请填休假(240字以内)',
renderType:'textarea',
maxLength:"240"
},
{title:"时长",require:true,field:"time",placeholder:'请输入小时数,保留一位小数。如休假请填0',renderType:'number'},
{title:"备注",require:false,field:"remark",placeholder:'请输入备注(240字以内)',
renderType:'textarea',maxLength:"240",dealWithKeyboard:true},
],
contentItem:{
content:'',
time:'',
remark:'',
},
}
}
}
</script>
三、API 使用指南
属性 | 说明 | 类型 | 默认值 |
---|---|---|---|
list | 页面展示的静态内容集合 | Array | [] |
renderType | 组件类型 | String | – |
maxLength | 最大长度限制 | String | – |
label | 展示文本 | String | – |
field | 输入值字段 | String | – |
placeholder | 提示 | String | – |
require | 是否为必输字段 | Boolean | – |
disabled | 值是 true 或者 disabled 则为反显值,否则为输入值 | Boolean | false |
dealWithKeyboard | 是否要处理安卓键盘遮挡问题 | Boolean | false |
result | 对应的字段值集合 | Object | {} |
四、源代码
Context.vue
文件路径:share/context/Context.vue
<template>
<div>
<div v-for="item in list">
<div class="cm-p-02 cm-bottom">
<div class="cm-fs-030">
<span class="cm-c-red" v-if="item.require">*</span>
<span :class="[focusText==item.field?'edit-focus-text':'',!item.require?'cm-ml-02':'']">{{item.title}}</span>
</div>
<el-input
v-if="item.renderType==='number'"
@focus="changeStyle(item)"
type="text"
@input.native="changeNumber"
:placeholder="item.placeholder"
class="edit-input cm-w-full cm-fs-028 cm-c-333"
v-model="result[item.field]"></el-input>
<el-input
:type="item.renderType"
v-else
@focus="changeStyle(item)"
:autosize="{ minRows: 2, maxRows: 4}"
:maxlength="item.maxLength"
class="edit-input cm-w-full cm-fs-028 cm-c-333"
:placeholder="item.placeholder"
rows="2"
v-model="result[item.field]">
</el-input>
</div>
</div>
</div>
</template>
<script>
import {autoTextarea,isAndroid} from '../../utils/common';
export default {
name: "ElContent",
data(){
return{
focusText:""
}
},
//获取子组件传过来的激活tab
props:{
list:{
type: Array,
default: function () {
return [];
}
},
result:{
type:Object,
default:{}
},
},
mounted(){
//为了适应苹果浏览器初始时展现多行状态。
setTimeout(() => {
autoTextarea();
}, 100);
},
methods:{
changeNumber({target}){
//此为数字输入框,控制非数字输入
target.value=(target.value.match(/^\d*(\.?\d{0,1})/g)[0]) || null
},
changeStyle(item){
//聚焦时改变label样式
this.focusText = item.field;
//避免安卓手机输入法弹出框挡住输入框
if(item.dealWithKeyboard && isAndroid()){
document.body.style.height = document.body.clientHeight + 100 +'px';
}
}
}
}
</script>
<style scoped>
.edit-focus-text{
color: #3296FA;
font-size: 0.22rem;
}
</style>
export function isAndroid(){
var u = navigator.userAgent;
var isAndroid = u.indexOf('Android') > -1 || u.indexOf('Adr') > -1; //android终端
if (isAndroid) {
return true
}else {
return false
}
}
export function autoTextarea(){
var textarea = document.getElementsByTagName("textarea");
for(var i=0;i<textarea.length;i++){
textarea[i].style.height = 'auto';
textarea[i].scrollTop = 0; //防抖动
textarea[i].style.height = textarea[i].scrollHeight + 'px';
textarea[i].addEventListener('input',function (e) {
console.log(e.target.scrollHeight);
e.target.style.height = 'auto';
e.target.scrollTop = 0;
if(e.target.scrollHeight>=100){
//控制最高4行
e.target.style.height = 100 + 'px';
}else {
e.target.style.height = e.target.scrollHeight + 'px';
}
//}
})
}
}
index.js
文件路径:share/context/index.js
import Content from './Content.vue';
/* istanbul ignore next */
Content.install = function(Vue) {
Vue.component(Content.name, Content);
};
export default Content;
注:里面用到一些公共样式,公共样式内容比较多,就不贴出来了。有需要的留言。
更多推荐
已为社区贡献12条内容
所有评论(0)