-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathindex.json
2 lines (1 loc) · 58.3 KB
/
index.json
1
2
[{"content":"","date":"17 August 2024","externalUrl":null,"permalink":"/tags/avaudio/","section":"Tags","summary":"","title":"AVAudio","type":"tags"},{"content":" iOS 音频引擎 AVAudioEngine # AVAudioEngine 是 AVFoundation 框架中的核心类,用于构建音频处理图,即一系列音频单元的连接,可以实现复杂的音频处理任务。在 AVAudioEngine 中,你可以使用各种内置的音频单元 (AVAudioUnit) 来添加各种音频效果。以下是 AVAudioEngine 中可用的一些主要音频效果单元及其详细说明:\n1. AVAudioUnitTimePitch # AVAudioUnitTimePitch 是 AVFoundation 框架中的一个音频单元,用于在 AVAudioEngine 的音频处理图中实时改变音频的时间和音调。这个单元允许你独立地调整音频的速度和音高,这对于音乐制作、音频编辑和实时音频效果非常有用。\n主要功能 # 时间拉伸: AVAudioUnitTimePitch 可以改变音频的播放速度,即时间拉伸,而不改变音高。这在需要调整音频长度以匹配特定时间线的情况下很有用。 音调变化: 同时,这个单元也可以改变音频的音调(音高),而不改变播放速度。这在需要调整音频的音高以匹配其他音轨或音阶时非常有用。 独立控制: 最重要的是,AVAudioUnitTimePitch 允许你独立控制时间拉伸和音调变化,这意味着你可以只改变音高而不改变速度,或者反之亦然。 属性 # AVAudioUnitTimePitch 提供了几个关键属性来控制其行为:\npitch: 一个浮点数,表示音高的变化。1.0 表示原始音高,小于1.0表示降低音高,大于1.0表示提高音高。 timePitchAlgorithm: 一个枚举值,表示所使用的时间拉伸和音调变化算法。可以是 .varispeed(仅改变播放速度)、.advanced(高级算法,提供独立的时间和音高控制)等。 pitchCorrection: 一个整数值,表示音高的半音变化。0 表示无变化,正数表示升高音高,负数表示降低音高。 rate: 一个浮点数,表示播放速度的变化。1.0 表示正常速度,小于1.0表示慢速播放,大于1.0表示快速播放。 使用示例 # 下面是一个使用 AVAudioUnitTimePitch 的简单示例:\nimport AVFoundation let audioEngine = AVAudioEngine() let timePitchUnit = AVAudioUnitTimePitch() // 设置音调变化和播放速度 timePitchUnit.pitch = 1.5 // 提升一个半音 timePitchUnit.rate = 1.0 // 正常速度播放 // 将时间音调单元添加到音频引擎 audioEngine.attach(timePitchUnit) // 连接输入和输出节点 let inputNode = audioEngine.inputNode let outputNode = audioEngine.outputNode audioEngine.connect(inputNode, to: timePitchUnit, format: nil) audioEngine.connect(timePitchUnit, to: outputNode, format: nil) // 准备并启动音频引擎 do { try audioEngine.start() } catch { print(\u0026#34;Error starting audio engine: \\(error)\u0026#34;) } 2. AVAudioUnitReverb(混响) # 提供混响效果,可以模拟不同环境下的声音反射,用于营造空间感和深度感。\n在音频处理领域,混响(Reverb)效果用于模拟声波在封闭空间中的反射,从而给声音添加深度和空间感。不同的混响算法和插件可以模拟各种环境,从小房间到大教堂,甚至是特殊的声学效果。在 AVAudioUnitReverb 类中,Apple 提供了几种预设的混响类型,但它们并不是所有可能的混响效果。下面列举的是 AVAudioUnitReverb 类中可用的几种预设混响类型:\nSmallRoom - 模拟一个小房间的声学环境。 MediumRoom - 模拟一个中等大小房间的声学环境。 LargeRoom - 模拟一个大房间的声学环境。 MediumHall - 模拟一个中等大小的音乐厅的声学环境。 LargeHall - 模拟一个大音乐厅的声学环境。 Plate - 模拟早期的金属板混响器(plate reverb)效果。 MediumChamber - 模拟一个中等大小的录音室的声学环境。 LargeChamber - 模拟一个大录音室的声学环境。 Cathedral - 模拟大教堂的声学环境,通常有很长的尾音。 Room - 一个通用的房间混响效果,可以进一步定制。 Hall - 一个通用的大厅混响效果,可以进一步定制。 Chamber - 一个通用的小室混响效果,可以进一步定制。 LiveRoom - 模拟现场表演场地的声学环境。 除了上述预设,AVAudioUnitReverb 还允许你自定义混响的参数,例如:\nWet/Dry Mix - 控制原始干声和混响湿声的混合比例。 Decay Time - 控制混响尾音消失的时间长度。 Diffusion - 控制声波的散射程度,影响混响的密度。 Density - 控制早期反射的数量和分布。 High Frequency Damping - 控制高频混响的衰减程度。 Lowpass Filter - 控制混响信号的高频上限。 除了 AVAudioUnitReverb 提供的预设,还有许多第三方插件和软件提供了更为专业和多样化的混响效果。这些插件通常在专业音频工作站(DAWs)中使用,如 Logic Pro、Pro Tools、Ableton Live 等,提供了更高级的控制和仿真效果,例如:\nConvolution Reverb - 基于真实空间的声学响应(Impulse Response)来模拟混响。 Modulated Reverb - 添加调制效果的混响,如颤音或镶边。 Algorithmic Reverb - 使用数学算法而非真实空间的声学响应来模拟混响。 Spring Reverb - 模拟早期弹簧混响器的效果。 Ambience - 专注于模拟环境声音,如风声、雨声等。 每种混响类型都有其独特的声学特性,选择哪种类型取决于你希望达到的特定声学效果。\n参数:wetDryMix 是混响效果的湿干比参数。它表示原始信号(干信号)和混响信号(湿信号)的混合比例。值范围是 0 到 100,其中 0 表示完全干信号(无混响),100 表示完全湿信号(只有混响)。\n3. AVAudioUnitDistortion(失真效果) # 用于添加失真效果,可以产生摇滚音乐中常见的吉他放大器失真效果。\n4. AVAudioUnitEQ(均衡器) # 均衡器单元,允许你调整音频的频率响应,通过增加或减少特定频率的增益,可以调整音色和清晰度。\nAVAudioUnitEQ 是一个强大的多频段均衡器类,提供了丰富的属性和方法来调整音频信号的频率响应。以下是 AVAudioUnitEQ 及其关键属性的详细说明:\nAVAudioUnitEQ 是 AVAudioUnitEffect 的子类,用于实现多频段均衡器。它包含多个 AVAudioUnitEQFilterParameters 对象,每个对象代表一个频段。\n关键属性 # bands # 类型: [AVAudioUnitEQFilterParameters]\n说明: 这是一个数组,包含均衡器的所有频段。每个频段由 AVAudioUnitEQFilterParameters 对象表示。\n示例:\nlet eq = AVAudioUnitEQ(numberOfBands: 10)\nlet bands = eq.bands\nglobalGain # 类型: Float\n说明: 设置均衡器的全局增益,以分贝 (dB) 为单位。可以用来整体提升或降低音量。\n示例: eq.globalGain = 1.0 // 增加全局增益1dB\nAVAudioUnitEQFilterParameters # AVAudioUnitEQFilterParameters 是 AVAudioUnitEQ 的一个子类,表示均衡器的单个频段。它包含以下关键属性:\nfilterType # 类型: AVAudioUnitEQFilterType\n说明: 设置滤波器的类型。可选值包括 .parametric, .lowPass, .highPass, .resonantLowPass, .resonantHighPass, .bandPass, .bandStop, .lowShelf, .highShelf, .resonantLowShelf, .resonantHighShelf。\n示例: band.filterType = .parametric\npublic enum AVAudioUnitEQFilterType :Int{ case Parametric 参量均衡器 可以通过设置一些参量,来调节咱们均衡器的频点 case LowPass 低通滤波器 衰弱高频 case HighPass 高通滤波器 衰弱低频 case ResonantLowPass 可以引发共鸣的 低通滤波器 case ResonantHighPass 可以引发共鸣的 高通滤波器 case BandPass 带通滤波器 提升某一频率附近的信号 忽略过高 或 过低的 部分 case BandStop 与上面的相反 忽略某一频率附近的信号 case LowShelf 低架 降低整体 case HighShelf 高架 提升整体 case ResonantLowShelf 可以引发共鸣的 低架 case ResonantHighShelf可以引发共鸣的 高架 } frequency # 类型: Float\n说明: 设置滤波器的中心频率,以赫兹 (Hz) 为单位。\n示例: band.frequency = 1000.0 // 设置中心频率为1000Hz\nbandwidth # 类型: Float\n说明: 设置滤波器的带宽,以八度 (octaves) 为单位。仅适用于参数均衡器类型。\n示例: band.bandwidth = 1.0 // 设置带宽为1个八度\ngain # 类型: Float\n说明: 设置滤波器的增益,以分贝 (dB) 为单位。正值表示提升,负值表示衰减。\n示例: band.gain = 5.0 // 增加增益5dB\nbypass # 类型: Bool\n说明: 设置是否绕过此频段。true 表示绕过,false 表示启用。\n示例: band.bypass = false // 启用此频段\n示例代码 # import AVFoundation // 创建音频引擎 let audioEngine = AVAudioEngine() // 创建均衡器,设置为10个频段 let eq = AVAudioUnitEQ(numberOfBands: 10) // 配置每个频段 for i in 0..\u0026lt;eq.bands.count { let band = eq.bands[i] band.filterType = .parametric band.frequency = Float(32 * pow(2.0, Double(i))) // 设置频率 band.bandwidth = 0.5 // 设置带宽 band.gain = 0.0 // 设置增益 band.bypass = false // 启用频段 } // 设置全局增益 eq.globalGain = 1.0 // 将均衡器添加到音频引擎 audioEngine.attach(eq) // 连接均衡器到主混音器节点 audioEngine.connect(eq, to: audioEngine.mainMixerNode, format: nil) // 启动音频引擎 do { try audioEngine.start() } catch { print(\u0026#34;音频引擎启动失败: \\(error)\u0026#34;) } // 调整某个频段的增益 eq.bands[0].gain = 5.0 // 增加第一个频段的增益 5. AVAudioUnitDelay # 延迟效果器,可以创建回声效果,常用于电子音乐制作和空间感增强。\n6. AVAudioUnitCompressor(压缩器) # 压缩器,用于控制音频的动态范围,可以防止峰值过载,同时使较弱的声音更加清晰。\n7. AVAudioUnitFlanger # 镶边器,可以产生一种类似于旋转扬声器的效果,常用于创造特殊的声音质感。\n8. AVAudioUnitPhaser # 相位器,通过对音频信号的不同频率进行相位移,可以产生扫频效果。\n9. AVAudioUnitDistortionFactory(失真效果) # AVAudioUnitDistortionFactory 是 AVAudioEngine 中的一个类,它提供了一系列预设的失真效果单元。这些失真效果可以应用于音频信号,以产生不同的音色变化,尤其是在音乐制作中非常有用,例如在电吉他音轨上添加失真效果。\n以下是在 AVAudioUnitDistortionFactory 中可获得的所有预设失真单元:\nOverdrive - 这种失真类型通常模仿真空管放大器的自然过载特性,产生温暖而柔和的失真效果。 Fuzz - Fuzz 失真通常会产生更加粗糙和饱和的音色,它会将输入信号的波峰削平,导致大量谐波的产生。 Distortion - Distortion 类型的失真通常比 Overdrive 更加激进,它可以产生强烈的非线性失真效果,适合硬摇滚和重金属风格的音乐。 Saturator - Saturator 效果模拟了磁带饱和或数字剪切的特性,可以产生更细腻的失真,通常用于轻微增强音色。 Tube - 这个预设模拟了真空管设备的特性,产生温暖且富有音乐性的失真。 Soft Clip - Soft clip 效果会平滑地限制信号的峰值,避免突然的音量尖峰,同时保留信号的基本音色。 Hard Clip - Hard clip 则会更剧烈地剪切信号峰值,产生更明显的失真和削波效果。 Foldback - Foldback 失真会在信号超过一定阈值时,将信号反向折叠,产生独特的音色变化。 Wave Shaper - Wave shaper 允许对信号波形进行任意形状的变换,可以产生从轻微到极端的各种失真效果。 Bit Crusher - Bit crusher 效果通过降低音频的比特深度来产生数字噪声和失真,通常用于创造电子音乐中的粗糙质感。 Sample and Hold - Sample and Hold 效果会在随机或定期的时间间隔内“采样”信号的瞬时值,并保持该值直到下一次采样,产生断断续续的音色变化。 10. AVAudioUnitChorus # 合唱效果器,通过轻微延迟和调制信号的叠加,可以模仿多个演奏者的合奏效果。\n11. AVAudioUnitAudioUnit # 这个单元允许你加载外部的 Audio Unit 插件,极大地扩展了 AVAudioEngine 的功能,可以使用第三方音频效果和乐器。\n12. AVAudioUnitSampler # 采样器单元,用于加载和播放采样音频,可以用来构建自己的乐器。\n13. AVAudioUnitInstrument # 乐器单元,可以加载和播放 MIDI 信息,用于合成音乐。\n14. AVAudioUnitVarispeed(播放速度) # 变速单元,可以改变音频的速度和播放时间,但不会改变音调。\n15. AVAudioUnitRecorder # 录音单元,用于录制音频流到文件,可以实现实时录音功能。\n16. AVAudioUnitTimeStretch # 时间拉伸单元,可以改变音频的播放时间而不改变音调,适用于节奏调整。\n17. AVAudioUnitMIDI # MIDI 单元,用于处理 MIDI 信息,可以将 MIDI 控制信息转换为音频输出。\n18. AVAudioUnitSampler # 虽然已经提过一次,但是值得注意的是,AVAudioUnitSampler 可以作为复杂的乐器引擎使用,它支持多种触发模式和多种音色切换。\n19. AVAudioUnitGenerator # 音频生成单元,可以生成特定的音频波形,如正弦波、方波等。\n20. AVAudioUnitMixer # 混音器单元,用于混合多个音频流,可以调整各路音频的音量和平衡。\n21. AVAudioUnitEffect # 一个通用效果单元,可以作为其他效果单元的基类,但通常不会直接实例化。\n22. AVAudioUnitEQFilter # 虽然 AVAudioUnitEQ 提供了均衡器功能,但 AVAudioUnitEQFilter 提供了更细粒度的滤波器控制,可以单独设置每个频段的参数。\n使用示例 # 使用这些单元时,你需要将它们添加到 AVAudioEngine 中,并通过 connect 方法将它们连接起来形成一个处理链。例如,下面的代码展示了如何将均衡器和混响效果添加到音频引擎中:\nlet audioEngine = AVAudioEngine() let eq = AVAudioUnitEQ(numberOfBands: 3) let reverb = AVAudioUnitReverb() // 添加单元 audioEngine.attach(eq) audioEngine.attach(reverb) // 连接单元 let inputNode = audioEngine.inputNode let outputNode = audioEngine.outputNode audioEngine.connect(inputNode, to: eq, format: nil) audioEngine.connect(eq, to: reverb, format: nil) audioEngine.connect(reverb, to: outputNode, format: nil) 注意事项 # 在音频处理链中,效果的顺序会影响最终的音频输出。以下是一些常见的音频效果及其通常的排列顺序:\n动态处理(Dynamic Processing): 包括压缩器(Compressor)、限制器(Limiter)等。这些效果通常放在最前面,以控制音频信号的动态范围。\n均衡器(Equalizer): 用于调整音频信号的频率响应。通常在动态处理之后,以便在处理动态范围后进行频率调整。\n失真(Distortion): 包括过载(Overdrive)、失真(Distortion)等。这些效果通常放在均衡器之后,以便在频率调整后添加失真效果。\n调制(Modulation): 包括合唱(Chorus)、镶边(Flanger)、相位(Phaser)等。这些效果通常放在失真之后,以便在失真处理后添加调制效果。\n延迟(Delay): 用于添加回声效果。通常放在调制效果之后,以便在调制处理后添加延迟效果。\n混响(Reverb): 用于模拟空间效果。通常放在延迟之后,以便在延迟处理后添加混响效果。\n获取频谱信息 # 目标需求 # 如何获取音频数据的频谱信息,根据音乐的律动,实现频谱可视化柱状图振幅效果?\n思路方案 # 要实现音频频谱可视化柱状图振幅效果,你需要从音频数据中提取频谱信息。可以使用 AVAudioEngine 和 AVAudioPCMBuffer 来获取音频数据,并使用快速傅里叶变换(FFT)来计算频谱。\n以下是一个简化的示例,展示如何获取音频数据的频谱信息并实现频谱可视化柱状图振幅效果:\n获取音频数据并计算频谱 # 使用 AVAudioEngine 和 AVAudioPCMBuffer 获取音频数据。\n使用 vDSP 库中的 FFT 函数计算频谱。\nimport AVFoundation import Accelerate class SpectrumAnalyzer { private var fftSetup: FFTSetup? private var log2n: vDSP_Length var bufferSize: Int // 将访问级别更改为 internal private var window: [Float] private var outputBuffer: [Float] private var frequencyData: [Float] private var downsampleFactor: Int init(bufferSize: Int, downsampleFactor: Int = 10) { // 默认降采样因子为10 self.bufferSize = bufferSize self.downsampleFactor = downsampleFactor self.log2n = vDSP_Length(log2(Float(bufferSize))) self.fftSetup = vDSP_create_fftsetup(log2n, Int32(kFFTRadix2)) self.window = [Float](repeating: 0, count: bufferSize) vDSP_hann_window(\u0026amp;window, vDSP_Length(bufferSize), Int32(vDSP_HANN_NORM)) self.outputBuffer = [Float](repeating: 0, count: bufferSize / 2) self.frequencyData = [Float](repeating: 0, count: bufferSize / 2) } deinit { if let fftSetup = fftSetup { vDSP_destroy_fftsetup(fftSetup) } } func analyze(buffer: AVAudioPCMBuffer) -\u0026gt; [Float] { guard let fftSetup = fftSetup else { return [] } let frameCount = buffer.frameLength var realp = [Float](repeating: 0, count: Int(frameCount / 2)) var imagp = [Float](repeating: 0, count: Int(frameCount / 2)) var magnitudes = [Float](repeating: 0.0, count: Int(frameCount / 2)) realp.withUnsafeMutableBufferPointer { realpPtr in imagp.withUnsafeMutableBufferPointer { imagpPtr in var output = DSPSplitComplex(realp: realpPtr.baseAddress!, imagp: imagpPtr.baseAddress!) buffer.floatChannelData?.pointee.withMemoryRebound(to: DSPComplex.self, capacity: Int(frameCount)) { (inputData) in vDSP_ctoz(inputData, 2, \u0026amp;output, 1, vDSP_Length(frameCount / 2)) } vDSP_fft_zrip(fftSetup, \u0026amp;output, 1, log2n, FFTDirection(FFT_FORWARD)) vDSP_zvmags(\u0026amp;output, 1, \u0026amp;magnitudes, 1, vDSP_Length(frameCount / 2)) } } return downsample(magnitudes, factor: downsampleFactor) } private func downsample(_ data: [Float], factor: Int) -\u0026gt; [Float] { guard factor \u0026gt; 0 else { return data } let downsampledCount = data.count / factor var downsampledData = [Float](repeating: 0.0, count: downsampledCount) for i in 0..\u0026lt;downsampledCount { let start = i * factor let end = start + factor let sum = data[start..\u0026lt;end].reduce(0, +) downsampledData[i] = sum / Float(factor) } return downsampledData } } 绑定AVAudioEngine # 将频谱数据传递给 UI 层,更新柱状图的振幅。\n以下是一个示例代码,展示如何实现这些步骤:\nimport AVFoundation import MediaPlayer class AudioEnginePlayer { //... var onSpectrumDataAvailable: (([Float]) -\u0026gt; Void)? //... private var playerNode: AVAudioPlayerNode private var spectrumAnalyzer: SpectrumAnalyzer //... /// 播放状态 var isPlaying: Bool = false { didSet { if !isPlaying { // 如果没有播放,则所有频谱柱显示为 0 值 onSpectrumDataAvailable?([Float](repeating: 0.0, count: 24)) } } } init() { //... playerNode = AVAudioPlayerNode() //... spectrumAnalyzer = SpectrumAnalyzer(bufferSize: 1024, downsampleFactor: 10) //... setupAudioEngineTap() } //... private func setupAudioEngineTap() { audioEngine.mainMixerNode.installTap(onBus: 0, bufferSize: AVAudioFrameCount(spectrumAnalyzer.bufferSize), format: audioEngine.mainMixerNode.outputFormat(forBus: 0)) { [weak self] (buffer, time) in guard let self = self else { return } let magnitudes = self.spectrumAnalyzer.analyze(buffer: buffer) DispatchQueue.main.async { if self.isPlaying { //print(\u0026#34;\\(magnitudes)\\n\\n\\n\u0026#34;) self.onSpectrumDataAvailable?(magnitudes) } } } } //... } 创建频谱显示视图 # 创建一个 VisualizerView 类,用于绘制频谱柱状图。\n在 updateUI 方法中调用 VisualizerView 的更新方法。\nimport UIKit class VisualizerView: UIView { private var magnitudes: [Float] = [] override init(frame: CGRect) { super.init(frame: frame) self.backgroundColor = .black // 设置背景颜色 } required init?(coder: NSCoder) { super.init(coder: coder) self.backgroundColor = .black // 设置背景颜色 } func update(with magnitudes: [Float]) { self.magnitudes = magnitudes setNeedsDisplay() } override func draw(_ rect: CGRect) { guard !magnitudes.isEmpty else { return } let context = UIGraphicsGetCurrentContext() context?.clear(rect) let barWidth = rect.width / CGFloat(magnitudes.count) for (index, magnitude) in magnitudes.enumerated() { let barHeight = CGFloat(magnitude) * rect.height let barRect = CGRect(x: CGFloat(index) * barWidth, y: rect.height - barHeight, width: barWidth, height: barHeight) context?.setFillColor(UIColor.green.cgColor) // 设置填充颜色 context?.fill(barRect) } // 添加调试日志 //print(\u0026#34;Drawing \\(magnitudes.count) bars\u0026#34;) } } 将频谱数据添加到界面 # 在视图控制器中添加 VisualizerView 并将频谱数据传递给它\nimport UIKit class ViewController: UIViewController { private var visualizerView: VisualizerView! lazy var audioEnginePlayer = AudioEnginePlayer() override func viewDidLoad() { super.viewDidLoad() visualizerView = VisualizerView(frame: CGRectMake(0, 0, view.bounds.width, 300)) view.addSubview(visualizerView) view.sendSubviewToBack(visualizerView) audioEnginePlayer.onSpectrumDataAvailable = { [weak self] magnitudes in //print(magnitudes) self?.visualizerView.update(with: magnitudes) } } } ","date":"17 August 2024","externalUrl":null,"permalink":"/posts/ios/audioengine/","section":"Posts","summary":"AVAudioEngine 是 AVFoundation 框架中的核心类,用于构建音频处理图,即一系列音频单元的连接,可以实现复杂的音频处理任务。","title":"AVAudioEngine详解","type":"posts"},{"content":"","date":"17 August 2024","externalUrl":null,"permalink":"/categories/","section":"Categories","summary":"","title":"Categories","type":"categories"},{"content":"","date":"17 August 2024","externalUrl":null,"permalink":"/categories/ios/","section":"Categories","summary":"","title":"IOS","type":"categories"},{"content":"Welcome to my knowledge base.\n","date":"17 August 2024","externalUrl":null,"permalink":"/posts/","section":"Posts","summary":"Welcome to my knowledge base.","title":"Posts","type":"posts"},{"content":"","date":"17 August 2024","externalUrl":null,"permalink":"/","section":"PPSW.ASIA","summary":"","title":"PPSW.ASIA","type":"page"},{"content":"","date":"17 August 2024","externalUrl":null,"permalink":"/tags/","section":"Tags","summary":"","title":"Tags","type":"tags"},{"content":"","date":"21 July 2024","externalUrl":null,"permalink":"/tags/cocoapods/","section":"Tags","summary":"","title":"Cocoapods","type":"tags"},{"content":" 一、Hosts配置 # 1.1 从Finder中配置显示Macintosh HD和用户目录 # 英文:打开Finder,点击顶部菜单Finder-\u0026gt;Settings\n中文:打开访达,点击顶部菜单访达-\u0026gt;设置-\u0026gt;边栏-\u0026gt;勾选硬盘-\u0026gt;勾选用户目录(房子图标)\n1.2 修改配置 /private/etc/Hosts # 进入Macintosh HD后,默认是看不到/private/etc/Hosts, 因为这些事系统的隐藏系统文件,按Command + Shift + . 组合命令,显示或隐藏文件。 找到/private/etc/Hosts,将Hosts文件复制到桌面再进行修改。\n## ##Host Database # ##localhost is used to configure the loopback interface ##when the system is booting. Do not change this entry. ## 127.0.0.1 localhost 255.255.255.255 broadcasthost ::1 localhost ##GitHub Start 140.82.114.4 github.com 140.82.114.20 gist.github.com 151.101.184.133 assets-cdn.github.com 151.101.184.133 raw.githubusercontent.com 151.101.184.133 gist.githubusercontent.com 151.101.184.133 cloud.githubusercontent.com 151.101.184.133 camo.githubusercontent.com 151.101.184.133 avatars0.githubusercontent.com 199.232.68.133 avatars0.githubusercontent.com 199.232.28.133 avatars1.githubusercontent.com 151.101.184.133 avatars1.githubusercontent.com 151.101.184.133 avatars2.githubusercontent.com 199.232.28.133 avatars2.githubusercontent.com 151.101.184.133 avatars3.githubusercontent.com 199.232.68.133 avatars3.githubusercontent.com 151.101.184.133 avatars4.githubusercontent.com 199.232.68.133 avatars4.githubusercontent.com 151.101.184.133 avatars5.githubusercontent.com 199.232.68.133 avatars5.githubusercontent.com 151.101.184.133 avatars6.githubusercontent.com 199.232.68.133 avatars6.githubusercontent.com 151.101.184.133 avatars7.githubusercontent.com 199.232.68.133 avatars7.githubusercontent.com 151.101.184.133 avatars8.githubusercontent.com 199.232.68.133 avatars8.githubusercontent.com ##GitHub End 主要是将##GitHub Start 到 ##GitHub End的内容添加进去,保存以后,在将Host文件复制替换到/private/etc/Hosts。\n二、Git安装 # 官方网站:https://www.git-scm.com/download/\n如果是iOS开发者,可以先装一个xcode,自带git环境安装。\n默认系统是没有git的,我们也可以手动先安装一个。\n我是macOS系统,https://www.git-scm.com/download/mac\n这里有很多种方式,我们选择Binary installer二进制安装文件,点击installer,进入https://sourceforge.net/projects/git-osx-installer/files/,选择最新的版本2.33.0。\n下载安装即可。\n三、Homebrew安装 # Homebrew官网: https://brew.sh/\n打开终端命令输入:\n/bin/bash -c \u0026#34;$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install.sh)\u0026#34; 或使用国内镜像更快\n/bin/zsh -c \u0026#34;$(curl -fsSL https://gitee.com/cunkai/HomebrewCN/raw/master/Homebrew.sh)\u0026#34; 如果失败多试几次,可能是你的网络问题,安装完成以后命令行输入:brew -v ,查看homebrew版本看看是否安装成功。\n四、Ruby安装 # Ruby官网: https://www.ruby-lang.org/zh_cn/downloads/\nRVM方式安装 # RVM(Ruby Version Manager)是一个命令行工具,用于管理多个 Ruby 版本和 Gem 集。它允许你在同一台机器上安装、管理和切换不同的 Ruby 版本,并为每个项目创建独立的 Gem 环境。\n安装命令 curl -L https://get.rvm.io | bash -s stable 载入RVM环境 source ~/.rvm/scripts/rvm 查看rvm版本 rvm -v 能输出版本信息说明安装完成。\n列出已知版本 rvm list known 安装指定ruby版本 rvm install 3.0.0 查看ruby版本信息 xiaopin@PPM2-MacBook-Air ~ % ruby -v ruby 3.0.0p0 (2020-12-25 revision 95aff21468) [arm64-darwin23]\n说明安装成功!\nbrew方式安装(推荐) # RVM方式好像停止更新一样,无法保持Ruby版本最新兼容,这次macOS 15.0系统,RVM方式的版本不兼容新系统。\n使用Brew安装最新的Ruby版本 brew install ruby 修改Shell配置文件, #Intel芯片(目前来说可以抛弃了,现在基本都是苹果芯片) echo \u0026#39;export PATH=\u0026#34;/usr/local/opt/ruby/bin:$PATH\u0026#34;\u0026#39; \u0026gt;\u0026gt; ~/.bash_profile source ~/.bash_profile #苹果M系列芯片 echo \u0026#39;export PATH=\u0026#34;/opt/homebrew/opt/ruby/bin:$PATH\u0026#34;\u0026#39; \u0026gt;\u0026gt; ~/.zshrc source ~/.zshrc 也可以手动的的找到.zshrc文件,一般在 Users/用户名/.zshrc 目录下,用文本编辑器打开,在最后面加上\n#如果是RVM安装的会自动有这行,可以不管,也可以注释 export PATH=\u0026#34;$PATH:$HOME/.rvm/bin\u0026#34; #在后面加上这行,会自动的将默认环境指向homebrew的ruby版本 export PATH=\u0026#34;/opt/homebrew/opt/ruby/bin:$PATH\u0026#34; 验证安装 #查看默认ruby路径 which ruby #查看ruby版本 ruby -v #ruby 3.3.5 (2024-09-03 revision ef084cc8f4) [arm64-darwin24] 五、升级gem和更换镜像源 # Gems 是 Ruby 的包管理系统(RubyGems)用来分发和管理 Ruby 库和应用程序的包。Gems 可以包含库、应用程序、文档和其他资源,方便开发者在项目中使用和管理依赖。\n升级gem命令 sudo gem update --system 更换镜像源 移除旧源\ngem sources --remove https://rubygems.org/ 添加新源\ngem sources -a https://gems.ruby-china.com 查看镜像源信息\ngem sources -l 六、彻底卸载cocoapods # 卸载已有旧版本 sudo gem uninstall cocoapods 查看本地已安装的cocoapods依赖 gem list --local | grep cocoapods 显示如下:\ncocoapods (1.0.1)\ncocoapods-core (1.0.1)\ncocoapods-deintegrate (1.0.1)\ncocoapods-downloader (1.1.1)\ncocoapods-plugins (1.0.0)\ncocoapods-search (1.0.0)\ncocoapods-stats (1.0.0)\ncocoapods-trunk (1.0.0)\ncocoapods-try (1.1.0)\n逐个删除 sudo gem uninstall cocoapods-core sudo gem uninstall cocoapods-deintegrate sudo gem uninstall cocoapods-downloader sudo gem uninstall cocoapods-plugins sudo gem uninstall cocoapods-search ... 七、Cocoapods安装 # macOS 10.11以后系统的安装cocoapods 指令,可安装制定版本:\nsudo gem install -n /usr/local/bin cocoapods 或 sudo gem install -n /usr/local/bin cocoapods -v 1.9.2 安装完成后,查看一下版本\npod --version 八、pod search异常解决 # 尝试删除 rm ~/Library/Caches/CocoaPods/search_index.json 不行的话再逐步执行一下命令 cd ~/.cocoapods/repos pod repo remove master git clone https://github.com/CocoaPods/Specs.git master rm ~/Library/Caches/CocoaPods/search_index.json pod search afnetworking 九、Cocoapods国内镜像源\u0026amp;Github镜像源 # 查看本地源\npod repo master Type: git (remotes/origin/master) URL: https://github.com/CocoaPods/Specs.git Path: /Users/xiaopin/.cocoapods/repos/master 修改默认镜像\n国内网络限制,github源下载麻烦,可以切换默认master源 清华源:https://mirrors.tuna.tsinghua.edu.cn/git/CocoaPods/Specs.git gitee源:https://gitee.com/mirrors/CocoaPods-Specs.git\n官方cdn: https://cdn.cocoapods.org/\n以Gitee为例:\npod repo remove master pod repo add master https://gitee.com/mirrors/CocoaPods-Specs.git pod repo update 修改Podfile\nsource \u0026#39;https://gitee.com/mirrors/CocoaPods-Specs.git\u0026#39; 也可以用官方CDN源,Podfile文件默认不设置source(推荐)\nsource \u0026#39;https://cdn.cocoapods.org/\u0026#39; ","date":"21 July 2024","externalUrl":null,"permalink":"/posts/ios/cocoapods/","section":"Posts","summary":"如果你使用Cocoapods环境出现各种问题,可以参考这篇文章就能彻底解决。","title":"万能解决方案之彻底解决cocoapods环境问题","type":"posts"},{"content":"","date":"20 July 2024","externalUrl":null,"permalink":"/tags/macos/","section":"Tags","summary":"","title":"MacOS","type":"tags"},{"content":"","date":"20 July 2024","externalUrl":null,"permalink":"/categories/macos/","section":"Categories","summary":"","title":"MacOS","type":"categories"},{"content":" 默认安装位置\u0026amp;自定义位置 # 默认安装位置:/usr/local/\nBrew默认安装位置:/opt/homebrew/\n自定义安装位置:/Users/xiaopin/dev/\n有些工具和包通过安装文件的方式安装的,可以自定义目录,但是需要自己配置环境变量,如果是用HomeBrew的,系统自定选择安装的默认位置。因为是考虑到有时候brew安装巨慢的时候,可以考虑手动官网下载安装程序进行安装。\nHosts配置 # 1.1 从Finder中配置显示Macintosh HD和用户目录 # 英文:打开Finder,点击顶部菜单Finder-\u0026gt;Settings\n中文:打开访达,点击顶部菜单访达-\u0026gt;设置-\u0026gt;边栏-\u0026gt;勾选硬盘-\u0026gt;勾选用户目录(房子图标)\n1.2 修改配置 /private/etc/Hosts # 进入Macintosh HD后,默认是看不到/private/etc/Hosts, 因为这些事系统的隐藏系统文件,按Command + Shift + . 组合命令,显示或隐藏文件。 找到/private/etc/Hosts,将Hosts文件复制到桌面再进行修改。\n## # Host Database # # localhost is used to configure the loopback interface # when the system is booting. Do not change this entry. ## 127.0.0.1 localhost 255.255.255.255 broadcasthost ::1 localhost # GitHub Start 140.82.114.4 github.com 140.82.114.20 gist.github.com 151.101.184.133 assets-cdn.github.com 151.101.184.133 raw.githubusercontent.com 151.101.184.133 gist.githubusercontent.com 151.101.184.133 cloud.githubusercontent.com 151.101.184.133 camo.githubusercontent.com 151.101.184.133 avatars0.githubusercontent.com 199.232.68.133 avatars0.githubusercontent.com 199.232.28.133 avatars1.githubusercontent.com 151.101.184.133 avatars1.githubusercontent.com 151.101.184.133 avatars2.githubusercontent.com 199.232.28.133 avatars2.githubusercontent.com 151.101.184.133 avatars3.githubusercontent.com 199.232.68.133 avatars3.githubusercontent.com 151.101.184.133 avatars4.githubusercontent.com 199.232.68.133 avatars4.githubusercontent.com 151.101.184.133 avatars5.githubusercontent.com 199.232.68.133 avatars5.githubusercontent.com 151.101.184.133 avatars6.githubusercontent.com 199.232.68.133 avatars6.githubusercontent.com 151.101.184.133 avatars7.githubusercontent.com 199.232.68.133 avatars7.githubusercontent.com 151.101.184.133 avatars8.githubusercontent.com 199.232.68.133 avatars8.githubusercontent.com # GitHub End 主要是将# GitHub Start 到 # GitHub End的内容添加进去,保存以后,在将Host文件复制替换到/private/etc/Hosts。\nXcode安装 # 1.更新macOS最新系统\n桌面左上角苹果图标-\u0026gt;系统设置-\u0026gt;通用-\u0026gt;软件更新\n2.直接通过AppStore安装Xcode,会将git一起安装\nGit安装\u0026amp;配置 # Git官网: https://git-scm.com\n下载地址: https://git-scm.com/download/mac\n如果安装了Xcode这个就不需要手动再次安装了,如果没有安装Xcode,就手动安装Binary installer\n取消代理设置:\ngit config --global unset http.proxy git config --global unset https.proxy HomeBrew安装\u0026amp;配置 # Homebrew官网\n打开终端命令输入:\n/bin/bash -c \u0026#34;$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install.sh)\u0026#34; 或使用国内镜像更快\n/bin/zsh -c \u0026#34;$(curl -fsSL https://gitee.com/cunkai/HomebrewCN/raw/master/Homebrew.sh)\u0026#34; 如果失败多试几次,可能是你的网络问题,安装完成以后命令行输入:brew -v ,查看homebrew版本看看是否安装成功。\nRuby安装\u0026amp;配置 # 一般情况下,macOS默认会安装ruby,版本可能不是最新的\n官方网站:https://www.ruby-lang.org/zh_cn/downloads/\n使用Brew安装最新的Ruby版本 brew install ruby 修改Shell配置文件, #Intel芯片(目前来说可以抛弃了,现在基本都是苹果芯片) echo \u0026#39;export PATH=\u0026#34;/usr/local/opt/ruby/bin:$PATH\u0026#34;\u0026#39; \u0026gt;\u0026gt; ~/.bash_profile source ~/.bash_profile #苹果M系列芯片 echo \u0026#39;export PATH=\u0026#34;/opt/homebrew/opt/ruby/bin:$PATH\u0026#34;\u0026#39; \u0026gt;\u0026gt; ~/.zshrc source ~/.zshrc 也可以手动的的找到.zshrc文件,一般在 Users/用户名/.zshrc 目录下,用文本编辑器打开,在最后面加上\n#如果是RVM安装的会自动有这行,可以不管,也可以注释 export PATH=\u0026#34;$PATH:$HOME/.rvm/bin\u0026#34; #在后面加上这行,会自动的将默认环境指向homebrew的ruby版本 export PATH=\u0026#34;/opt/homebrew/opt/ruby/bin:$PATH\u0026#34; 验证安装 #查看默认ruby路径 which ruby #查看ruby版本 ruby -v 也可以通过 rbenv 和 rvm 方式安装,之前一直用的rvm,但是rvm更新较慢,无法保证是最新的ruby版本。只要那种方式能安装最新的,就用哪种。\nCocoapods安装\u0026amp;配置 # 升级gem和更换镜像源 Gems 是 Ruby 的包管理系统(RubyGems)用来分发和管理 Ruby 库和应用程序的包。Gems 可以包含库、应用程序、文档和其他资源,方便开发者在项目中使用和管理依赖。\n升级gem命令 sudo gem update --system 更换镜像源 移除旧源\ngem sources --remove https://rubygems.org/ 添加新源\ngem sources -a https://gems.ruby-china.com 查看镜像源信息\ngem sources -l 彻底卸载cocoapods 卸载已有旧版本 sudo gem uninstall cocoapods 查看本地已安装的cocoapods依赖 gem list --local | grep cocoapods 显示如下:\ncocoapods (1.0.1)\ncocoapods-core (1.0.1)\ncocoapods-deintegrate (1.0.1)\ncocoapods-downloader (1.1.1)\ncocoapods-plugins (1.0.0)\ncocoapods-search (1.0.0)\ncocoapods-stats (1.0.0)\ncocoapods-trunk (1.0.0)\ncocoapods-try (1.1.0)\n逐个删除 sudo gem uninstall cocoapods-core sudo gem uninstall cocoapods-deintegrate sudo gem uninstall cocoapods-downloader sudo gem uninstall cocoapods-plugins sudo gem uninstall cocoapods-search ... Cocoapods安装 macOS 10.11以后系统的安装cocoapods 指令,可安装制定版本:\nsudo gem install -n /usr/local/bin cocoapods 或 sudo gem install -n /usr/local/bin cocoapods -v 1.9.2 安装完成后,查看一下版本\npod --version Flutter安装\u0026amp;配置 # 前提: 安装配置了上面的环境后\n下载SDK: https://docs.flutter.cn/release/archive\n解压到自定义目录下:/Users/xiaopin/dev/目录下后为:/Users/xiaopin/dev/flutter\n将配置添加到~/.zshrc\nexport PATH=/Users/xiaopin/dev/flutter/bin:$PATH export PUB_HOSTED_URL=https://pub.flutter-io.cn export FLUTTER_STORAGE_BASE_URL=https://storage.flutter-io.cn 运行命令查看\nflutter doctor Go安装\u0026amp;配置 # 安装配置 # 官网下载\nhttps://go.dev/dl/,官方都是通过安装包方式安装的。对于开发环境来说可以。如果是服务器环境的话采用docker方式,命令行方式。\n安装程序安装\n到官网地址下载最新的安装程序包以后,根据步骤安装,默认自动安装到 /usr/local/go 路径下,同时会自动的将 /usr/local/go/bin 添加到环境变量中。在命令行中查看版本验证是否正常安装:\ngo version #go version go1.22.5 darwin/arm64 命令安装\ndocker安装\n常用命令 # 其他插件的安装配置 # dlv\ngoctl\ngopls\nprotoc\nProtoc-gen-go\nreverse\nxorm\n\u0026hellip;.\nmysql安装\u0026amp;配置 # Nodejs安装\u0026amp;配置 # 安装配置 # 官方网站下载安装教程\nhttps://nodejs.org/zh-cn/download/package-manager\n命令安装\n# NOTE: # Homebrew is not a Node.js package manager. Please ensure it is already installed # on your system. Follow official instructions at https://brew.sh/ # Homebrew only supports installing major Node.js versions and might not support # the latest Node.js version from the 20 release line. # download and install Node.js brew install node@20 # verifies the right Node.js version is in the environment node -v # should print `v20.15.1` # verifies the right NPM version is in the environment npm -v # should print `10.7.0` 安装程序安装\n默认安装目录\n• Node.js v20.15.1 to /usr/local/bin/node • npm v10.7.0 to /usr/local/bin/npm\n方式方法有很多种,因为我用的是macOS环境,只列举macOS的安装配置教程。我采用了安装程序的方式。\n常用命令\nNode.js 命令 # node 启动 Node.js 解释器,可以直接执行 JavaScript 文件或进入 REPL(交互式解释器)模式。 示例:node app.js node --version 或 node -v 显示当前 Node.js 的版本信息。 node inspect \u0026lt;script\u0026gt; 使用调试器启动脚本。 node --inspect=\u0026lt;port\u0026gt; \u0026lt;script\u0026gt; 启动脚本并监听指定端口,用于远程调试。 npm 命令 # npm init 初始化一个 npm 项目,创建或更新 package.json 文件。 npm install 或 npm i 安装项目所需的依赖包,根据 package.json 和 package-lock.json 文件。 npm install \u0026lt;package\u0026gt; 或 npm i \u0026lt;package\u0026gt; 安装指定的包到项目中。 npm install \u0026lt;package\u0026gt; --save 或 npm i \u0026lt;package\u0026gt; -S 安装包并将它添加到 dependencies 列表中。 npm install \u0026lt;package\u0026gt; --save-dev 或 npm i \u0026lt;package\u0026gt; -D 安装包并将它添加到 devDependencies 列表中。 npm uninstall \u0026lt;package\u0026gt; 或 npm un \u0026lt;package\u0026gt; 卸载指定的包。 npm uninstall \u0026lt;package\u0026gt; --save 或 npm un \u0026lt;package\u0026gt; -S 卸载包并从 dependencies 中移除。 npm uninstall \u0026lt;package\u0026gt; --save-dev 或 npm un \u0026lt;package\u0026gt; -D 卸载包并从 devDependencies 中移除。 npm update 更新所有已安装的包到最新版本。 npm update \u0026lt;package\u0026gt; 更新指定的包到最新版本。 npm outdated 显示哪些已安装的包有更新的版本。 npm list 或 npm ls 列出所有已安装的包及其版本。 npm publish 发布当前项目到 npm 仓库。 npm run \u0026lt;script\u0026gt; 执行 package.json 文件中定义的脚本。 npm start 运行 package.json 文件中定义的 start 脚本。 npm test 运行 package.json 文件中定义的 test 脚本。 npm config get prefix 显示全局包的安装前缀。 npm config set prefix \u0026lt;path\u0026gt; 设置全局包的安装前缀。 npm cache clean 清理 npm 缓存。 npm help 显示帮助信息。 以上命令覆盖了 Node.js 和 npm 的大部分日常使用场景,从项目初始化到包管理,再到运行和调试应用程序。\npnpm安装和使用 # pnpm 是一个高性能的包管理器,用于 Node.js 项目,它提供了比 npm 和 yarn 更快的速度和更少的磁盘空间占用。要在你的系统上安装 pnpm,你可以遵循以下步骤:\n对于 Linux 和 macOS 用户 # 确保 Node.js 已经安装 在开始之前,你需要确保你的机器上已经安装了 Node.js 和 npm,因为 pnpm 是通过 npm 安装的。\n全局安装 pnpm 在你的终端中运行以下命令来全局安装 pnpm:\nsudo npm install -g pnpm 验证 pnpm 安装 安装完成后,你可以通过运行以下命令来确认 pnpm 是否成功安装:\npnpm --version 如果安装成功,该命令将显示你安装的 pnpm 的版本号。\nPython安装\u0026amp;配置 # ","date":"20 July 2024","externalUrl":null,"permalink":"/posts/ios/macos_dev_env/","section":"Posts","summary":"macOS开发环境的安装和配置","title":"macOS开发环境的安装和配置","type":"posts"},{"content":"个人信息展示\n","date":"1 July 2024","externalUrl":null,"permalink":"/about/","section":"PPSW.ASIA","summary":"个人信息展示","title":"About","type":"page"},{"content":"HelloApp base on Flutter. Support Android, iOS, Web, macOS, Windows\n","date":"17 June 2024","externalUrl":null,"permalink":"/portfolio/hello_app/","section":"Portfolio","summary":"HelloApp base on Flutter. Support Android, iOS, Web, macOS, Windows","title":"HelloApp","type":"portfolio"},{"content":"参与作品和独立开发作品广泛,涉及:资讯,社交,电商,即时通讯,音视频,企业级领域。\n","date":"17 June 2024","externalUrl":null,"permalink":"/portfolio/","section":"Portfolio","summary":"参与作品和独立开发作品广泛,涉及:资讯,社交,电商,即时通讯,音视频,企业级领域。","title":"Portfolio","type":"portfolio"},{"content":"","date":"17 June 2024","externalUrl":null,"permalink":"/tags/git/","section":"Tags","summary":"","title":"Git","type":"tags"},{"content":" 安装Git # \u0026hellip;\n命令模式 # 初始化和推送 # # 1. 初始化 Git 仓库 git init # 2. 添加所有文件到暂存区 git add . # 3. 提交更改 git commit -m \u0026#34;Initial commit\u0026#34; # 4. 添加远程仓库(将 \u0026lt;your-repo-url\u0026gt; 替换为你的 GitHub 仓库 URL) git remote add origin https://github.com/xiaopindev/pp_kits.git # 5. 推送到远程仓库 git push -u origin master # 查看当前分支名称 git branch # 如果当前分支是 main,推送到 main git push -u origin main # 如果需要重命名分支为 master git branch -M master git push -u origin master #如果已经存在远程仓库, 删除现有的 origin 远程仓库 git remote remove origin # 重新添加新的远程仓库 git remote add origin https://github.com/xiaopindev/pp_kits.git # 推送到远程仓库 git push -u origin main 分支操作 # 创建分支 # # 创建本地分支 git branch feature-branch # 创建并切换到新的本地分支 git checkout -b feature-branch # 从远程分支创建并切换到新的本地分支 # 假设远程分支名为 origin/feature-branch git checkout -b feature-branch origin/feature-branch 查看分支 # # 查看本地和远程分支 git branch -a # 只查看远程分支 git branch -r 修改分支 # 删除分支 # # 删除本地分支 git branch -d \u0026lt;branch_name\u0026gt; # 强制删除本地分支(如果分支没有被合并) git branch -D \u0026lt;branch_name\u0026gt; # 删除远程分支 git push origin --delete \u0026lt;branch_name\u0026gt; 汇总(待整理) # # 初始化一个新的Git仓库 git init # 克隆一个远程仓库 git clone \u0026lt;repository_url\u0026gt; # 查看当前仓库的状态 git status # 添加文件到暂存区 git add \u0026lt;file_name\u0026gt; git add . # 添加所有文件 # 提交暂存区的文件到本地仓库 git commit -m \u0026#34;提交信息\u0026#34; # 查看提交历史 git log # 查看简洁的提交历史 git log --oneline # 创建一个新的分支 git branch \u0026lt;branch_name\u0026gt; # 切换到指定分支 git checkout \u0026lt;branch_name\u0026gt; # 创建并切换到新的分支 git checkout -b \u0026lt;branch_name\u0026gt; # 合并指定分支到当前分支 git merge \u0026lt;branch_name\u0026gt; # 删除分支 git branch -d \u0026lt;branch_name\u0026gt; # 查看所有分支 git branch -a # 添加远程仓库 git remote add origin \u0026lt;repository_url\u0026gt; # 查看远程仓库 git remote -v # 推送本地分支到远程仓库 git push origin \u0026lt;branch_name\u0026gt; # 推送所有分支到远程仓库 git push --all origin # 拉取远程仓库的更新 git pull # 查看远程仓库的分支 git branch -r # 删除远程分支 git push origin --delete \u0026lt;branch_name\u0026gt; # 查看文件的修改历史 git log -p \u0026lt;file_name\u0026gt; # 显示某个文件的历史版本 git show \u0026lt;commit_id\u0026gt;:\u0026lt;file_name\u0026gt; # 恢复工作区的文件到暂存区的状态 git checkout -- \u0026lt;file_name\u0026gt; # 恢复暂存区的文件到上一次提交的状态 git reset HEAD \u0026lt;file_name\u0026gt; # 撤销上一次的提交,但保留提交的内容 git reset --soft HEAD^ # 撤销上一次的提交,并删除提交的内容 git reset --hard HEAD^ # 暂存当前的修改 git stash # 恢复暂存的修改 git stash pop # 查看暂存的修改 git stash list # 删除暂存的修改 git stash drop 软件模式 # SourceTree # Github Desktop # ","date":"17 June 2024","externalUrl":null,"permalink":"/posts/git/use/","section":"Posts","summary":"安装Git # \u0026hellip;","title":"Git入门教程","type":"posts"},{"content":"","date":"17 June 2024","externalUrl":null,"permalink":"/categories/tools/","section":"Categories","summary":"","title":"Tools","type":"categories"},{"content":"","date":"17 June 2024","externalUrl":null,"permalink":"/agreements/","section":"Agreements","summary":"","title":"Agreements","type":"agreements"},{"content":"This End User License Agreement (\u0026ldquo;Agreement\u0026rdquo;) is a legal agreement between you (\u0026ldquo;User\u0026rdquo; or \u0026ldquo;you\u0026rdquo;) and [Your Company Name] (\u0026ldquo;Company,\u0026rdquo; \u0026ldquo;we,\u0026rdquo; \u0026ldquo;us,\u0026rdquo; or \u0026ldquo;our\u0026rdquo;) for the use of \u0026ldquo;HelloApp\u0026rdquo; (\u0026ldquo;Software\u0026rdquo;). By installing, copying, or otherwise using the Software, you agree to be bound by the terms of this Agreement.\n1. License Grant # Subject to the terms and conditions of this Agreement, the Company grants you a limited, non-exclusive, non-transferable, revocable license to use the Software solely for your personal or internal business purposes.\n2. Restrictions # You agree not to:\nCopy, modify, or create derivative works of the Software; Distribute, transfer, sublicense, lease, lend, or rent the Software to any third party; Reverse engineer, decompile, or disassemble the Software, except to the extent expressly permitted by applicable law; Remove, alter, or obscure any proprietary notices or labels on the Software. 3. Ownership # The Software is licensed, not sold. The Company retains all right, title, and interest in and to the Software, including all intellectual property rights therein.\n4. Updates # The Company may provide updates, upgrades, or enhancements to the Software. Any such updates, upgrades, or enhancements shall be deemed part of the Software and subject to the terms of this Agreement.\n5. Termination # This Agreement is effective until terminated. Your rights under this Agreement will terminate automatically without notice if you fail to comply with any term(s) of this Agreement. Upon termination, you must cease all use of the Software and destroy all copies of the Software in your possession or control.\n6. Disclaimer of Warranties # The Software is provided \u0026ldquo;AS IS\u0026rdquo; without warranty of any kind, either express or implied, including, but not limited to, the implied warranties of merchantability, fitness for a particular purpose, or non-infringement. The Company does not warrant that the Software will meet your requirements or that the operation of the Software will be uninterrupted or error-free.\n7. Limitation of Liability # To the maximum extent permitted by applicable law, in no event shall the Company be liable for any special, incidental, indirect, or consequential damages whatsoever (including, but not limited to, damages for loss of profits, loss of data, or other information, for business interruption, for personal injury, for loss of privacy) arising out of or in any way related to the use of or inability to use the Software, even if the Company has been advised of the possibility of such damages.\n8. Governing Law # This Agreement shall be governed by and construed in accordance with the laws of [Your Jurisdiction], without regard to its conflict of law principles.\n9. Entire Agreement # This Agreement constitutes the entire agreement between you and the Company concerning the Software and supersedes all prior or contemporaneous understandings regarding such subject matter. No amendment to or modification of this Agreement will be binding unless in writing and signed by the Company.\n10. Contact Information # If you have any questions about this Agreement, please contact us at:\nEmail: [email protected]\nThank you for using our software. We hope you have a great experience.\n","date":"17 June 2024","externalUrl":null,"permalink":"/agreements/eula/hello_app/","section":"Agreements","summary":"This End User License Agreement (\u0026ldquo;Agreement\u0026rdquo;) is a legal agreement between you (\u0026ldquo;User\u0026rdquo; or \u0026ldquo;you\u0026rdquo;) and [Your Company Name] (\u0026ldquo;Company,\u0026rdquo; \u0026ldquo;we,\u0026rdquo; \u0026ldquo;us,\u0026rdquo; or \u0026ldquo;our\u0026rdquo;) for the use of \u0026ldquo;HelloApp\u0026rdquo; (\u0026ldquo;Software\u0026rdquo;).","title":"End User License Agreement (EULA)","type":"agreements"},{"content":"Git安装教程\n","date":"17 June 2024","externalUrl":null,"permalink":"/posts/git/started/","section":"Posts","summary":"Git安装教程","title":"Git安装","type":"posts"},{"content":"We highly value your privacy and are committed to protecting your personal information. This privacy policy explains how we collect, use, disclose, and protect your information.\nInformation Collection # We may collect the following types of information:\nPersonal Information: When you register an account, subscribe to our services, or contact us, we may collect personal information such as your name, email address, and phone number. Usage Data: We may automatically collect information about how you access and use our services, such as your IP address, browser type, access times, and pages visited. Information Use # We use the collected information to:\nProvide and maintain our services; Improve and personalize your user experience; Process your transactions and send related information; Communicate with you, including responding to your inquiries and providing customer support; Analyze usage trends and monitor the usage of our services. Information Disclosure # We do not sell, trade, or rent your personal information to third parties. We may disclose your information in the following circumstances:\nLegal Requirements: We may disclose your information if required by law or in response to legal processes. Protection of Rights: We may disclose your information to protect our rights, privacy, safety, or property, and that of our users or the public. Information Protection # We take reasonable measures to protect your information from unauthorized access, use, or disclosure. However, no method of internet transmission or electronic storage is completely secure, and we cannot guarantee absolute security.\nYour Rights # Depending on applicable privacy laws, you may have the following rights:\nAccess and update your personal information; Request the deletion of your personal information; Withdraw your consent to our processing of your personal information; Lodge a complaint. Changes to This Privacy Policy # We may update this privacy policy from time to time. We will post any changes on this page and notify you of any significant changes by email or through a prominent notice on our website before the changes take effect.\nContact Us # If you have any questions or concerns about this privacy policy, please contact us at:\nEmail: [email protected]\nThank you for reading our privacy policy. We are committed to protecting your privacy and hope you feel safe and secure when using our services.\n","date":"17 June 2024","externalUrl":null,"permalink":"/agreements/privacy/","section":"Agreements","summary":"We highly value your privacy and are committed to protecting your personal information.","title":"Privacy Policy","type":"agreements"},{"content":"These Terms of Service (\u0026ldquo;Terms\u0026rdquo;) are a legal agreement between you (\u0026ldquo;User\u0026rdquo; or \u0026ldquo;you\u0026rdquo;) and PPSW.ASIA (\u0026ldquo;Company,\u0026rdquo; \u0026ldquo;we,\u0026rdquo; \u0026ldquo;us,\u0026rdquo; or \u0026ldquo;our\u0026rdquo;) governing your use of our services (\u0026ldquo;Services\u0026rdquo;). By accessing or using our Services, you agree to be bound by these Terms.\n1. Acceptance of Terms # By accessing or using our Services, you agree to comply with and be bound by these Terms and all applicable laws and regulations. If you do not agree to these Terms, you must not use our Services.\n2. Changes to Terms # We reserve the right to modify these Terms at any time. We will notify you of any changes by posting the new Terms on our website. Your continued use of the Services after the changes have been posted will constitute your acceptance of the new Terms.\n3. Use of Services # You agree to use the Services only for lawful purposes and in accordance with these Terms. You agree not to:\nUse the Services in any way that violates any applicable federal, state, local, or international law or regulation; Engage in any conduct that restricts or inhibits anyone\u0026rsquo;s use or enjoyment of the Services, or which, as determined by us, may harm the Company or users of the Services; Use the Services in any manner that could disable, overburden, damage, or impair the Services or interfere with any other party\u0026rsquo;s use of the Services. 4. Account Registration # To access certain features of the Services, you may be required to register for an account. You agree to provide accurate, current, and complete information during the registration process and to update such information to keep it accurate, current, and complete. You are responsible for safeguarding your account information and for any activities or actions under your account.\n5. Intellectual Property # The Services and their entire contents, features, and functionality (including but not limited to all information, software, text, displays, images, and audio) are owned by the Company, its licensors, or other providers of such material and are protected by copyright, trademark, patent, trade secret, and other intellectual property or proprietary rights laws.\n6. Termination # We may terminate or suspend your access to the Services immediately, without prior notice or liability, for any reason whatsoever, including without limitation if you breach the Terms. Upon termination, your right to use the Services will immediately cease.\n7. Limitation of Liability # To the fullest extent permitted by applicable law, in no event shall the Company, its affiliates, directors, employees, or agents be liable for any indirect, incidental, special, consequential, or punitive damages, including without limitation, loss of profits, data, use, goodwill, or other intangible losses, resulting from (i) your use or inability to use the Services; (ii) any unauthorized access to or use of our servers and/or any personal information stored therein; (iii) any interruption or cessation of transmission to or from the Services; (iv) any bugs, viruses, trojan horses, or the like that may be transmitted to or through our Services by any third party; (v) any errors or omissions in any content or for any loss or damage incurred as a result of the use of any content posted, emailed, transmitted, or otherwise made available through the Services; and/or (vi) the defamatory, offensive, or illegal conduct of any third party. In no event shall the Company’s aggregate liability exceed the amount paid by you, if any, for accessing the Services.\n8. Governing Law # These Terms shall be governed and construed in accordance with the laws of [Your Jurisdiction], without regard to its conflict of law provisions.\n9. Changes to Terms # We reserve the right, at our sole discretion, to modify or replace these Terms at any time. If a revision is material, we will provide at least 30 days\u0026rsquo; notice prior to any new terms taking effect. What constitutes a material change will be determined at our sole discretion.\n10. Contact Us # If you have any questions about these Terms, please contact us at:\nEmail: [email protected]\nThank you for using our services. We hope you have a great experience.\n","date":"17 June 2024","externalUrl":null,"permalink":"/agreements/termsofuse/","section":"Agreements","summary":"These Terms of Service (\u0026ldquo;Terms\u0026rdquo;) are a legal agreement between you (\u0026ldquo;User\u0026rdquo; or \u0026ldquo;you\u0026rdquo;) and PPSW.","title":"Terms of use","type":"agreements"},{"content":"HelloApp Admin Web\n","date":"17 May 2024","externalUrl":null,"permalink":"/portfolio/hello_admin/","section":"Portfolio","summary":"HelloApp Admin Web","title":"HelloApp Admin Web","type":"portfolio"},{"content":"","externalUrl":null,"permalink":"/authors/","section":"Authors","summary":"","title":"Authors","type":"authors"},{"content":"When the work is tired, let\u0026rsquo;s take a break, listen to music in the rest area, look at beautiful women, and combine work and rest!\n","externalUrl":null,"permalink":"/lounge/","section":"Lounge","summary":"When the work is tired, let\u0026rsquo;s take a break, listen to music in the rest area, look at beautiful women, and combine work and rest!","title":"Lounge","type":"lounge"},{"content":"","externalUrl":null,"permalink":"/series/","section":"Series","summary":"","title":"Series","type":"series"}]