iPhone获取字符串高度和宽度 …

本文介绍了一种使用UILabel显示长字符串并使其自动换行的方法。通过设置字体大小、宽度约束及换行模式,UILabel能准确计算出字符串的换行高度。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

通常我们使用UILabel只是显示较短的字符串,下面是一种获取字符串的换行高度,显示

 

  代码如下所示:

  1. NSString* str @"test testImplement viewDidLoad to do additional setup after loading the view, typically from nib";  
  2.   
  3. //CGSize labelSize  [str sizeWithFont:[UIFont systemFontOfSize:14]];      
  4.   
  5. //可以精确计算字符串的换行,高宽等   
  6. CGSize labelSize [str sizeWithFont:[UIFont boldSystemFontOfSize:17.0f]  
  7.                         constrainedToSize:CGSizeMake(280, 100)   
  8.                         lineBreakMode:UILineBreakModeCharacterWrap];  
  9.   
  10. UILabel* label [[UILabel alloc] init];  
  11. label.frame CGRectMake(50, 20, labelSize.width, labelSize.height);  
  12. label.backgroundColor [UIColor whiteColor];  
  13. label.text str;  
  14. label.font [UIFont systemFontOfSize:17.0f];  
  15. label.numberOfLines 0;  
  16. label.lineBreakMode UILineBreakModeCharacterWrap;  
  17.   
  18. [self.view addSubview:label];  
  19. [label release];  
        NSString* str = @"test testImplement viewDidLoad to do additional setup after loading the view, typically from a nib";

        //CGSize labelSize =  [str sizeWithFont:[UIFont systemFontOfSize:14]];   
        
        //可以精确计算字符串的换行,高宽等
        CGSize labelSize = [str sizeWithFont:[UIFont boldSystemFontOfSize:17.0f]
                                                constrainedToSize:CGSizeMake(280, 100) 
                                                    lineBreakMode:UILineBreakModeCharacterWrap];
        
        UILabel* label = [[UILabel alloc] init];
        label.frame = CGRectMake(50, 20, labelSize.width, labelSize.height);
        label.backgroundColor = [UIColor whiteColor];
        label.text = str;
        label.font = [UIFont systemFontOfSize:17.0f];
        label.numberOfLines = 0;
        label.lineBreakMode = UILineBreakModeCharacterWrap;
        
        [self.view addSubview:label];
        [label release];

<template> <view class="detail-container"> <view class="detail-title">{{ detail.title }}</view> <view class="detail-date">发布日期:{{ formatDate(detail.publishDate) }}</view> <!-- 使用处理后的富文本内容 --> <rich-text class="detail-content" :nodes="parseContent(detail.content)" /> <!-- 返回顶部按钮 --> <view class="back-to-top" :class="{ show: showBackTop }" @click="scrollToTop" > <uni-icons type="arrow-up" size="24" color="#fff"></uni-icons> </view> </view> </template> <script setup> import { ref, onMounted, onUnmounted } from 'vue'; import { onLoad } from '@dcloudio/uni-app'; const detail = ref({ title: '', publishDate: '', content: '' }); // 控制返回顶部按钮显示 const showBackTop = ref(false); onLoad((options) => { if (options && options.articleId) { fetchDetail(options.articleId); } else { uni.showToast({ title: '缺少文章ID', icon: 'error' }); } }); // 添加页面滚动监听 onMounted(() => { window.addEventListener('scroll', handleScroll); }); // 移除滚动监听 onUnmounted(() => { window.removeEventListener('scroll', handleScroll); }); // 处理滚动事件 - 控制返回顶部按钮显示 const handleScroll = () => { // 获取滚动位置 const scrollTop = window.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop; // 当滚动超过300px时显示按钮 showBackTop.value = scrollTop > 300; }; // 平滑滚动到顶部 const scrollToTop = () => { uni.pageScrollTo({ scrollTop: 0, duration: 300 }); }; // 格式化日期 const formatDate = (dateStr) => { if (!dateStr) return ''; const date = new Date(dateStr); return `${date.getFullYear()}-${(date.getMonth() + 1).toString().padStart(2, '0')}-${date.getDate().toString().padStart(2, '0')}`; }; // 优化的富文本处理函数 - 图片大小自适应优化 const parseContent = (str) => { if (!str) return ''; // 1. 处理双重转义 const handleDoubleEscapes = (input) => { return input .replace(/\\\\u([0-9a-fA-F]{4})/g, (match, hex) => { return String.fromCharCode(parseInt(hex, 16)); }) .replace(/\\\\/g, '\\') .replace(/\\"/g, '"') .replace(/\\\//g, '/'); }; // 2. 解码标准Unicode转义序列 const decodeUnicode = (input) => { return input.replace(/\\u([0-9a-fA-F]{4})/g, (match, grp) => String.fromCharCode(parseInt(grp, 16)) ); }; // 3. 执行双重转义处理 let processedHtml = handleDoubleEscapes(str); // 4. 解码标准Unicode processedHtml = decodeUnicode(processedHtml); // 5. 处理空格转义 processedHtml = processedHtml.replace(/\\u00a0|\\u0020/g, ' '); // 6. 优化图片处理 - 添加自适应大小居中 processedHtml = processedHtml.replace( /<img[^>]+src="([^"]+)"[^>]*>/gi, (match, src) => { // 处理URL中的转义字符 const cleanSrc = src .replace(/\\/g, '') .replace(/\s+/g, '%20'); // 添加图片自适应居中样式 return ` <img src="${cleanSrc}" class="adaptive-img" style="max-width:100%!important;height:auto!important;display:block!important;margin:20rpx auto;border-radius:16rpx;object-fit:contain;" /> `; } ); // 7. 移除所有内联的widthheight属性 processedHtml = processedHtml.replace(/(<img[^>]*)width="[^"]*"/gi, '$1'); processedHtml = processedHtml.replace(/(<img[^>]*)height="[^"]*"/gi, '$1'); // 8. 处理其他HTML实体 processedHtml = processedHtml .replace(/&nbsp;/g, ' ') .replace(/</g, '<') .replace(/>/g, '>') .replace(/&/g, '&') .replace(/"/g, '"') .replace(/'/g, "'"); return processedHtml; }; // 获取详情数据 const fetchDetail = async (id) => { try { uni.showLoading({ title: '加载中...', mask: true }); const res = await uni.request({ url: `/api/incorruptFront/frontArticleDet/${id}`, method: 'GET', header: { 'Content-Type': 'application/json; charset=utf-8' } }); // 兼容不同平台响应结构 const response = res[1] || res; if (response.data && response.data.code === 200) { detail.value = response.data.data; } else { throw new Error(response.data?.msg || '数据加载失败'); } } catch (error) { uni.showToast({ title: error.message || '网络请求失败', icon: 'none', duration: 3000 }); console.error('API请求错误:', error); } finally { uni.hideLoading(); } }; </script> <style scoped> .detail-container { padding: 30rpx; background-color: #fff; line-height: 1.8; min-height: 100vh; position: relative; max-width: 100%; overflow-x: hidden; } .detail-title { font-size: 40rpx; font-weight: bold; margin-bottom: 20rpx; color: #333; text-align: center; line-height: 1.5; padding: 0 20rpx; } .detail-date { font-size: 26rpx; color: #999; margin-bottom: 40rpx; text-align: center; } /* 富文本内容样式增强 */ .detail-content { font-size: 30rpx; color: #555; text-align: left; padding: 0 20rpx; max-width: 100%; overflow-x: hidden; /* 全局段落样式 */ :deep(p) { margin: 25rpx 0; line-height: 1.8; text-align: justify; text-indent: 2em; /* 添加首行缩进 */ max-width: 100%; overflow-x: hidden; } /* 图片样式 - 优化自适应居中 */ :deep(.adaptive-img) { max-width: 100% !important; width: auto !important; height: auto !important; display: block !important; margin: 30rpx auto !important; border-radius: 16rpx; box-shadow: 0 8rpx 24rpx rgba(0,0,0,0.1); background-color: #f8f8f8; transition: transform 0.3s ease, opacity 0.3s ease; opacity: 0.95; object-fit: contain; } /* 修复图片内联样式可能被覆盖的问题 */ :deep(img) { max-width: 100% !important; height: auto !important; display: block !important; margin: 30rpx auto !important; } /* 图片加载动画 */ :deep(.adaptive-img:not([src])) { background: linear-gradient(90deg, #f0f0f0 25%, #e0e0e0 50%, #f0f0f0 75%); background-size: 200% 100%; animation: loading 1.5s infinite; } /* 图片悬停效果 */ :deep(.adaptive-img:hover) { transform: scale(1.02); opacity: 1; box-shadow: 0 12rpx 30rpx rgba(0,0,0,0.15); } /* 标题样式 */ :deep(h1) { font-size: 40rpx; font-weight: bold; margin: 40rpx 0 20rpx; text-indent: 0; max-width: 100%; overflow-x: hidden; } /* 响应式图片处理 */ @media (max-width: 600rpx) { :deep(.adaptive-img) { max-height: 400rpx !important; border-radius: 12rpx; margin: 20rpx auto; } } } /* 特殊设备适配 */ @media (max-height: 700px) { :deep(.adaptive-img) { max-height: 300rpx !important; } } /* 返回顶部按钮样式 */ .back-to-top { position: fixed; right: 40rpx; bottom: 40rpx; width: 80rpx; height: 80rpx; border-radius: 50%; background-color: #007AFF; display: flex; justify-content: center; align-items: center; box-shadow: 0 6rpx 16rpx rgba(0, 122, 255, 0.3); opacity: 0; transform: translateY(120rpx); transition: all 0.4s cubic-bezier(0.175, 0.885, 0.32, 1.275); z-index: 999; } .back-to-top.show { opacity: 0.9; transform: translateY(0); } .back-to-top:active { transform: scale(0.95) translateY(0); background-color: #0062cc; } /* 添加悬停效果 */ @media (hover: hover) { .back-to-top:hover { opacity: 1; transform: translateY(-10rpx); } } /* 图片加载动画 */ @keyframes loading { 0% { background-position: 200% 0; } 100% { background-position: -200% 0; } } /* 按钮动画 */ @keyframes bounce { 0%, 20%, 50%, 80%, 100% {transform: translateY(0);} 40% {transform: translateY(-20rpx);} 60% {transform: translateY(-10rpx);} } /* 添加按钮动画效果 */ .back-to-top.show { animation: bounce 1.5s ease infinite; } </style> 这个是uniapp+vue3的移动端页面代码,我先要固定宽高富文本里的图片使得其单独占一行如果是手机打开就宽度就是手机宽度最大高度固定适用于手机屏幕,浏览器打开最大宽高固定
最新发布
08-22
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值