Uni-App Common Scenarios Quick Reference

Common Scenarios in uni-app Development Quick Reference

This document records common issues encountered during uni-app development for future reference.

1. Line Break Display in ElementUI Textarea

When using el-input with type="textarea", the text content may not display line breaks in a table. To show line breaks, render the content as HTML and use <br> tags.

<el-table-column prop="content" label="Content" width="500">
  <template slot-scope="scope">
    <span v-html="scope.row.content"></span>
  </template>
</el-table-column>

Line break display

2. Scrolling Text in uni-app

Use a swiper component to display multiple text items in a loop.

<template>
  <view>
    <view class="scroll_box">
      <swiper class="swiper" :autoplay="autoplay" :interval="interval" :duration="duration">
        <swiper-item v-for="(item, index) in list" :key="index">
          <view class="swiper-item uni-bg-green">{{ item }}</view>
        </swiper-item>
      </swiper>
    </view>
  </view>
</template>

<script>
export default {
  data() {
    return {
      autoplay: true,
      interval: 6000,
      duration: 12000,
      list: [
        'Project initial phase, contact support for issues',
        'Project initial phase, contact support for issues',
        'Project initial phase, contact support for issues'
      ]
    };
  }
}
</script>

<style lang="scss">
.scroll_box {
  position: fixed;
  top: 10rpx;
  width: 100%;
  height: 10%;
  background: #FFFFFF;
  border-radius: 10rpx;
  .swiper {
    width: 100%;
    height: 100%;
  }
}
</style>

3. Pull-to-Refresh and Infinnite Scroll Pagination

Use onPullDownRefresh and onReachBottom lifecycle hooks.

<script>
export default {
  data() {
    return {
      items: [],
      currentPageItems: [],
      currentPage: 1,
      pageSize: 2
    };
  },
  async onPullDownRefresh() {
    this.items = [];
    this.currentPageItems = [];
    this.currentPage = 1;
    await this.fetchData(this.currentPage, this.pageSize);
    uni.stopPullDownRefresh();
  },
  onReachBottom() {
    this.currentPage++;
    this.fetchData(this.currentPage, this.pageSize);
  },
  methods: {
    async fetchData(page, size) {
      const response = await fetchItems({ currentPage: page, pageSize: size });
      this.currentPageItems = response.data.list.map(item => ({
        // data processing
      }));
      this.items = this.items.length === 0 ? this.currentPageItems : [...this.items, ...this.currentPageItems];
    }
  }
}
</script>

Note: Use spread operator for array concatenation; concat may not update reactivity.

4. Gaussian Blur on Images

Use CSS filter: blur(radius); larger radius means more blur.

.img_content {
  filter: blur(4px);
}

Before: Before blur After: After blur

5. Global Methods via Vue.prototype Not Working in Config Files

When using Vue.prototype to define global methods, they are only available in Vue components, not in plain JS files. To use them, import the module directly.

// commonMethod.js
const showLoading = () => {
  uni.showLoading({ title: 'Loading...', mask: true });
};
const hideLoading = () => {
  uni.hideLoading();
};
export const commonMethod = {
  showLoading,
  hideLoading
};
// packageMethod.js
import { commonMethod } from '@/common/commonMethod.js';

function postRequest(url, data, header) {
  return new Promise((resolve, reject) => {
    commonMethod.showLoading();
    // ... request logic
  });
}

6. Hide Navigation Bar Back Button on H5

mounted() {
  document.querySelector('.uni-page-head-hd').style.display = 'none';
  // To hide entire navigation bar:
  // document.querySelector('.uni-page-head').style.display = 'none';
}

7. WeChat Mini Program Share URL Parameters

Share to friends:

onShareAppMessage(res) {
  return {
    title: 'Share Title',
    path: '/pages/index/index?userId=256',
    mpId: '12456'
  };
}

Share to timeline:

onShareTimeline(res) {
  return {
    title: 'Share Timeline Title',
    query: 'userId=456'
  };
}

Retrieve parameters on page load:

created() {
  const pages = getCurrentPages();
  const page = pages[0].options;
  console.log('userId:', page.userId);
}

8. Circular Avatar

Set equal width and height, and border-radius to half of them.

<image src="avatar.jpg" style="height: 80px; width: 80px; border-radius: 40px;"></image>

9. View set to width:100% Not Working

Ensure parent element has 100% width. Alternatively use vw/vh units.

  • vw: 1% of viewport width
  • vh: 1% of viewport height

9.1 Full Screen Height for View

Set uni-page-body height to 100% in App.vue or page style:

uni-page-body {
  height: 100%;
}

Then set the outermost view to height: 100%.

10. Passing Parameters from WeChat Mini Program WebView to H5

Append parameters to the webview URL:

<web-view src="https://abc.com?userId=2">Become VIP</web-view>

In H5, retrieve via event:

onload(event) {
  console.log('userId:', event.userId);
}

11. SCSS Reuse with @extend and @mixin

@extend for identical styles, @mixin for parameterized styles.

Example:

// Define common styles
%common-box {
  display: flex;
  justify-content: center;
  align-items: center;
}

// Use @extend
.box1 {
  @extend %common-box;
  width: 100px;
  height: 100px;
}

// Use @mixin
@mixin box-size($w, $h) {
  width: $w;
  height: $h;
}

.box2 {
  @include box-size(200px, 150px);
}

12. Centered View with Equal Left/Right Margins

.view {
  margin: auto;
  height: 100%;
  width: 95%; /* 2.5% margin on each side */
}

13. Fix /pages/xxx/xxx.wxml Not Found Error

If renaming a page file causes this error, delete the old folder and its configuration, recompile, then recreate the folder and configuration.

14. Interval Timer

let count = 0;
const timer = setInterval(() => {
  count++;
  console.log('Executed');
  if (count === 6) clearInterval(timer);
}, 1000);

To use methods inside timer, use arrow function or that = this.

const that = this;
setTimeout(function() {
  that.$commonMethod.goToTabbar('/pages/index/index');
}, 1000);

15. Box with Equal Left/Right Spacing on Screen

.parent {
  .child {
    margin: auto;
    height: 100%;
    width: 96%;
  }
}

16. Ternary Operator Replacement with || and &&

header: {
  'content-type': contentType || 'application/json',
  'token': needsToken && uni.getStorageSync('token')
}

17. Styling Specific Words in Text

Use inline span with style.

<view class="private_desc">
  Thank you for using our mini program. Read and agree to the
  <span style="color: #0070D9;" @tap="openPolicy(1)">Privacy Policy</span>
  and
  <span style="color: #0070D9;" @tap="openPolicy(2)">User Agreement</span>
  before continuing.
</view>

18. File Upload with POST Request

Server endpoint:

@PostMapping("/uploadFile")
public ResultVo uploadFile(@NotNull MultipartFile multipartFile,
                            @NotNull Integer fileType) { }

Client:

uni.uploadFile({
  url: serverUrl + '/uploadFile',
  filePath: filePath,
  name: 'multipartFile',
  formData: {
    'fileType': fileType
  },
  success: (res) => { }
});

19. Custom Button with Centered Text

<view class="btns">
  <button class="item reject" style="background: #f4f4f5; color: #909399;">
    <text>Reject</text>
  </button>
  <button class="item agree" type="primary" @tap="login()">
    <text>Agree</text>
  </button>
</view>
.btns {
  margin-top: 48rpx;
  width: 90%;
  display: flex;
  .item {
    justify-content: space-between;
    width: 244rpx;
    height: 80rpx;
    display: flex;
    align-items: center;
    justify-content: center;
    border-radius: 16rpx;
    box-sizing: border-box;
    border: none;
  }
  .reject {
    background: #f4f4f5;
    color: #909399;
  }
  .agree {
    background: #07c160;
    color: #fff;
  }
}

20. Paragraph First-Line Indentation

Use text-indent on parent container.

.des_item {
  text-indent: 5%;
}

21. SCSS Reuse with Multiple Classes on Same Element

Define common classes in a separate SCSS file and import globally.

// common.scss
.display-flex {
  display: flex;
}
.flex-row {
  flex-direction: row;
}
.flex-wrap {
  flex-wrap: wrap;
}

In App.vue:

@import url("common/common.scss");

Usage:

<view class="content display-flex flex-row flex-wrap">
  ...
</view>

22. Fix Style Height/Width Not Applying

Use browser developer tools to manually modify styles and copy the correct value.

23. Reference Server URL from Axios Config in Vue Files

Export baseURL from axios config:

export const baseURL = 'https://127.0.0.1:8081/admin/';

Import in Vue file:

import { baseURL } from "@/plugins/axios";

24. Array Operations

  • Add element: arr.push(4);
  • Add array elements: arr.push(...arr2);
  • Remove element by value: arr = arr.filter(item => item !== 5);
  • Remove by index: arr.splice(2, 1);
  • Array to string: arr.join();
  • Sort by date: arr.sort((a, b) => new Date(b.dateTime) - new Date(a.dateTime));
  • Find first matching: arr.find(item => item.age === 18);
  • Filter: arr.filter(item => item.age === 18);
  • Check existence: arr.some(item => item.id === 2);
  • Replace object: arr[foundIndex] = newObj;
  • Map: arr.map(item => ({ name: item.name, age: item.age }));

25. Text Centering

Flexbox way:

.container {
  display: flex;
  justify-content: center;
  align-items: center;
}

Line-height way:

.text {
  text-align: center;
  line-height: 200px; /* same as height */
}

26. Flex Layout

flex-direction: row, row-reverse, column, column-reverse flex-wrap: nowrap, wrap, wrap-reverse

27. Positioning

  • absolute: relative to nearest positioned ancestor
  • fixed: relative to viewport
  • relative: relative to normal position
  • sticky: hybrid of relative and fixed

28. Scroll-View Examples

Vertical scroll:

<scroll-view scroll-y="true" class="scroll-Y">
  <view class="item_content">
    <!-- items -->
  </view>
</scroll-view>

Horizontal scroll:

<scroll-view scroll-x="true" class="scroll-X" style="white-space: nowrap;">
  <view class="item" style="display: inline-block;">...</view>
  <view class="item" style="display: inline-block;">...</view>
</scroll-view>

29. Box Model

291. Box Width/Height Calculation

Default box-sizing: content-box: Total width = content width + padding + border

With box-sizing: border-box: Total width = set width (includes padding and border)

292. Box Shadow

box-shadow: 2px 2px 10px 2px #e5e5e5;

293. Gradient

background: -webkit-linear-gradient(left, white, rgb(5,239,169));

294. Equal Spacing for Multiple Items

Use justify-content: space-between and calculate vertical margin as percentage of horizontal gap.

.content {
  display: flex;
  justify-content: space-between;
  flex-wrap: wrap;
  .item {
    width: 48%;
    margin-top: 4%; /* 100% - 2*48% = 4% gap */
  }
}

295. Truncate Text with Ellipsis

.ellipsis {
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

296. Auto Height for Content

Set height: auto.

297. Line Clamp for Multiline Ellipsis

.clamp {
  display: -webkit-box;
  -webkit-box-orient: vertical;
  -webkit-line-clamp: 2;
  overflow: hidden;
}

298. Line Height

line-height: 1.5;

299. Word Break and Wrap

.word-break {
  word-break: break-all;
  word-wrap: break-word;
  white-space: pre-wrap;
}

2991. Left Align Last Line in Flex Wrap

.item:last-child {
  margin-right: auto;
}

30. CSS Triangles and Quadrilaterals

Quadrilateral with borders:

.square {
  width: 0;
  height: 0;
  border-top: 50px solid skyblue;
  border-bottom: 50px solid purple;
  border-left: 50px solid pink;
  border-right: 50px solid tomato;
}

Left-pointing triangle:

.left-angle {
  width: 0;
  height: 0;
  border-right: 50px solid yellow;
  border-top: 50px solid transparent;
  border-bottom: 50px solid transparent;
}

31. Scale and Translate

Scale: transform: scale(0.5); Translate: transform: translateY(20px);

32. Dynamic Bottom Position Based on Adjacent Component Height

Use CSS custom properties.

const submit = document.querySelector('.submit');
const height = getComputedStyle(submit).getPropertyValue('height').replace(/[^\d.]/g, '');
document.documentElement.style.setProperty('--bottom-height', height + 'px');
.floating-box {
  bottom: var(--bottom-height);
}

33. Event Priority: Blur vs Click

Wrap click handler in setTimeout to delay blur.

blur() {
  setTimeout(() => {
    this.show = false;
  }, 150);
}

34. Thin Line

.line {
  height: 0;
  border-top: 1rpx solid #c8c7cc;
  transform: scaleY(0.5);
}

Or:

.line {
  height: 1rpx;
  background: red;
  transform: scaleY(0.5);
}

35. Passing Boolean in URL

const url = '/a.com/delFlag=' + (param ? 1 : '');

On receiving page:

onLoad(e) {
  const flag = Boolean(e.delFlag);
}

36. Centering Foreground Image on Background

Use relative parent and absolute positioning.

.container {
  position: relative;
}
.foreground {
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
}

37. Specifying Return Page for Navigation Bar Back Button in App/Web

Use onUnload lifecycle to navigate to specific page.

onUnload() {
  uni.navigateTo({ url: '/pages/chat/chat_record' });
}

38. Format Number to Two Decimal Places

const num = parseFloat(str).toFixed(2);
if (str.indexOf('.') === -1) {
  str = str + '.00';
}

39. Custom Navigation Bar with Right Title

Disable default navigation bar in pages.json:

"navigationStyle": "custom"

Then create custom navigation:

<view class="custom-nav">
  <image src="back.png" @tap="goBack"></image>
  <view class="right-title">Right Title</view>
</view>
.custom-nav {
  display: flex;
  align-items: center;
  justify-content: space-between;
  height: 44px;
}

40. Generate Sequential Array

function generateArray(start, end) {
  return Array.from({ length: end - start + 1 }, (_, i) => start + i);
}

41. Custom Date-Time Picker

Use picker with mode="multiSelector".

<picker :range="dateTimeList" :value="pickerValues" @change="onDateTimeChange" mode="multiSelector">
  {{ dateTimeList[0][monthIndex] }}月{{ dateTimeList[1][dayIndex] }}日 {{ dateTimeList[2][hourIndex] }}:{{ dateTimeList[3][minuteIndex] }}
</picker>

42. Component Data Initialization

Initialize in data using computed values:

data() {
  const currentMonth = new Date().getMonth();
  return {
    monthIndex: currentMonth
  };
}

43. H5 Navigation Bar Display Issue

Hide default navigation bar in App.vue:

uni-page-head {
  display: none;
}

44. Parent Height Following Child

Do not set parent height; let child determine it.

45. Required Field Indicator

.label::before {
  content: "*";
  color: red;
}

46. Watermark Component and Global Registration

Watermark component:

<template>
  <view class="watermark">
    <view class="list">
      <view class="item" v-for="i in 500" :key="i">
        <text>{{ info }}</text>
      </view>
    </view>
  </view>
</template>
<script>
export default {
  name: 'watermark',
  props: {
    info: { type: String, default: 'Watermark' }
  }
}
</script>
<style scoped>
.watermark {
  position: fixed;
  width: 100%; height: 100%; top: 0; left: 0; z-index: 9999;
  pointer-events: none;
  .list {
    width: 500%; height: 400%; top: -50%; left: -50%;
    transform: rotate(-45deg);
    display: flex; flex-wrap: wrap;
    .item {
      font-size: 28px; color: rgba(220,220,220,0.3); padding: 30rpx;
      pointer-events: none;
    }
  }
}
</style>

Global registration in main.js:

import watermark from '@/components/waterMark/waterMark.vue';
Vue.component('watermark', watermark);

47. App-Specific Issues

1. Navigation Bar Display

Custom navigation with status bar height.

2. Back Button Arrow Click

onBackPress(options) {
  if (options.from === 'navigateBack') {
    uni.navigateBack();
    return true;
  }
  return false;
}

3. Status Bar Same Color as Navigation Bar

Increase navigation bar height and add top margin.

4. Prevent Scroll Under Status Bar

Disable immersion:

"app-plus": {
  "statusbar": {
    "immersed": false
  }
}

48. Input Placeholder and Text Color

<input placeholder-style="color:white;" placeholder="Enter phone" style="color: white;"/>

49. Remove Inherited Style from SCSS Mixin

Override with a new class:

.item {
  border: 1px dashed #a7a7a7;
}
.no-border {
  border: none;
}

50. Time Utility Functions

export default {
  secondsToHMS(seconds) { /* ... */ },
  getCurrentTime(pattern) { /* ... */ },
  // etc.
}

51. Dynamic CSS via Custom Properties

<view :style="dynamicStyle"></view>
data() { return { dynamicStyle: '--height: 370px;' } }

52. Gradient Background

background-image: linear-gradient(to top, #fbc2eb 0%, #a6c1ee 100%);

53. Passing Array as Parameter

// API call
findVo({ ids: this.userIds }).then(response => { });

54. Grayscale Overlay

filter: grayscale(100%);
opacity: 0.5;

55. Hide Navigation Bar in Mini Program

"style": {
  "navigationBarTitleText": "Home",
  "navigationStyle": "custom",
  "navigationBarRightButton": {
    "hide": true
  }
}

56. Initialize Child Component in uni-popup

<uni-popup ref="popup">
  <child-component @event="handler"></child-component>
</uni-popup>

Child component mounted() will run when popup opens.

57. Copy to Clipboard on H5

copyText(text) {
  const input = document.createElement('input');
  input.value = text;
  document.body.appendChild(input);
  input.select();
  document.execCommand('Copy');
  uni.showToast({ title: 'Copied', icon: 'none' });
  input.remove();
}

58. Check for Undefined

if (this.value === undefined) {
  // handle
}

59. Pass Multiple Parameters in Change Event

<picker @change="(e) => handleChange(e, index)"></picker>
handleChange(event, index) {}

60. Space Placeholder

<text>&nbsp;&nbsp;</text>

61. Full Screen Background Image

<div class="background">
  <img src="bg.jpg" style="position: absolute; top:0; left:0; width:100%; height:100%; z-index:-1;">
</div>

62. Sticky Position

position: sticky;
top: 0;

63. Prevent Outer Page Scroll, Only Inner ScrollView Scrolls

.outer {
  position: fixed;
  top: 0; left: 0; right: 0; bottom: 0;
  overflow: hidden;
}

64. Disable Page Scroll for Full Screen Image on Android

<view @touchmove.stop.prevent="noop">
  <!-- content -->
</view>
methods: {
  noop() {}
}

Tags: uni-app vue scss wechat-mini-program h5

Posted on Fri, 15 May 2026 00:56:41 +0000 by vineld