通过js来判断是否是横屏如果是就自刷新页面解决横屏之后只有屏幕一半宽度的问题

判断页面是横屏还是竖屏

    window.addEventListener("load", rotate, false);
    window.addEventListener("onorientationchange" in window ? "orientationchange" : "resize", rotate, false);
	function rotate() {
      if (window.orientation == 180 || window.orientation == 0) {
      	console.log('竖屏')
      }
      if (window.orientation == 90 || window.orientation == -90) {
      	console.log('横屏')
      }
    }

如果是横屏自刷新页面 (在App.vue)写入

<template>
  <div id="app">
    <keep-alive>
      <router-view v-if="$route.meta.keepAlive || isRouterAlive" />
    </keep-alive>
    <router-view v-if="!$route.meta.keepAlive || isRouterAlive" />
  </div>
</template>

<script>
  export default {
    name: 'App',
    provide() {
      // 在祖先组件中通过 provide 提供变量
      return {
        reload: this.reload, //  声明一个变量
      }
    },
    data() {
      return {
        isRouterAlive: true, // 控制 router-view 是否显示达到刷新效果
      }
    },
    methods: {
      // provide中声明的变量
      reload() {
        // 通过 this.isRouterAlive 控制 router-view 达到刷新效果
        this.isRouterAlive = false
        this.$nextTick(function () {
          this.isRouterAlive = true
        })
      },
    },
  }
</script>

在你需要自刷新的页面中写入

<template>
  <div v-cloak id="main" class="transform">
   
  </div>
</template>

<script>
  export default {
    // inject: ['reload'], // 使用 inject 注入 reload 变量
    data() {
      return {
      }
    },
   
    mounted() {
       window.addEventListener('load', rotate, false)
       window.addEventListener(
         'onorientationchange' in window ? 'orientationchange' : 'resize',
         rotate,
         false
       )
		// 与app交互的 横屏方法  
       this.getOrientation()
       function rotate() {
         if (window.orientation == 180 || window.orientation == 0) {
           console.log('竖屏')
         }
         if (window.orientation == 90 || window.orientation == -90) {
          console.log('横屏')
          // 自刷新
           this.reload() // 直接使用
        }
       }
    },

通过js来判断是否是横屏如果是就自刷新页面解决横屏之后只有屏幕一半宽度的问题

css 旋转90度来强制横屏方法

 #main {
    width: 100%;
    height: 100%;
  }

  @media screen and (orientation: portrait) {
    #main {
      position: absolute;
      width: 100vh;
      height: 100vw;
      top: 0;
      left: 100vw;
      -webkit-transform: rotate(90deg);
      -moz-transform: rotate(90deg);
      -ms-transform: rotate(90deg);
      transform: rotate(90deg);
      transform-origin: 0% 0%;
    }
  }

  @media screen and (orientation: landscape) {
    #main {
      position: absolute;
      top: 0;
      left: 0;
      width: 100vw;
      height: 100vh;
    }
  }

Vue自创插件发布到npm以及使用方法

目标:创建my-popup-selector下拉框组件,并发布到npm,效果如下图:
在这里插入图片描述
禁用时样式:
在这里插入图片描述

①创建vue项目:

my-popup-selector

②项目目录结构截图如下:

在这里插入图片描述

③在项目根目录新建 packages/ 文件夹用于存放组件,由于 packages/ 是新增的,webpack无法获取编译,因此需要在webpack配置文件里加上相关配置

④在项目根目录新建 vue.config.js 配置文件,并写入一下配置:

module.exports = {
 css: { // 是否将组件中的 CSS 提取至一个独立的 CSS 文件中 (而不是动态注入到 JavaScript 中的 inline 代码)。
   extract: false, // 生产环境下是 true,开发环境下是 false
 },
 // 扩展 webpack 配置,使 packages 加入编译
 // chainWebpack 是一个函数,会接收一个基于 webpack-chain 的 ChainableConfig 实例。允许对内部的 webpack 配置进行更细粒度的修改
 chainWebpack: config => {
   config.module
     .rule('js')
     .include
     .add(__dirname + 'packages') // 注意这里需要绝对路径,所以要拼接__dirname
     .end()
     .use('babel')
     .loader('babel-loader')
     .tap(options => {
       // 修改它的选项...
       return options
     })
 }
}

⑤在 packages/ 文件夹下创建组件,新建 vue-popup-selector/ 文件夹和 index.js 文件,截图如下:
⑥在 my-popup-selector/ 文件加下新建 VueAmazingSelector.vue 组件文件和 index.js 文件,截图如下:

5 - 6步骤图

⑦在 VueAmazingSelector.vue 中编写组件代码:

<template>
  <div class="m-amazing-select" :style="`height: ${height}px;`">
    <div
      :class="['m-select-wrap', {'hover': !disabled, 'focus': showOptions, 'disabled': disabled}]"
      :style="`width: ${width - 2}px; height: ${height - 2}px;`"
      tabindex="0"
      @mouseenter="onInputEnter"
      @mouseleave="onInputLeave"
      @blur="activeBlur && !disabled ? onBlur() : e => e.preventDefault()"
      @click="disabled ? e => e.preventDefault() : openSelect()">
      <div
        :class="['u-select-input', {'placeholder': !selectedName}]"
        :style="`line-height: ${height - 2}px;width: ${width - 37}px; height: ${height - 2}px;`"
        :title="selectedName"
      >{{ selectedName || placeholder }}</div>
      <svg :class="['triangle', {'rotate': showOptions, 'show': !showClose}]" viewBox="64 64 896 896" data-icon="down" aria-hidden="true" focusable="false"><path d="M884 256h-75c-5.1 0-9.9 2.5-12.9 6.6L512 654.2 227.9 262.6c-3-4.1-7.8-6.6-12.9-6.6h-75c-6.5 0-10.3 7.4-6.5 12.7l352.6 486.1c12.8 17.6 39 17.6 51.7 0l352.6-486.1c3.9-5.3.1-12.7-6.4-12.7z"></path></svg>
      <svg @click.stop="onClear" :class="['close', {'show': showClose}]" focusable="false" data-icon="close-circle" aria-hidden="true" viewBox="64 64 896 896"><path d="M512 64C264.6 64 64 264.6 64 512s200.6 448 448 448 448-200.6 448-448S759.4 64 512 64zm165.4 618.2l-66-.3L512 563.4l-99.3 118.4-66.1.3c-4.4 0-8-3.5-8-8 0-1.9.7-3.7 1.9-5.2l130.1-155L340.5 359a8.32 8.32 0 01-1.9-5.2c0-4.4 3.6-8 8-8l66.1.3L512 464.6l99.3-118.4 66-.3c4.4 0 8 3.5 8 8 0 1.9-.7 3.7-1.9 5.2L553.5 514l130 155c1.2 1.5 1.9 3.3 1.9 5.2 0 4.4-3.6 8-8 8z"></path></svg>
    </div>
    <transition name="fade">
      <div
        v-show="showOptions"
        class="m-options-panel"
        @mouseenter="onEnter"
        @mouseleave="onLeave"
        :style="`top: ${height + 6}px; line-height: ${height - 12}px; max-height: ${ num * (height - 2) }px; width: ${width}px;`">
        <p
          v-for="(option, index) in options" :key="index"
          :class="['u-option', {'option-selected': option[label]===selectedName, 'option-hover': !option.disabled&&option[value]===hoverValue, 'option-disabled': option.disabled }]"
          :title="option[label]"
          @mouseenter="onHover(option[value])"
          @click="option.disabled ? e => e.preventDefault() : onChange(option[value], option[label], index)">
          {{ option[label] }}
        </p>
      </div>
    </transition>
  </div>
</template>
<script>
export default {
  name: 'VueAmazingSelector',
  model: {
    prop: 'selectedValue',
    event: 'model'
  },
  props: {
    options: { // 选项数据
      type: Array,
      default: () => []
    },
    label: { // 选择器字典项的文本字段名
      type: String,
      default: 'label'
    },
    value: { // 选择器字典项的值字段名
      type: String,
      default: 'value'
    },
    placeholder: { // 选择框默认文字
      type: String,
      default: '请选择'
    },
    disabled: { // 是否禁用下拉
      type: Boolean,
      default: false
    },
    allowClear: { // 是否支持清除
      type: Boolean,
      default: false
    },
    width: { // 选择框宽度
      type: Number,
      default: 200
    },
    height: { // 选择框高度
      type: Number,
      default: 36
    },
    num: { // 下拉面板最多能展示的下拉项数,超过后滚动显示
      type: Number,
      default: 6
    },
    selectedValue: { // 当前选中的option条目(v-model)
      type: [Number, String],
      default: null
    }
  },
  data () {
    return {
      selectedName: null,
      hoverValue: null, // 鼠标悬浮项的value值
      activeBlur: true, // 是否激活blur事件
      showClose: false, // 清除按钮显隐
      showOptions: false // options面板
    }
  },
  watch: {
    options () {
      this.initSelector()
      console.log('options')
    },
    selectedValue () {
      this.initSelector()
      console.log('selectedValue')
    }
  },
  mounted () {
    this.initSelector()
  },
  methods: {
    initSelector () {
      if (this.selectedValue) {
        const target = this.options.find(option => option[this.value] === this.selectedValue)
        if (target) {
          this.selectedName = target[this.label]
          this.hoverValue = target[this.value]
        } else {
          this.selectedName = this.selectedValue
          this.hoverValue = null
        }
      } else {
        this.selectedName = null
        this.hoverValue = null
      }
    },
    onBlur () {
      if (this.showOptions) {
        this.showOptions = false
      }
    },
    onInputEnter () {
  // console.log('input enter')
      if (this.allowClear && this.selectedName) {
        this.showClose = true
      }
    },
    onInputLeave () {
      // console.log('input leave')
      if (this.allowClear && this.showClose) {
        this.showClose = false
      }
    },
    onHover (value) {
      this.hoverValue = value
    },
    onEnter () {
      this.activeBlur = false
    },
    onLeave () {
      this.hoverValue = null
      this.activeBlur = true
    },
    openSelect () {
      this.showOptions = !this.showOptions
      if (!this.hoverValue && this.selectedName) {
        const target = this.options.find(option => option[this.label] === this.selectedName)
        this.hoverValue = target ? target[this.value] : null
      }
    },
    onClear () {
      this.showClose = false
      this.selectedName = null
      this.hoverValue = null
    },
    onChange (value, label, index) { // 选中下拉项后的回调
      if (this.selectedValue !== value) {
        this.selectedName = label
        this.hoverValue = value
        this.$emit('model', value)
        this.$emit('change', value, label, index)
      }
      this.showOptions = false
    }
  }
}
</script>
<style lang="less" scoped>
@themeColor: #1890ff; // 自定义主题色
P {
  margin: 0;
}
.m-amazing-select {
  position: relative;
  display: inline-block;
  font-size: 14px;
  font-weight: 400;
  color: rgba(0,0,0,.65);
}
.fade-enter-active, .fade-leave-active {
  transform: scaleY(1);
  transform-origin: 0% 0%;
  opacity: 1;
  transition: all .3s;
}
.fade-enter {
  transform: scaleY(0.8);
  transform-origin: 0% 0%;
  opacity: 0;
}
.fade-leave-to {
  transform: scaleY(1);
  opacity: 0;
}
.m-select-wrap {
  position: relative;
  display: inline-block;
  border: 1px solid #d9d9d9;
  border-radius: 4px;
  cursor: pointer;
  transition: all .3s cubic-bezier(.645,.045,.355,1);
  .u-select-input {
    display: block;
    text-align: left;
    margin-left: 11px;
    margin-right: 24px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
  }
  .placeholder {
    color: #bfbfbf;
  }
  .triangle {
    position: absolute;
    top: 0;
    bottom: 0;
    margin: auto 0;
    right: 12px;
    width: 12px;
    height: 12px;
    fill: rgba(0,0,0,.25);
    opacity: 0;
    pointer-events: none;
    transition: all 0.3s ease-in-out;
  }
  .rotate {
    transform: rotate(180deg);
    -webkit-transform: rotate(180deg);
  }
  .close {
    opacity: 0;
    pointer-events: none;
    transition: all 0.3s ease-in-out;
    position: absolute;
    top: 0;
    bottom: 0;
    margin: auto 0;
    right: 12px;
    width: 12px;
    height: 12px;
    fill: rgba(140, 140, 140, 0.6);
    &:hover {
      fill: rgba(100, 100, 100,.8);
    }
  }
  .show {
    opacity: 1;
    pointer-events: auto;
  }
}
.hover { // 悬浮时样式
  &:hover {
    border-color: @themeColor;
  }
}
.focus { // 激活时样式
  border-color: @themeColor;
  box-shadow: 0 0 0 2px fade(@themeColor, 20%);
}
.disabled { // 下拉禁用样式
  color: rgba(0,0,0,.25);
  background: #f5f5f5;
  user-select: none;
  cursor: not-allowed;
}
.m-options-panel {
  position: absolute;
  z-index: 999;
  overflow: auto;
  background: #FFF;
  padding: 4px 0;
  border-radius: 4px;
  box-shadow: 0 2px 8px rgba(0,0,0,15%);
  .u-option { // 下拉项默认样式
    text-align: left;
    position: relative;
    display: block;
    padding: 5px 12px;
    font-weight: 400;
    overflow: hidden;
    white-space: nowrap;
    text-overflow: ellipsis;
    cursor: pointer;
    transition: background .3s ease;
  }
  .option-selected { // 被选中的下拉项样式
    font-weight: 600;
    background: #fafafa;
  }
  .option-hover { // 悬浮时的下拉项样式
    background: #e6f7ff;
    // background: saturate(fade(@themeColor, 12%), 30%);
  }
  .option-disabled { // 禁用某个下拉选项时的样式
    color: rgba(0,0,0,.25);
    user-select: none;
    cursor: not-allowed;
  }
}
</style>

⑧在 my-popup-selector/index.js 中导出组件

// 引入组件
import VueAmazingSelector from './VueAmazingSelector.vue'
 
// 为组件提供 install 安装方法,供按需引入
VueAmazingSelector.install = (Vue) => {
  Vue.component(VueAmazingSelector.name, VueAmazingSelector)
}
 
// 导出组件
export default VueAmazingSelector

⑨在 packages/index.js 文件中对整个组件库进行导出

import VueAmazingSelector from './vue-amazing-selector'
// 存储组件列表
const components = [
  VueAmazingSelector
]
/* 
  定义install 方法,接收Vue作为参数,如果使用use注册插件,则所有的组件都将被注册
*/
const install = function (Vue) {
  // 判断是否安装
  if (install.installed) { return }
  // 遍历所有组件
  components.map(component => {
    Vue.component(component.name, component)
  })
}
// 判断是否引入文件
if (typeof window !== 'undefined' && window.Vue) {
  install(window.Vue)
}
export {
  VueAmazingSelector
}
export default {
  install
}

在 src/main.js 中导入刚创建的组件,检测是否正常可用

import VueAmazingSelector from '../packages'
Vue.use(VueAmazingSelector)
// 在 App.vue 中引用,并启动项目查看

app.vue代码

	<template>
  <VueAmazingSelector
    :options="options"
    label="label"
    value="value"
    placeholder="请选择"
    :disabled="false"
    :width="160"
    :height="36"
    :num="6"
    v-model="selectedValue"
    @change="onChange" />
</template>
<script>
export default {
  name: 'App',
  data () {
    return {
      options: [
        {
          label: '北京市',
          value: 1
        },
        {
          label: '上海市上海市上海市上海市',
          value: 2,
          disabled: true
        },
        {
          label: '郑州市',
          value: 3
        },
        {
          label: '纽约市纽约市纽约市纽约市',
          value: 4
        },
        {
          label: '旧金山',
          value: 5
        },
        {
          label: '悉尼市',
          value: 6
        },
        {
          label: '伦敦市',
          value: 7
        },
        {
          label: '巴黎市',
          value: 8
        }
      ],
      selectedValue: 1
    }
  },
  watch: {
    selectedValue (to) {
      console.log('selectedValue:', to)
    }
  },
  mounted () {
    setTimeout(() => { // 模拟接口调用
      this.selectedValue = 3
    }, 1000)
  },
  methods: {
    onChange (value, label, index) {
      console.log('item:', value, label, index)
    }
  }
}
</script>

⑪在 package.json 的 scripts 中添加一条编译命令


--target: 构建目标,默认为应用模式。这里修改为 lib 启用库模式。
--dest : 输出目录,默认 dist。这里我们改成 lib
[entry]: 最后一个参数为入口文件,默认为 src/App.vue。这里我们指定编译 packages/ 组件库目录。
 
"scripts": {
	"lib": "vue-cli-service build --target lib --name selector --dest lib packages/index.js"
}

⑫执行编译命令

yarn lib(或num run lib)

执行结果如下图:

在这里插入图片描述

然后在项目根目录会生成如下图所示文件夹:

在这里插入图片描述

⑬在终端执行 npm init 初始化包配置文件package.json 可忽略这一步

package.json部分截图如下:

在这里插入图片描述
name: 包名,该名字是唯一的。可在 npm 官网搜索名字,不可重复。
version: 版本号,每次发布至 npm 需要修改版本号,不能和历史版本号相同。
main: 入口文件,需指向最终编译后的包文件。
author:作者

private:是否私有,需要修改为 false 才能发布到 npm

⑭在项目根目录创建 .npmignore 文件,设置忽略发布的文件,类似 .gitignore 文件

只有编译后的 lib 目录、package.json、README.md是需要被发布的

# 忽略目录

.DS_Store

node_modules

packages/

public/

src/

# 忽略指定文件

.eslintrc.cjs

.gitignore

.npmignore

.npmrc

babel.config.js

vue.config.js

yarn.lock

*.map

⑮编写README.md文件(使用markdown格式)

参考文档: http://markdown.p2hp.com/index.html
# vue-amazing-selector
 
## An Amazing Select Component For Vue2
 
## Install & Use
 
```sh
npm install vue-amazing-selector
#or
yarn add vue-amazing-selector

Import and register component

Global

import Vue from 'vue'
import VueAmazingSelector from 'vue-amazing-selector'
Vue.use(VueAmazingSelector)

Local

<template>
  <VueAmazingSelector
    :options="options"
    label="label"
    value="value"
    placeholder="请选择"
    :disabled="false"
    :width="160"
    :height="36"
    :num="6"
    v-model="selectedValue"
    @change="onChange" />
</template>
<script>
export default {
  name: 'App',
  data () {
    return {
      options: [
        {
          label: '北京市',
          value: 1
        },
        {
          label: '上海市上海市上海市上海市',
          value: 2,
          disabled: true
        },
        {
          label: '郑州市',
          value: 3
        },
        {
          label: '纽约市纽约市纽约市纽约市',
          value: 4
        },
        {
          label: '旧金山',
          value: 5
        },
        {
          label: '悉尼市',
          value: 6
        },
        {
          label: '伦敦市',
          value: 7
        },
        {
          label: '巴黎市',
          value: 8
        }
      ],
      selectedValue: 1
    }
  },
  watch: {
    selectedValue (to) {
      console.log('selectedValue:', to)
    }
  },
  mounted () {
    setTimeout(() => { // 模拟接口调用
      this.selectedValue = 3
    }, 1000)
  },
  methods: {
    onChange (value, label, index) {
      console.log('item:', value, label, index)
    }
  }
}
</script>
 
## Props
 
| 属性 | 说明 | 类型 | 默认值 |
| :--- | :--- | :--- | :--- |
options | 选项数据 | Array | []
label | 选择器字典项的文本字段名 | String | label
value | 选择器字典项的值字段名 | String | value
placeholder | 选择框默认文字 | String | 请选择
disabled | 是否禁用下拉 | Boolean | false
allowClear | 是否支持清除 | Boolean | false
width | 选择框宽度 | Number | 200
height | 选择框高度 | Number | 36
num | 下拉面板最多能展示的下拉项数,超过后滚动显示 | Number | 6
selectedValue | (v-model)当前选中的option条目 | /Number/String | null
 
## Events
 
事件名 | 说明 | 返回值
:--- | :--- | :---
change | 选择某项下拉后的回调函数 | value, label, index(value值,label文本值,index索引值)

⑯登录npm

如果没有npm账号,可以去npm官网( npm) 注册一个账号

注册成功后在本地查看npm镜像:

npm config get registry

输出:https://registry.npmjs.org 即可

如果不是则需要设置为npm镜像:

npm config set registry https://registry.npmjs.org

然后在终端执行:

npm login

依次输入用户名,密码,邮箱

输出Logged in as…即可

npm whoami // 查看当前用户是否已登录

在这里插入图片描述

⑰发布组件到npm

在终端执行:npm publish

发布成功后即可在npm官网搜索到该组件,如下图;并可以通过 npm install my-popup-selector(或yarn add my-popup-selector)进行安装
在这里插入图片描述

⑱在要使用的项目中安装并注册插件

yarn add my-popup-selector

// 在 main.js 文件中引入并注册:
import Vue from 'vue'
import VueAmazingSelector from 'my-popup-selector'
Vue.use(VueAmazingSelector)

在要使用组件的页面直接使用即可:

<template>
  <VueAmazingSelector
    :options="options"
    label="label"
    value="value"
    placeholder="请选择"
    :disabled="false"
    :width="160"
    :height="36"
    :num="6"
    v-model="selectedValue"
    @change="onChange" />
</template>
<script>
export default {
  name: 'App',
  data () {
    return {
      options: [
        {
          label: '北京市',
          value: 1
        },
        {
          label: '上海市上海市上海市上海市',
          value: 2,
          disabled: true
        },
        {
          label: '郑州市',
          value: 3
        },
        {
          label: '纽约市纽约市纽约市纽约市',
          value: 4
        },
        {
          label: '旧金山',
          value: 5
        },
        {
          label: '悉尼市',
          value: 6
        },
        {
          label: '伦敦市',
          value: 7
        },
        {
          label: '巴黎市',
          value: 8
        }
      ],
      selectedValue: 1
    }
  },
  watch: {
    selectedValue (to) {
      console.log('selectedValue:', to)
    }
  },
  mounted () {
    setTimeout(() => { // 模拟接口调用
      this.selectedValue = 3
    }, 1000)
  },
  methods: {
    onChange (value, label, index) {
      console.log('item:', value, label, index)
    }
  }
}
</script>

如果遇到less-loader版本过高问题:

yarn add less-loader安装版本过高,报错如图
在这里插入图片描述
解决:yarn add less-loader@6.0.0

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/24547.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

力扣高频SQL50题(基础版)——第一天

力扣高频SQL50题(基础版)——第一天 1 可回收且低脂的产品 1.1 题目内容 1.1.1 基本题目信息 1.1.2 示例输入输出 1.2 示例sql语句 # WHERE子句中使用多条件 SELECT product_id FROM Products WHERE low_fatsY AND recyclableY1.3 运行截图 2 寻找用户推荐人 2.1 题目内容…

《数据库应用系统实践》------ 小区停车管理系统

系列文章 《数据库应用系统实践》------ 小区停车管理系统 文章目录 系列文章一、需求分析1、系统背景2、 系统功能结构&#xff08;需包含功能结构框图和模块说明&#xff09;3&#xff0e;系统功能简介 二、概念模型设计1&#xff0e;基本要素&#xff08;符号介绍说明&…

第13届蓝桥杯Scratch选拔赛真题集锦

第13届蓝桥杯Scratch选拔赛真题集锦 编程题 第 1 题问答题 跳舞机游戏 题目说明 编程实现 跳舞机游戏。 具体要求: 1).点击绿旗,舞台左上角显示得分0代表玩家分数,在得分右侧倒计时10代表游戏时长(10s) 2).游戏开始倒数计时,在舞台上随机显示上、下、左、右四个箭头中…

SCMA基本原理介绍

SCMA: Sparse Code Multiple Access SCMA基本原理 我们考虑一个同步&#xff08;synchronous&#xff09;的SCMA系统&#xff0c; 含1个基站&#xff08;Base Station, BS&#xff09;&#xff1b; J J J个用户&#xff08;so called layers&#xff09;&#xff1b;K个OFDM…

vue2介绍(入门)

目录 声明式渲染 v-bind v-if条件与循环 name命名 学会log打印 一些js方法 双向绑定v-model和v-bind 那么请实现一个复选框吧 自定义标签模板 声明式渲染 我感觉这里文档的意思是双向绑定&#xff0c; 或许需要清理一下js缓存机制 &#xff0c;嗯...不懂,响应式&…

深入解析Linux C/C++ 编程中的内存泄漏问题

深入解析Linux C/C 编程中的内存泄漏问题 I. 前言 (Introduction)1.1 文章目的与内容概述 (Purpose and Overview of the Content)1.2 重要性和实用性的说明 (Significance and Practicality Explanation)1.3 数据结构与内存泄漏的基本概念 (Basic Concepts of Data Structure …

PDF文件数字证书签名指南

一、安装PDF证书的环境 1.1 PDF证书安装环境 Windows pc 机一台 安装Adobe Acrobat 软件 PDF文档签名证书一张(备注&#xff1a;本指南使用沃通内部文档加密证书进行操作,通用其它版本证书) 1.2 网络环境要求 请确保您签名的电脑可以正常访问外网。 二、PDF证书安装 2.…

数据结构之二叉树的基本实现

在我们之前已经了解的堆这样的完全二叉树的实现&#xff0c;也对树型结构有了一些了解&#xff0c;那么今天我们来看看二叉树的一些性质。 因为二叉树是一种每个节点至多只有两个子树&#xff08;即二叉树的每个节点的度不大于2&#xff09;&#xff0c;并且二叉树的子树有左右…

Shell脚本攻略:shell函数应用

目录 一、理论 1.shell函数 2.函数传参 3.函数变量的作用范围 4.递归 5.函数位置变量与脚本位置变量区别 6.创建库 二、实验 1.实验一 一、理论 1.shell函数 &#xff08;1&#xff09;概念 将命令序列按格式写在一起&#xff0c;可方便重复使用命令序列。 ① 避免…

Docker容器与虚拟机(VM)大对比

Docker是一个开源应用容器引擎。Docker可以将应用程序与基本架构分开&#xff0c;从而快速交付软件。 传统虚拟机的运行需要占用较高的资源&#xff0c;包括磁盘空间、内存和处理器性能。每个虚拟机都需要完整的操作系统和应用程序副本&#xff0c;这在资源利用和启动时间上存…

js实现PDF 预览和文件下载

在开发过程中要求对 PDF 类型的发票提供 预览 和 下载 功能&#xff0c;PDF 类型文件的来源又包括 H5 移动端 和 PC 端&#xff0c;而针对这两个不同端的处理会有些许不同&#xff0c;下文会有所提及。 针对 PDF 预览 的文章不在少数&#xff0c;但似乎都没有提及可能遇到的问…

Markdown可以在线编辑吗?这个办法很好用

Markdown是一种轻量级标记语言&#xff0c;它使用简单的语法来创建文本&#xff0c;非常易于学习。它最初被设计为一种用于写作的格式&#xff0c;但现在已经成为了一种非常受欢迎的文本编辑工具。 作为一个较为方便的在线文本编辑器&#xff0c;它可以用代码代替文字&#xf…

27事务管理AOP

一、MySQL事务回顾 二、Spring事务管理 Spring框架的第一大核心&#xff1a;IOC控制反转 在DeptServiceImpl下删除部门方法下新加一个删除员工信息的操作&#xff0c;注意&#xff1a;此时的id是部门id。 1、问题分析 2、Transactional-Spring事务管理 一般是在Service实现类的…

Visual Studio内引用Lua解释器,编译Lua源码,执行Lua脚本

前言 本篇在讲什么 在Visual Studio中引入lua的解释器 使用C调用Lua文件 本篇适合什么 适合初学Lua的小白 适合需要C/C和lua结合开发的人 本篇需要什么 对Lua语法有简单认知 对C/C语法有简单认知 依赖Lua5.1的环境 依赖VS 2017编辑器 本篇的特色 具有全流程的图文…

springboot中将logback切换为log4j2

前言 springboot默认使用logback作为日志记录框架&#xff0c;常见的日志记录框架有log4j、logback、log4j2。这篇文章我们来学习怎样将logbak替换为log4j2。 一、为什么使用log4j2&#xff1f; 我们在项目中经常使用一个叫SLF4J的依赖&#xff0c;它是做什么的呢&#xff1f; …

Activity的预览窗口StartingWindow添加

Activity的预览窗口StartingWindow添加 1、Activity组件启动2、ActivityStarter.java#startActivityInner() > 主要查看Task.java#startActivityLocked3、ActivityRecord.java#addStartingWindow到WindowManagerService.java#addWindow3.1 ActivityRecord.java#addStartingW…

C/C++开发,libiec61850库学习及运用

目录 一、libiec61850库下载编译 1.1 下载 1.2 linux编译&#xff1a; 1.3 win编译 二、案例编译测试 2.1 CMakeLists.txt调整(server_example_goose) 2.2 模型static_model.h/static_model.cpp生成 2.3 案例编译(server_goose) 2.4 客户端编译 2.5 运行测试 一、libiec61850…

【Python开发】FastAPI 03:请求参数—请求体

除了路径参数和查询参数&#xff0c;还有请求体&#xff0c;其用于传递 JSON、XML 或其他格式的数据&#xff0c;以便服务器能够读取并做出相应的处理&#xff0c;可以说请求体的作用更为强大。试想一下&#xff0c;如果存在七八个参数&#xff0c;路径参数和查询是不是就招架不…

Android播放器拖动进度条的小图预览

Android播放器拖动进度条的小图预览 背景效果图关键代码1. 获取指定位置的视频帧2. 预览图的显示和隐藏 完整代码1. xml布局文件activity_video.xml2. Activity文件VideoActivity.java 背景 我们在使用一些播放器时&#xff0c;拖动进度条会有一个预览框&#xff0c;上一篇博客…

Docker容器 和 Kubernetes容器集群管理系统

一、快速了解Docker 1. 什么是Docker的定义 Docker 是一个开源的应用容器引擎&#xff0c;基于Go语言并遵从 Apache2.0 协议开源。Docker 可以让开发者打包他们的应用以及依赖包到一个轻量级、可移植的容器中&#xff0c;然后发布到任何流行的 Linux 机器上&#xff0c;也可以…