修改3.x版本demo首页+readme补充3.x差异

Signed-off-by: madixin <madixin@huawei.com>
This commit is contained in:
madixin 2024-04-10 10:11:41 +08:00
parent 46b12bf7c2
commit 660490aec6
7 changed files with 293 additions and 39 deletions

View File

@ -1,17 +1,47 @@
## 3.0.0-rc.0
使用Image组件替换Canvas组件渲染并重构大部分的实现逻辑提升渲染性能
缺失特性
- gif/webp动图显示与控制
- 支持自定义key的实现
- 不支持drawLifeCycle接口通过canvas自会图片
- mainScaleTypeborder等参数新版本与系统Image保持一致
- gif/webp动图播放与控制
- signature自定义key的实现
- 支持进行图片变换: 支持图像像素源图片变换效果。
- 使用IDrawLifeCycle自绘Canvas
- 抗锯齿相关参数
较2.x版本增强点
- 使用Image组件渲染提升渲染性能
- 使用Image组件代替Canvas组件渲染
- 重构Dispatch分发逻辑支持控制并发请求数支持请求排队队列的优先级
- 支持通过initMemoryCache自定义策略内存缓存策略和大小。
- 支持option自定义实现图片获取/网络下载
- 继承Image的能力支持option传入border设置边框圆角
- 继承Image的能力支持option传入objectFit设置图片缩放
- 并发请求数量,支持请求排队队列的优先级
## 2.1.2-rc.12
- 新增gif播放次数功能
- 新增磁盘预加载返回文件路径接口prefetchToDiskCache
- 新增跳过网络判断缓存或者磁盘中是否存在图片接口isUrlExist
- 删除多余操作磁盘记录读写
- 清除定时器改为Gif图时清除
- uuid改为util.generateRandomUUID()
## 2.1.2-rc.11
- 修复设置磁盘容量最大值出现闪退
- 修复概率出现jscrash问题
- 修复进度条问题
- 修复单帧gif图片加载失败
- removeRunning删除running队列log设置开关
- ImageKnife新增图片宽高自适应功能
- 修复onlyRetrieveFromCache属性(仅磁盘和内存获取资源)失效
- 修改拼写错误
- 新增多线程优先级
- 修复复用场景下图片闪动以及概率错位
- 获取组件宽高改为使用CanvasRenderingContext2D对象获取宽高并修复改变字体大小导致部分图片消失
- 修复获取不到磁盘缓存文件问题
- 修复获取不到网络请求错误回调问题
## 2.1.2-rc.10
- 修复部分gif图片识别成静态图
- 修复同一张图片发送多次请求
- 复用场景缓存到树aboutToRecycle清理定时器
## 2.1.2-rc.9
- 使用taskpool实现多线程加载图片资源

View File

@ -12,22 +12,31 @@
- 支持option自定义实现图片获取/网络下载
- 支持监听网络下载回调进度
- 继承Image的能力支持option传入border设置边框圆角
- 继承Image的能力支持option传入objectFit设置图片缩放
- 继承Image的能力支持option传入objectFit设置图片缩放包括objectFit为auto时根据图片自适应高度
- 支持通过设置transform缩放图片
- 并发请求数量,支持请求排队队列的优先级
- 支持生命周期已销毁的图片,不再发起请求
待实现特性
- gif/webp动图显示与控制
- 内存降采样优化,节约内存的占用
- 支持自定义图片加载和请求并发数量
- 支持声明周期已销毁的图片,不再发起请求
- 支持自定义图片加载
- 支持自定义图片解码
- 支持自定义key的实现
- 支持进行图片变换: 支持图像像素源图片变换效果。
待确认arkui的能力
- 精确获取开发者给组件设置的宽和高
- 动图的显示与控制
注意3.x版本相对2.x版本做了重大的重构主要体现在
- 使用Image组件代替Canvas组件渲染
- 重构Dispatch分发逻辑支持控制并发请求数支持请求排队队列的优先级
- 支持通过initMemoryCache自定义策略内存缓存策略和大小。
- 支持option自定义实现图片获取/网络下载
因此API及能力上目前有部分差异主要体现在
- 不支持drawLifeCycle接口通过canvas自会图片
- mainScaleTypeborder等参数新版本与系统Image保持一致
- gif/webp动图播放与控制
- signature自定义key的实现
- 支持进行图片变换: 支持图像像素源图片变换效果。
- 抗锯齿相关参数
## 下载安装
```
@ -39,7 +48,7 @@ ohpm install @ohos/imageknife
```
ImageKnifeComponent({
ImageKnifeOption: {
src: $r("app.media.app_icon"),
loadSrc: $r("app.media.app_icon"),
placeholderSrc: $r("app.media.loading"),
errorholderSrc: $r("app.media.app_icon"),
objectFit: ImageFit.Auto
@ -51,7 +60,7 @@ ImageKnifeComponent({
```
ImageKnifeComponent({
ImageKnifeOption: {
src: this.localFile,
loadSrc: this.localFile,
placeholderSrc: $r("app.media.loading"),
errorholderSrc: $r("app.media.app_icon"),
objectFit: ImageFit.Auto
@ -63,7 +72,7 @@ ImageKnifeComponent({
```
ImageKnifeComponent({
ImageKnifeOption: {
src:"https://www.openharmony.cn/_nuxt/img/logo.dcf95b3.png",
loadSrc:"https://www.openharmony.cn/_nuxt/img/logo.dcf95b3.png",
placeholderSrc: $r("app.media.loading"),
errorholderSrc: $r("app.media.app_icon"),
objectFit: ImageFit.Auto
@ -75,7 +84,7 @@ ImageKnifeComponent({
```
ImageKnifeComponent({
ImageKnifeOption: {
src: "https://file.atomgit.com/uploads/user/1704857786989_8994.jpeg",
loadSrc: "https://file.atomgit.com/uploads/user/1704857786989_8994.jpeg",
placeholderSrc: $r("app.media.loading"),
errorholderSrc: $r("app.media.app_icon"),
objectFit: ImageFit.Auto,
@ -96,7 +105,7 @@ async function custom(context: Context, src: string | PixelMap | Resource): Prom
```
ImageKnifeComponent({
ImageKnifeOption: {
src:"https://www.openharmony.cn/_nuxt/img/logo.dcf95b3.png",
loadSrc:"https://www.openharmony.cn/_nuxt/img/logo.dcf95b3.png",
progressListener:(progress:number)=>{console.info("ImageKinfe:: call back progress = " + progress)}
}
}).width(100).height(100)
@ -105,7 +114,7 @@ ImageKnifeComponent({
```
ImageKnifeComponent({ ImageKnifeOption:
{
src: $r("app.media.rabbit"),
loadSrc: $r("app.media.rabbit"),
border: {radius:50}
}
}).width(100).height(100)

View File

@ -12,39 +12,51 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import { ImageKnifeComponent, ImageKnifeOption } from "@ohos/imageknife"
import router from '@system.router';
@Entry
@Component
struct Index {
localFile: string = getContext(this).filesDir + "/icon.png"
@State ImageKnifeOption: ImageKnifeOption = {
loadSrc: $r("app.media.rabbit"),
// src:"https://www.openharmony.cn/_nuxt/img/logo.dcf95b3.png",
// src: this.localFile,
placeholderSrc: $r("app.media.loading"),
errorholderSrc: $r("app.media.app_icon"),
objectFit: ImageFit.Contain,
border: { radius: 50 }
}
aboutToAppear(): void {
// 拷贝本地文件
// let icon: Uint8Array = getContext(this).resourceManager.getMediaContentSync($r("app.media.startIcon"));
// let file = fs.openSync(this.localFile, fs.OpenMode.CREATE | fs.OpenMode.READ_WRITE);
// fs.writeSync(file.fd, icon.buffer);
// fs.fsyncSync(file.fd);
// fs.closeSync(file);
}
build() {
Column() {
ImageKnifeComponent({ ImageKnifeOption: this.ImageKnifeOption }).height(200).width(200)
Button("单个图片使用").onClick(()=>{
router.push({
uri: 'pages/SingleImage',
});
})
Button("多图 + Foreach").margin({top:10}).onClick(()=>{
router.push({
uri: 'pages/ManyPhotoShowPage',
});
})
Button("多图 + reuse + LazyForeach").margin({top:10}).onClick(()=>{
router.push({
uri: 'pages/UserPage',
});
})
Button("长图").margin({top:10}).onClick(()=>{
router.push({
uri: 'pages/LongImagePage',
});
})
Button("缩放").margin({top:10}).onClick(()=>{
router.push({
uri: 'pages/TransformPage',
});
})
// Image($r('app.media.rabbit')).objectFit(ImageFit.Contain).height(200).width(200)
// .border({radius:50})
}
.width('100%')

View File

@ -0,0 +1,83 @@
import { ImageKnifeComponent, ImageKnifeOption } from '@ohos/imageknife'
// const logger = new imUtils.logger.IMLogger('Avatar')
class MyImageOption extends ImageKnifeOption {
account?: string
}
@Component
export struct UserAvatar {
@Prop @Watch('userInfoUpdate') userInfo: string = ""
// @Prop userInfo: string = ""
imgSize: number = 100
radius: number = 12
borderSize: number = 0
imgSizes: number = 1
@State ImageKnifeOption: ImageKnifeOption = new ImageKnifeOption()
@StorageProp('WeLink_Mob_fontSize_multiple') @Watch('updateImgSize') WeLink_Mob_fontSize_multiple: number = 0
scaleable: boolean = true;
@State calcImgSize: number = 100
aboutToAppear(): void {
this.userInfoUpdate()
this.setImageSize()
}
setImageSize() {
if (!this.scaleable) {
this.calcImgSize = this.imgSize
} else if (this.WeLink_Mob_fontSize_multiple < 0.9) {
this.calcImgSize = this.imgSize * 0.9
} else if (this.WeLink_Mob_fontSize_multiple > 1.6) {
this.calcImgSize = this.imgSize * 1.6
} else {
this.calcImgSize = this.imgSize * this.WeLink_Mob_fontSize_multiple
}
}
updateImgSize() {
this.setImageSize()
}
aboutToReuse(param: ESObject) {
this.userInfoUpdate()
}
userInfoUpdate() {
// if (uri === 'userInfo' && this.imageKnifeOption.account !== this.userInfo.contactId) return;
// // logger.info(`userInfoUpdate uri=${uri} oldAcc=${this.imageKnifeOption.loadSrc} nowAcc=${this.userInfo.externalHeadUrl}`)
// if (this.userInfo.externalHeadUrl === this.imageKnifeOption.loadSrc && this.userInfo.infoUpdateTime.getTime()
// .toString() === this.imageKnifeOption?.signature?.getKey()) return;
this.ImageKnifeOption = {
//TODO:写死loadSRC场景变更组件大小所有图片不显示
loadSrc: this.userInfo,
placeholderSrc: $r('app.media.icon'),
border: { radius:20,width:5,color:$r('app.color.start_window_background') },
objectFit:ImageFit.Contain
// signature: new ObjectKey(this.userInfo.infoUpdateTime.getTime().toString())
}
}
build() {
Row() {
// Image(this.imageKnifeOption.loadSrc)
ImageKnifeComponent({ ImageKnifeOption: this.ImageKnifeOption })
.borderRadius(this.radius)
.clip(true)
.width(this.calcImgSize)
.height(this.calcImgSize)
.backgroundColor(Color.Pink)
// Image(this.userInfo)
// Text((this.imageKnifeOption.loadSrc as string).split('/')[8])
// .position({ x: 0, y: 0 })
// .zIndex(9)
// .fontSize(12)
// .fontColor('#ff0000')
}
}
}

View File

@ -0,0 +1,119 @@
import { UserAvatar } from './User'
class CommonDataSource <T> implements IDataSource {
private dataArray: T[] = []
private listeners: DataChangeListener[] = []
constructor(element: []) {
this.dataArray = element
}
public getData(index: number) {
return this.dataArray[index]
}
public totalCount(): number {
return this.dataArray.length
}
public addData(index: number, data: T[]): void {
this.dataArray = this.dataArray.concat(data)
this.notifyDataAdd(index)
}
unregisterDataChangeListener(listener: DataChangeListener): void {
const pos = this.listeners.indexOf(listener);
if (pos >= 0) {
this.listeners.splice(pos, 1);
}
}
registerDataChangeListener(listener: DataChangeListener): void {
if (this.listeners.indexOf(listener) < 0) {
this.listeners.push(listener)
}
}
notifyDataAdd(index: number): void {
this.listeners.forEach((listener: DataChangeListener) => {
listener.onDataAdd(index)
})
}
}
@Entry
@Component
struct Index {
@State hotCommendList:CommonDataSource<string> = new CommonDataSource<string>([])
private data:string[] = [
"http://e.hiphotos.baidu.com/image/pic/item/a1ec08fa513d2697e542494057fbb2fb4316d81e.jpg",
"http://c.hiphotos.baidu.com/image/pic/item/30adcbef76094b36de8a2fe5a1cc7cd98d109d99.jpg",
"http://h.hiphotos.baidu.com/image/pic/item/7c1ed21b0ef41bd5f2c2a9e953da81cb39db3d1d.jpg",
"http://g.hiphotos.baidu.com/image/pic/item/55e736d12f2eb938d5277fd5d0628535e5dd6f4a.jpg",
"http://e.hiphotos.baidu.com/image/pic/item/4e4a20a4462309f7e41f5cfe760e0cf3d6cad6ee.jpg",
"http://b.hiphotos.baidu.com/image/pic/item/9d82d158ccbf6c81b94575cfb93eb13533fa40a2.jpg",
"http://e.hiphotos.baidu.com/image/pic/item/4bed2e738bd4b31c1badd5a685d6277f9e2ff81e.jpg",
"http://g.hiphotos.baidu.com/image/pic/item/0d338744ebf81a4c87a3add4d52a6059252da61e.jpg",
"http://a.hiphotos.baidu.com/image/pic/item/f2deb48f8c5494ee5080c8142ff5e0fe99257e19.jpg",
"http://f.hiphotos.baidu.com/image/pic/item/4034970a304e251f503521f5a586c9177e3e53f9.jpg",
"http://b.hiphotos.baidu.com/image/pic/item/279759ee3d6d55fbb3586c0168224f4a20a4dd7e.jpg",
"http://img2.xkhouse.com/bbs/hfhouse/data/attachment/forum/corebbs/2009-11/2009113011534566298.jpg",
"http://a.hiphotos.baidu.com/image/pic/item/e824b899a9014c087eb617650e7b02087af4f464.jpg",
"http://c.hiphotos.baidu.com/image/pic/item/9c16fdfaaf51f3de1e296fa390eef01f3b29795a.jpg",
"http://d.hiphotos.baidu.com/image/pic/item/b58f8c5494eef01f119945cbe2fe9925bc317d2a.jpg",
"http://h.hiphotos.baidu.com/image/pic/item/902397dda144ad340668b847d4a20cf430ad851e.jpg",
"http://b.hiphotos.baidu.com/image/pic/item/359b033b5bb5c9ea5c0e3c23d139b6003bf3b374.jpg",
"http://a.hiphotos.baidu.com/image/pic/item/8d5494eef01f3a292d2472199d25bc315d607c7c.jpg",
"http://b.hiphotos.baidu.com/image/pic/item/e824b899a9014c08878b2c4c0e7b02087af4f4a3.jpg",
"http://g.hiphotos.baidu.com/image/pic/item/6d81800a19d8bc3e770bd00d868ba61ea9d345f2.jpg",
"https://hbimg.huabanimg.com/cc6af25f8d782d3cf3122bef4e61571378271145735e9-vEVggB",
'https://img-blog.csdnimg.cn/20191215043500229.png',
'https://img-blog.csdn.net/20140514114029140',
'https://hbimg.huabanimg.com/95a6d37a39aa0b70d48fa18dc7df8309e2e0e8e85571e-x4hhks_fw658/format/webp',
]
aboutToAppear(): void {
this.hotCommendList.addData(this.hotCommendList.totalCount(),this.data)
AppStorage.set("WeLink_Mob_fontSize_multiple",1)
}
build() {
Column() {
Button("bigger").onClick(()=>{
AppStorage.set("WeLink_Mob_fontSize_multiple",1.6)
})
Button("small").onClick(()=>{
AppStorage.set("WeLink_Mob_fontSize_multiple",0.8)
})
List(){
LazyForEach(this.hotCommendList,(item:string)=>{
ListItem(){
ReuseImage({
userInfo:item
}).width("100%").height("100%").backgroundColor(Color.Yellow)
}.width(200).height(200).margin({bottom:5})
})
}
// .cachedCount(20)
.width("100%")
.height("100%")
.backgroundColor(0xFAEEE0)
}.width('100%').height("100%")
}
}
@Reusable
@Component
struct ReuseImage {
@State userInfo:string = ""
aboutToReuse(params: ESObject): void {
this.userInfo = params.userInfo
}
build() {
Column(){
UserAvatar({
userInfo:this.userInfo
})
}.width("100%").height("100%")
}
}

View File

@ -5,6 +5,7 @@
"pages/SingleImage",
"pages/ManyPhotoShowPage",
"pages/LongImagePage",
"pages/TransformPage"
"pages/TransformPage",
"pages/UserPage"
]
}