Compare commits
220 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4e7ca97def | ||
|
|
348d8fa54e | ||
|
|
5809217adc | ||
|
|
b17d08b7a6 | ||
|
|
cc3336ea26 | ||
|
|
32c75254b9 | ||
|
|
0aa78709e6 | ||
|
|
040d3d08d3 | ||
|
|
7770e3b98b | ||
|
|
211d12be70 | ||
|
|
ccf14504c9 | ||
|
|
d105c2567e | ||
|
|
7e83c56d80 | ||
|
|
8359cfcc81 | ||
|
|
aac293832c | ||
|
|
422b0481bc | ||
|
|
c517e21465 | ||
|
|
8f1a696e94 | ||
|
|
4047d726ac | ||
|
|
4b26b4d9e6 | ||
|
|
2f251c4f63 | ||
|
|
d2985bab88 | ||
|
|
f897241a08 | ||
|
|
8f26cae3f0 | ||
|
|
bbe2aa5d2f | ||
|
|
12f1742f71 | ||
|
|
931e5e831f | ||
|
|
6c6e1515ef | ||
|
|
eb49564282 | ||
|
|
7ea9f0ef1c | ||
|
|
a0c1357f85 | ||
|
|
4f8bb5ac57 | ||
|
|
10f06b2794 | ||
|
|
b2b734f295 | ||
|
|
9800b03b63 | ||
|
|
4377817bef | ||
|
|
8fee436996 | ||
|
|
9f949dd99b | ||
|
|
714c98130a | ||
|
|
fc79fb76c1 | ||
|
|
9878f02f70 | ||
|
|
9c149334fa | ||
|
|
2130047bd6 | ||
|
|
bcc76dd6ab | ||
|
|
e7bbe0e235 | ||
|
|
8ffed5651d | ||
|
|
faa666b54d | ||
|
|
42aaaed045 | ||
|
|
4705b35694 | ||
|
|
073035bee9 | ||
|
|
ab4771e015 | ||
|
|
d0ad10429f | ||
|
|
7f56207fa1 | ||
|
|
21eea53dfd | ||
|
|
2d6fb1f3bb | ||
|
|
528d15e6c9 | ||
|
|
615fe66544 | ||
|
|
01c1227895 | ||
|
|
ecd17cb628 | ||
|
|
134b414f0b | ||
|
|
421f55192e | ||
|
|
cf763d3a32 | ||
|
|
4a417cc02c | ||
|
|
c6924a8b92 | ||
|
|
344aa60893 | ||
|
|
7f492f3a9f | ||
|
|
1c95f17460 | ||
|
|
674a486c7f | ||
|
|
412accc066 | ||
|
|
ba24c72347 | ||
|
|
11dd302689 | ||
|
|
58bc654304 | ||
|
|
c5410326fe | ||
|
|
db0e768f81 | ||
|
|
23a1dc7e07 | ||
|
|
a7b6a80799 | ||
|
|
fad20ba4c7 | ||
|
|
2a7fc0034c | ||
|
|
658981adf7 | ||
|
|
b6f5402220 | ||
|
|
de0d6cff40 | ||
|
|
881787bed6 | ||
|
|
e25b656275 | ||
|
|
a784b6fdb4 | ||
|
|
bfb8ef31fe | ||
|
|
4e4da93b6c | ||
|
|
b0c1d9a229 | ||
|
|
ac80080f90 | ||
|
|
d28c8e512a | ||
|
|
be57a43589 | ||
|
|
0465ac9c1b | ||
|
|
77d2d3a01d | ||
|
|
704459225b | ||
|
|
04770c403d | ||
|
|
f42980e090 | ||
|
|
7ad33f509e | ||
|
|
1b013c3590 | ||
|
|
cef27bdfa0 | ||
|
|
f7334882c3 | ||
|
|
9397d58986 | ||
|
|
7f6b7229f6 | ||
|
|
a0a03760cd | ||
|
|
9606e11e0e | ||
|
|
7f04293361 | ||
|
|
e6b33a70e4 | ||
|
|
179a59ac1b | ||
|
|
2a5ed14599 | ||
|
|
1cc5d2eb53 | ||
|
|
687e50914f | ||
|
|
a165ba38a6 | ||
|
|
6b7cfc5ab2 | ||
|
|
1f2c3d43a6 | ||
|
|
5bee5ae143 | ||
|
|
f01c126b36 | ||
|
|
3d1fa11973 | ||
|
|
93245dc4d6 | ||
|
|
86447299b1 | ||
|
|
64259f73e8 | ||
|
|
8031739110 | ||
|
|
27e5c2bc74 | ||
|
|
bb26cec0ec | ||
|
|
ef663d2051 | ||
|
|
be8568ce00 | ||
|
|
5399e3ad8c | ||
|
|
68379f4098 | ||
|
|
daa1d96f12 | ||
|
|
998d83c15c | ||
|
|
0cb43dd17c | ||
|
|
b89aaed785 | ||
|
|
47cc2b2304 | ||
|
|
a20215d9da | ||
|
|
4f362760b6 | ||
|
|
2e43d4c7a1 | ||
|
|
4b2688245f | ||
|
|
082f85a4e2 | ||
|
|
0ce76c9c36 | ||
|
|
6e71d7c414 | ||
|
|
84909cf397 | ||
|
|
fc290d5a6a | ||
|
|
ebd530f652 | ||
|
|
e50c5f73d7 | ||
|
|
1db0006c96 | ||
|
|
7d0a9df1c3 | ||
|
|
8e1b4e35a3 | ||
|
|
859afc63d3 | ||
|
|
ee6db35b34 | ||
|
|
283c0fce03 | ||
|
|
ac5e69f1a0 | ||
|
|
b2df22104e | ||
|
|
c88f028f3e | ||
|
|
312bfd99d5 | ||
|
|
ca576a0224 | ||
|
|
a5f35b133f | ||
|
|
f197c9f43d | ||
|
|
bce9efcc43 | ||
|
|
80c38d95e9 | ||
|
|
0b535d1dd8 | ||
|
|
e2ff745949 | ||
|
|
fbcf85559e | ||
|
|
ed3da927cc | ||
|
|
225d0ba8f9 | ||
|
|
afaf16620a | ||
|
|
4883d13950 | ||
|
|
b094ddc5f9 | ||
|
|
a422105c61 | ||
|
|
96423b8918 | ||
|
|
ba131ff14b | ||
|
|
7d59f5ebfb | ||
|
|
95f3a4b09a | ||
|
|
728f982310 | ||
|
|
2ca236c291 | ||
|
|
8a22282191 | ||
|
|
935600a6d9 | ||
|
|
d3bf4b6207 | ||
|
|
aa09a0dcc2 | ||
|
|
cd8cc8cbc6 | ||
|
|
1bfbe09c6f | ||
|
|
61d05b49c5 | ||
|
|
9752afbebc | ||
|
|
e210b4a65a | ||
|
|
6581868336 | ||
|
|
7ee668e474 | ||
|
|
62b949679b | ||
|
|
6242e8d9b9 | ||
|
|
ee59bb76de | ||
|
|
3eb134a280 | ||
|
|
257023209b | ||
|
|
0da20180ac | ||
|
|
1f57c782e5 | ||
|
|
1f6e06fc85 | ||
|
|
ed3675ca7f | ||
|
|
695e419722 | ||
|
|
3bceac1515 | ||
|
|
473f7e1445 | ||
|
|
fcf95a3ea6 | ||
|
|
cc02e38aef | ||
|
|
9c119c6e29 | ||
|
|
9e297866ed | ||
|
|
261929f4c3 | ||
|
|
9976e134ca | ||
|
|
1b410e5a80 | ||
|
|
9ebe53fdbf | ||
|
|
5f59aab40a | ||
|
|
4f46134f10 | ||
|
|
519f4afe17 | ||
|
|
30ffce6939 | ||
|
|
fe47f841e7 | ||
|
|
f33cd60b84 | ||
|
|
431e2b522d | ||
|
|
d1ba5daead | ||
|
|
6fe4b6467f | ||
|
|
89a1a14b2c | ||
|
|
3ea331332c | ||
|
|
38c155cc95 | ||
|
|
b4d2be18fe | ||
|
|
1a5f62ace2 | ||
|
|
935c6fc73a | ||
|
|
947fded387 | ||
|
|
e6bd16e2d4 | ||
|
|
4806744c94 |
7
.editorconfig
Normal file
@@ -0,0 +1,7 @@
|
||||
root=true
|
||||
|
||||
[*]
|
||||
indent_style=tab
|
||||
indent_size=4
|
||||
trim_trailing_whitespace=true
|
||||
insert_final_newline=true
|
||||
61
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
Normal file
@@ -0,0 +1,61 @@
|
||||
name: Bug report
|
||||
description: Create a report to help us improve
|
||||
labels: Bug
|
||||
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
**Please, make sure you are using [latest](https://github.com/Open-Shell/Open-Shell-Menu/releases) `Open-Shell` build before reporting a bug.**
|
||||
Especially on `Windows 11` you should use 4.4.190 (or newer).
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Describe the bug
|
||||
description: A clear and concise description of what the bug is. Screenshots are also encouraged.
|
||||
placeholder: Please use English for reports and screenshots to allow maintainers to easily understand the issue.
|
||||
validations:
|
||||
required: true
|
||||
- type: dropdown
|
||||
attributes:
|
||||
label: Area of issue
|
||||
description: What component(s) of Open-Shell does this involve? Select all that apply.
|
||||
multiple: true
|
||||
options:
|
||||
- Start menu
|
||||
- Taskbar
|
||||
- Windows Explorer
|
||||
- Internet Explorer
|
||||
- Installation/Other
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: To reproduce
|
||||
description: Steps to reproduce the behavior
|
||||
placeholder: |
|
||||
1. Go to '...'
|
||||
2. Click on '....'
|
||||
3. Scroll down to '....'
|
||||
4. See error
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Expected behavior
|
||||
placeholder: What did you expect to happen?
|
||||
- type: input
|
||||
attributes:
|
||||
label: Open-Shell version
|
||||
placeholder: e.g. 4.4.170
|
||||
validations:
|
||||
required: true
|
||||
- type: input
|
||||
attributes:
|
||||
label: Windows version
|
||||
placeholder: e.g. Windows 10 22H2
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: Add any other context about the problem here.
|
||||
5
.github/ISSUE_TEMPLATE/config.yml
vendored
Normal file
@@ -0,0 +1,5 @@
|
||||
blank_issues_enabled: false
|
||||
contact_links:
|
||||
- name: Github Discussions
|
||||
url: https://github.com/Open-Shell/Open-Shell-Menu/discussions
|
||||
about: Please ask and answer questions here.
|
||||
39
.github/ISSUE_TEMPLATE/feature_request.yml
vendored
Normal file
@@ -0,0 +1,39 @@
|
||||
name: Feature request
|
||||
description: Suggest an idea for this project
|
||||
labels: Enhancement/Feature Request
|
||||
|
||||
body:
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Is your feature request related to a problem? Please describe.
|
||||
description: A clear and concise description of what the problem is.
|
||||
placeholder: Ex. I'm always frustrated when [...]
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Describe the solution you'd like
|
||||
description: A clear and concise description of what you want to happen.
|
||||
validations:
|
||||
required: true
|
||||
- type: dropdown
|
||||
attributes:
|
||||
label: Area of issue
|
||||
description: What component(s) of Open-Shell does this involve? Select all that apply.
|
||||
multiple: true
|
||||
options:
|
||||
- Start menu
|
||||
- Taskbar
|
||||
- Windows Explorer
|
||||
- Internet Explorer
|
||||
- Installation/Other
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Alternatives you've considered
|
||||
description: A clear and concise description of any alternative solutions or features you've considered.
|
||||
- type: textarea
|
||||
attributes:
|
||||
label: Additional context
|
||||
description: Add any other context or screenshots about the feature request here.
|
||||
359
.gitignore
vendored
Normal file
@@ -0,0 +1,359 @@
|
||||
.vs
|
||||
## Ignore Visual Studio temporary files, build results, and
|
||||
## files generated by popular Visual Studio add-ons.
|
||||
##
|
||||
## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore
|
||||
|
||||
# ignore vscode stuff
|
||||
.vscode/
|
||||
.ionide/
|
||||
|
||||
# User-specific files
|
||||
*.suo
|
||||
*.user
|
||||
*.userosscache
|
||||
*.sln.docstates
|
||||
|
||||
# User-specific files (MonoDevelop/Xamarin Studio)
|
||||
*.userprefs
|
||||
|
||||
# Build results
|
||||
[Dd]ebug/
|
||||
[Dd]ebug64/
|
||||
[Dd]ebugPublic/
|
||||
[Rr]elease/
|
||||
[Rr]elease64/
|
||||
[Rr]eleases/
|
||||
x64/
|
||||
x86/
|
||||
bld/
|
||||
[Bb]in/
|
||||
[Oo]bj/
|
||||
[Ll]og/
|
||||
|
||||
# Visual Studio 2015/2017 cache/options directory
|
||||
.vs/
|
||||
# Uncomment if you have tasks that create the project's static files in wwwroot
|
||||
#wwwroot/
|
||||
|
||||
# Visual Studio 2017 auto generated files
|
||||
Generated\ Files/
|
||||
|
||||
# MSTest test Results
|
||||
[Tt]est[Rr]esult*/
|
||||
[Bb]uild[Ll]og.*
|
||||
|
||||
# NUNIT
|
||||
*.VisualState.xml
|
||||
TestResult.xml
|
||||
|
||||
# Build Results of an ATL Project
|
||||
[Dd]ebugPS/
|
||||
[Rr]eleasePS/
|
||||
dlldata.c
|
||||
|
||||
# Benchmark Results
|
||||
BenchmarkDotNet.Artifacts/
|
||||
|
||||
# .NET Core
|
||||
project.lock.json
|
||||
project.fragment.lock.json
|
||||
artifacts/
|
||||
|
||||
# StyleCop
|
||||
StyleCopReport.xml
|
||||
|
||||
# Files built by Visual Studio
|
||||
*.dll
|
||||
*_i.c
|
||||
*_p.c
|
||||
*_i.h
|
||||
*_h.h
|
||||
*.ilk
|
||||
*.meta
|
||||
*.obj
|
||||
*.exe
|
||||
*.iobj
|
||||
*.pch
|
||||
*.pdb
|
||||
*.ipdb
|
||||
*.pgc
|
||||
*.pgd
|
||||
*.rsp
|
||||
*.sbr
|
||||
*.tlb
|
||||
*.tli
|
||||
*.tlh
|
||||
*.tmp
|
||||
*.tmp_proj
|
||||
*.log
|
||||
*.tlog/
|
||||
*.tlog
|
||||
*.vspscc
|
||||
*.vssscc
|
||||
.builds
|
||||
*.pidb
|
||||
*.svclog
|
||||
*.scc
|
||||
*.lastbuildstate
|
||||
*.exp
|
||||
*.lib
|
||||
*.res
|
||||
*.ipdb
|
||||
|
||||
# Chutzpah Test files
|
||||
_Chutzpah*
|
||||
|
||||
# Visual C++ cache files
|
||||
ipch/
|
||||
*.aps
|
||||
*.ncb
|
||||
*.opendb
|
||||
*.opensdf
|
||||
*.sdf
|
||||
*.cachefile
|
||||
*.VC.db
|
||||
*.VC.VC.opendb
|
||||
|
||||
# Visual Studio profiler
|
||||
*.psess
|
||||
*.vsp
|
||||
*.vspx
|
||||
*.sap
|
||||
|
||||
# Visual Studio Trace Files
|
||||
*.e2e
|
||||
|
||||
# TFS 2012 Local Workspace
|
||||
$tf/
|
||||
|
||||
# Guidance Automation Toolkit
|
||||
*.gpState
|
||||
|
||||
# ReSharper is a .NET coding add-in
|
||||
_ReSharper*/
|
||||
*.[Rr]e[Ss]harper
|
||||
*.DotSettings.user
|
||||
|
||||
# JustCode is a .NET coding add-in
|
||||
.JustCode
|
||||
|
||||
# TeamCity is a build add-in
|
||||
_TeamCity*
|
||||
|
||||
# DotCover is a Code Coverage Tool
|
||||
*.dotCover
|
||||
|
||||
# AxoCover is a Code Coverage Tool
|
||||
.axoCover/*
|
||||
!.axoCover/settings.json
|
||||
|
||||
# Visual Studio code coverage results
|
||||
*.coverage
|
||||
*.coveragexml
|
||||
|
||||
# NCrunch
|
||||
_NCrunch_*
|
||||
.*crunch*.local.xml
|
||||
nCrunchTemp_*
|
||||
|
||||
# MightyMoose
|
||||
*.mm.*
|
||||
AutoTest.Net/
|
||||
|
||||
# Web workbench (sass)
|
||||
.sass-cache/
|
||||
|
||||
# Installshield output folder
|
||||
[Ee]xpress/
|
||||
|
||||
# DocProject is a documentation generator add-in
|
||||
DocProject/buildhelp/
|
||||
DocProject/Help/*.HxT
|
||||
DocProject/Help/*.HxC
|
||||
DocProject/Help/*.hhc
|
||||
DocProject/Help/*.hhk
|
||||
DocProject/Help/*.hhp
|
||||
DocProject/Help/Html2
|
||||
DocProject/Help/html
|
||||
|
||||
# Click-Once directory
|
||||
publish/
|
||||
|
||||
# Publish Web Output
|
||||
*.[Pp]ublish.xml
|
||||
*.azurePubxml
|
||||
# Note: Comment the next line if you want to checkin your web deploy settings,
|
||||
# but database connection strings (with potential passwords) will be unencrypted
|
||||
*.pubxml
|
||||
*.publishproj
|
||||
|
||||
# Microsoft Azure Web App publish settings. Comment the next line if you want to
|
||||
# checkin your Azure Web App publish settings, but sensitive information contained
|
||||
# in these scripts will be unencrypted
|
||||
PublishScripts/
|
||||
|
||||
# NuGet Packages
|
||||
*.nupkg
|
||||
# The packages folder can be ignored because of Package Restore
|
||||
**/[Pp]ackages/*
|
||||
# except build/, which is used as an MSBuild target.
|
||||
!**/[Pp]ackages/build/
|
||||
# Uncomment if necessary however generally it will be regenerated when needed
|
||||
#!**/[Pp]ackages/repositories.config
|
||||
# NuGet v3's project.json files produces more ignorable files
|
||||
*.nuget.props
|
||||
*.nuget.targets
|
||||
|
||||
# Microsoft Azure Build Output
|
||||
csx/
|
||||
*.build.csdef
|
||||
|
||||
# Microsoft Azure Emulator
|
||||
ecf/
|
||||
rcf/
|
||||
|
||||
# Windows Store app package directories and files
|
||||
AppPackages/
|
||||
BundleArtifacts/
|
||||
Package.StoreAssociation.xml
|
||||
_pkginfo.txt
|
||||
*.appx
|
||||
|
||||
# Visual Studio cache files
|
||||
# files ending in .cache can be ignored
|
||||
*.[Cc]ache
|
||||
# but keep track of directories ending in .cache
|
||||
!*.[Cc]ache/
|
||||
|
||||
# Others
|
||||
ClientBin/
|
||||
~$*
|
||||
*~
|
||||
*.dbmdl
|
||||
*.dbproj.schemaview
|
||||
*.jfm
|
||||
*.pfx
|
||||
*.publishsettings
|
||||
orleans.codegen.cs
|
||||
|
||||
# Including strong name files can present a security risk
|
||||
# (https://github.com/github/gitignore/pull/2483#issue-259490424)
|
||||
#*.snk
|
||||
|
||||
# Since there are multiple workflows, uncomment next line to ignore bower_components
|
||||
# (https://github.com/github/gitignore/pull/1529#issuecomment-104372622)
|
||||
#bower_components/
|
||||
|
||||
# RIA/Silverlight projects
|
||||
Generated_Code/
|
||||
|
||||
# Backup & report files from converting an old project file
|
||||
# to a newer Visual Studio version. Backup files are not needed,
|
||||
# because we have git ;-)
|
||||
_UpgradeReport_Files/
|
||||
Backup*/
|
||||
UpgradeLog*.XML
|
||||
UpgradeLog*.htm
|
||||
ServiceFabricBackup/
|
||||
*.rptproj.bak
|
||||
|
||||
# SQL Server files
|
||||
*.mdf
|
||||
*.ldf
|
||||
*.ndf
|
||||
|
||||
# Business Intelligence projects
|
||||
*.rdl.data
|
||||
*.bim.layout
|
||||
*.bim_*.settings
|
||||
*.rptproj.rsuser
|
||||
|
||||
# Microsoft Fakes
|
||||
FakesAssemblies/
|
||||
|
||||
# GhostDoc plugin setting file
|
||||
*.GhostDoc.xml
|
||||
|
||||
# Node.js Tools for Visual Studio
|
||||
.ntvs_analysis.dat
|
||||
node_modules/
|
||||
|
||||
# Visual Studio 6 build log
|
||||
*.plg
|
||||
|
||||
# Visual Studio 6 workspace options file
|
||||
*.opt
|
||||
|
||||
# Visual Studio 6 auto-generated workspace file (contains which files were open etc.)
|
||||
*.vbw
|
||||
|
||||
# Visual Studio LightSwitch build output
|
||||
**/*.HTMLClient/GeneratedArtifacts
|
||||
**/*.DesktopClient/GeneratedArtifacts
|
||||
**/*.DesktopClient/ModelManifest.xml
|
||||
**/*.Server/GeneratedArtifacts
|
||||
**/*.Server/ModelManifest.xml
|
||||
_Pvt_Extensions
|
||||
|
||||
# Paket dependency manager
|
||||
.paket/paket.exe
|
||||
paket-files/
|
||||
|
||||
# FAKE - F# Make
|
||||
.fake/
|
||||
|
||||
# JetBrains Rider
|
||||
.idea/
|
||||
*.sln.iml
|
||||
|
||||
# CodeRush
|
||||
.cr/
|
||||
|
||||
# Python Tools for Visual Studio (PTVS)
|
||||
__pycache__/
|
||||
*.pyc
|
||||
|
||||
# Cake - Uncomment if you are using it
|
||||
# tools/**
|
||||
# !tools/packages.config
|
||||
|
||||
# Tabs Studio
|
||||
*.tss
|
||||
|
||||
# Telerik's JustMock configuration file
|
||||
*.jmconfig
|
||||
|
||||
# BizTalk build output
|
||||
*.btp.cs
|
||||
*.btm.cs
|
||||
*.odx.cs
|
||||
*.xsd.cs
|
||||
|
||||
# OpenCover UI analysis results
|
||||
OpenCover/
|
||||
|
||||
# Azure Stream Analytics local run output
|
||||
ASALocalRun/
|
||||
|
||||
# MSBuild Binary and Structured Log
|
||||
*.binlog
|
||||
|
||||
# NVidia Nsight GPU debugger configuration file
|
||||
*.nvuser
|
||||
|
||||
# MFractors (Xamarin productivity tool) working folder
|
||||
.mfractor/
|
||||
|
||||
# PVS-Studio temporary files (Github integration performance fix)
|
||||
*.PVS-Studio.*
|
||||
|
||||
# Classic-Shell specific ignores
|
||||
Src/Setup/Output/
|
||||
Src/Setup/Final/
|
||||
Src/Setup/Temp/
|
||||
*.adml
|
||||
*.admx
|
||||
*.zip
|
||||
*.bin
|
||||
*.chm
|
||||
21
LICENSE
Normal file
@@ -0,0 +1,21 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2017-2018
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
@@ -1,7 +1,7 @@
|
||||
<a href="#"><img src="https://raw.githubusercontent.com/Open-Shell/Open-Shell-Menu/master/Src/Setup/OpenShell.ico" width="96" align="left"/></a>
|
||||
<a href="#"><img src=/Src/Setup/OpenShell.ico width="80" align="left"/></a>
|
||||
|
||||
|
||||
# Open-Shell
|
||||
# Open-Shell
|
||||
|
||||
A collection of utilities bringing back classic features to Windows.
|
||||
|
||||
@@ -9,35 +9,32 @@ A collection of utilities bringing back classic features to Windows.
|
||||
|
||||
[](https://github.com/Open-Shell/Open-Shell-Menu/releases/latest) [](https://github.com/Open-Shell/Open-Shell-Menu/releases) [](https://ci.appveyor.com/project/passionate-coder/open-shell-menu/branch/master) [](https://gitq.com/passionate-coder/Classic-Start) [](https://gitter.im/open-shell/Lobby) [](https://discord.gg/7H6arr5)
|
||||
|
||||
[Open-Shell Homepage](https://open-shell.github.io/Open-Shell-Menu)
|
||||
|
||||
### Features
|
||||
- Classic style Start menu for Windows 7, 8, 8.1, 10, 11
|
||||
- Classic style Start menu for Windows 7, 8, 8.1, 10, and 11
|
||||
- Toolbar for Windows Explorer
|
||||
- Explorer status bar with file size and disk space
|
||||
- Classic copy UI (Windows 7 only)
|
||||
- Title bar and status bar for Internet Explorer
|
||||
|
||||
### Download
|
||||
You can find the latest stable version here:
|
||||
You can find the latest stable version here:
|
||||
|
||||
[](https://github.com/Open-Shell/Open-Shell-Menu/releases/latest)
|
||||
|
||||
You can find the latest nightly build here:
|
||||
### ⚠️ Windows for ARM compatibility ⚠️
|
||||
Open-Shell is not compatible with Windows for ARM. If you install it on a Windows for ARM installation (ex. using Parallels Desktop on an Apple Silicon Mac), you will no longer be able to log into your account the next time you reboot. Please refrain from installing Open-Shell on Windows for ARM.
|
||||
|
||||
[](https://github.com/Open-Shell/Open-Shell-Menu/releases)
|
||||
|
||||
### Get Help
|
||||
- [Report an issue](https://github.com/Open-Shell/Open-Shell-Menu/issues)
|
||||
- [Ask in Discussions](https://github.com/Open-Shell/Open-Shell-Menu/discussions)
|
||||
- [Post in Gitter room](https://gitter.im/Open-Shell)
|
||||
- [Join our Discord](https://discord.gg/7H6arr5)
|
||||
|
||||
### Temporary Translation/Language Solution
|
||||
### Temporary Translation/Language Solution
|
||||
1. Download [language DLL](https://coddec.github.io/Classic-Shell/www.classicshell.net/translations/index.html)
|
||||
2. Place it either in the Open-Shell's __install folder__ or in the `%ALLUSERSPROFILE%\Open-Shell\Languages` folder.
|
||||
2. Place it either in the Open-Shell's __install folder__ or in the `%ALLUSERSPROFILE%\OpenShell\Languages` folder
|
||||
|
||||
---
|
||||
----
|
||||
|
||||
*For archival reasons, we have a mirror of `www.classicshell.net` [here](https://coddec.github.io/Classic-Shell/www.classicshell.net/).*
|
||||
|
||||
[How To Skin a Start Menu](https://coddec.github.io/Classic-Shell/www.classicshell.net/tutorials/skintutorial.html)
|
||||
[Classic Shell: Custom Start Buttons](https://coddec.github.io/Classic-Shell/www.classicshell.net/tutorials/buttontutorial.html)
|
||||
[Questions? Ask on the Discussions section](https://github.com/Open-Shell/Open-Shell-Menu/discussions) or on [Discord](https://discord.gg/7H6arr5)
|
||||
[Submit a bug report/feature request](https://github.com/Open-Shell/Open-Shell-Menu/issues)
|
||||
19
Src/BUILDME.txt
Normal file
@@ -0,0 +1,19 @@
|
||||
To build Open-Shell, navigate to the Setup folder and run __MakeFinal.bat.
|
||||
It will compile the binaries, produce installer for English, and create the final archives.
|
||||
Then you can run the individual language files like _BuildFrench.bat to create the installers
|
||||
for other languages.
|
||||
The final files (installers, archives) are saved to the Setup\Final folder.
|
||||
|
||||
You need the following tools:
|
||||
Visual Studio 2022 (Community Edition is enough)
|
||||
- Desktop development with C++ workload
|
||||
- Windows 11 SDK (10.0.22621.0) for Desktop C++
|
||||
- Visual C++ ATL support
|
||||
HTML Help Workshop
|
||||
WiX 3.14
|
||||
7-Zip
|
||||
It is possible to convert the projects to newer versions of Visual Studio and newer SDKs.
|
||||
Newer versions of WiX will probably work fine.
|
||||
|
||||
Note: Unlike the official release, the source code does not contain digital certificate and
|
||||
produces unsigned binaries.
|
||||
776
Src/ClassicExplorer/ClassicCopy.cpp
Normal file
@@ -0,0 +1,776 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include "stdafx.h"
|
||||
#include <commctrl.h>
|
||||
#include <oleacc.h>
|
||||
#include <atlcomcli.h>
|
||||
#include <dwmapi.h>
|
||||
#include <utility>
|
||||
#include "Translations.h"
|
||||
#include "Settings.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "ComHelper.h"
|
||||
#include "dllmain.h"
|
||||
|
||||
static wchar_t g_TitleMove[256];
|
||||
static wchar_t g_TitleCopy[256];
|
||||
static wchar_t g_TitleFolder[256];
|
||||
static wchar_t g_ButtonMove[256];
|
||||
static wchar_t g_ButtonDontMove[256];
|
||||
static wchar_t g_ButtonCopy[256];
|
||||
static wchar_t g_ButtonDontCopy[256];
|
||||
static wchar_t g_ButtonCancel[256];
|
||||
static wchar_t g_ButtonMore[256];
|
||||
static HMODULE g_hShell32;
|
||||
|
||||
static void LogPrint( CString *pLog, const wchar_t *format, ... )
|
||||
{
|
||||
wchar_t buf[256];
|
||||
va_list args;
|
||||
va_start(args,format);
|
||||
int len=Vsprintf(buf,_countof(buf),format,args);
|
||||
va_end(args);
|
||||
*pLog+=buf;
|
||||
}
|
||||
|
||||
// CClassicCopyFile - this is the implementation of the Copy UI dialog box for files
|
||||
|
||||
class CClassicCopyFile
|
||||
{
|
||||
public:
|
||||
CClassicCopyFile( void );
|
||||
~CClassicCopyFile( void );
|
||||
|
||||
bool Run( HWND hWnd, IAccessible *pAcc, CString *pLog );
|
||||
|
||||
private:
|
||||
void EnumAccChildren( IAccessible *pAcc, CString *pLog );
|
||||
void AddAccChild( IAccessible *pAcc, const VARIANT &id, CString *pLog );
|
||||
void GetFileInfo( IAccessible *pAcc, bool bSrc );
|
||||
|
||||
CString m_FileName;
|
||||
bool m_bSystem;
|
||||
bool m_bReadOnly;
|
||||
HICON m_Icon;
|
||||
|
||||
CString m_SrcSize;
|
||||
CString m_SrcTime;
|
||||
HICON m_SrcIcon;
|
||||
|
||||
CString m_DstSize;
|
||||
CString m_DstTime;
|
||||
HICON m_DstIcon;
|
||||
|
||||
typedef std::pair<CComPtr<IAccessible>,int> CControl;
|
||||
CControl m_YesButton;
|
||||
CControl m_NoButton;
|
||||
CControl m_CheckBox;
|
||||
CControl m_Cancel;
|
||||
bool m_bCopyMultiLast; // the last of a series of multi-file boxes
|
||||
|
||||
static INT_PTR CALLBACK DialogProc( HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam );
|
||||
|
||||
static void PumpMessages( void );
|
||||
};
|
||||
|
||||
CClassicCopyFile::CClassicCopyFile( void )
|
||||
{
|
||||
m_Icon=m_SrcIcon=m_DstIcon=NULL;
|
||||
m_bCopyMultiLast=false;
|
||||
m_bSystem=m_bReadOnly=false;
|
||||
}
|
||||
|
||||
CClassicCopyFile::~CClassicCopyFile( void )
|
||||
{
|
||||
if (m_Icon) DestroyIcon(m_Icon);
|
||||
if (m_SrcIcon) DestroyIcon(m_SrcIcon);
|
||||
if (m_DstIcon) DestroyIcon(m_DstIcon);
|
||||
}
|
||||
|
||||
// Show the dialog box. Returns true to suppress the original task dialog box
|
||||
bool CClassicCopyFile::Run( HWND hWnd, IAccessible *pAcc, CString *pLog )
|
||||
{
|
||||
// find all interesting controls
|
||||
EnumAccChildren(pAcc,pLog);
|
||||
|
||||
if (!m_YesButton.first || m_YesButton.second!=CHILDID_SELF || !m_NoButton.first || m_NoButton.second!=CHILDID_SELF || !m_Cancel.first)
|
||||
return false; // something is wrong, do nothing
|
||||
|
||||
if (pLog) pLog->Empty(); // success - no need to log anything
|
||||
|
||||
// get the info for the source and the destination file (file name, icon, properties)
|
||||
m_bReadOnly=false;
|
||||
m_bSystem=false;
|
||||
GetFileInfo(m_YesButton.first,true);
|
||||
GetFileInfo(m_NoButton.first,false);
|
||||
|
||||
TlsData *pTlsData=GetTlsData();
|
||||
if (m_CheckBox.first)
|
||||
pTlsData->bCopyMultiFile=true;
|
||||
else if (pTlsData->bCopyMultiFile)
|
||||
m_bCopyMultiLast=true;
|
||||
|
||||
// pick the correct dialog template (for single and multiple files, for LTR and RTL)
|
||||
int dlg=pTlsData->bCopyMultiFile?(IsLanguageRTL()?IDD_FILEMULTIR:IDD_FILEMULTI):(IsLanguageRTL()?IDD_FILER:IDD_FILE);
|
||||
|
||||
HWND parent=GetWindow(GetAncestor(hWnd,GA_ROOT),GW_OWNER);
|
||||
|
||||
int res=(int)DialogBoxParam(g_Instance,MAKEINTRESOURCE(dlg),parent,DialogProc,(LPARAM)this);
|
||||
|
||||
if (res==IDOK || (res==IDYES && m_bCopyMultiLast))
|
||||
{
|
||||
// Yes was pressed, proceed with the operation
|
||||
m_YesButton.first->accDoDefaultAction(CComVariant(CHILDID_SELF));
|
||||
}
|
||||
else if (res==IDNO)
|
||||
{
|
||||
// No
|
||||
if (m_CheckBox.first && GetKeyState(VK_SHIFT)<0)
|
||||
m_CheckBox.first->accDoDefaultAction(CComVariant(CHILDID_SELF)); // Shift+No = No to All
|
||||
PumpMessages(); // messages need to be pumped after every accessibility action. otherwise the next action doesn't work
|
||||
m_NoButton.first->accDoDefaultAction(CComVariant(CHILDID_SELF));
|
||||
}
|
||||
else if (res==IDYES)
|
||||
{
|
||||
// Yes to All
|
||||
m_CheckBox.first->accDoDefaultAction(CComVariant(CHILDID_SELF));
|
||||
PumpMessages(); // messages need to be pumped after every accessibility action. otherwise the next action doesn't work
|
||||
m_YesButton.first->accDoDefaultAction(CComVariant(CHILDID_SELF));
|
||||
}
|
||||
if (res==IDCANCEL)
|
||||
{
|
||||
// Cancel
|
||||
if (GetKeyState(VK_SHIFT)<0 || GetKeyState(VK_CONTROL)<0)
|
||||
return false; // // Shift+Cancel or Ctrl+Cancel was clicked - show the original dialog box
|
||||
m_Cancel.first->accDoDefaultAction(CComVariant(CHILDID_SELF));
|
||||
}
|
||||
if (res==IDC_LINKMORE)
|
||||
{
|
||||
// More... was clicked - show the original dialog box
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void CClassicCopyFile::PumpMessages( void )
|
||||
{
|
||||
MSG msg;
|
||||
while (PeekMessage(&msg,NULL,0,0,PM_REMOVE))
|
||||
{
|
||||
TranslateMessage(&msg);
|
||||
DispatchMessage(&msg);
|
||||
}
|
||||
}
|
||||
|
||||
void CClassicCopyFile::AddAccChild( IAccessible *pAcc, const VARIANT &id, CString *pLog )
|
||||
{
|
||||
CComVariant state;
|
||||
pAcc->get_accState(id,&state);
|
||||
if (state.intVal&(STATE_SYSTEM_UNAVAILABLE|STATE_SYSTEM_INVISIBLE)) return;
|
||||
CComVariant role;
|
||||
pAcc->get_accRole(id,&role);
|
||||
if (role.intVal==ROLE_SYSTEM_PUSHBUTTON)
|
||||
{
|
||||
CComBSTR name;
|
||||
if (SUCCEEDED(pAcc->get_accName(id,&name)) && name)
|
||||
{
|
||||
if (pLog)
|
||||
LogPrint(pLog,L"button found: '%s', %d\r\n",name,id.intVal);
|
||||
if (_wcsicmp(name,g_ButtonCopy)==0 || _wcsicmp(name,g_ButtonMove)==0)
|
||||
{
|
||||
m_YesButton.first=pAcc;
|
||||
m_YesButton.second=id.intVal;
|
||||
if (pLog)
|
||||
LogPrint(pLog,L"YES button: %p, %d\r\n",pAcc,id.intVal);
|
||||
}
|
||||
else if (_wcsicmp(name,g_ButtonDontCopy)==0 || _wcsicmp(name,g_ButtonDontMove)==0)
|
||||
{
|
||||
m_NoButton.first=pAcc;
|
||||
m_NoButton.second=id.intVal;
|
||||
if (pLog)
|
||||
LogPrint(pLog,L"NO button: %p, %d\r\n",pAcc,id.intVal);
|
||||
}
|
||||
else if (_wcsicmp(name,g_ButtonCancel)==0)
|
||||
{
|
||||
m_Cancel.first=pAcc;
|
||||
m_Cancel.second=id.intVal;
|
||||
if (pLog)
|
||||
LogPrint(pLog,L"CANCEL button: %p, %d\r\n",pAcc,id.intVal);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (role.intVal==ROLE_SYSTEM_CHECKBUTTON)
|
||||
{
|
||||
// hopefully there is only one checkbox
|
||||
m_CheckBox.first=pAcc;
|
||||
m_CheckBox.second=id.intVal;
|
||||
}
|
||||
}
|
||||
|
||||
void CClassicCopyFile::EnumAccChildren( IAccessible *pAcc, CString *pLog )
|
||||
{
|
||||
AddAccChild(pAcc,CComVariant(CHILDID_SELF),pLog);
|
||||
long count;
|
||||
pAcc->get_accChildCount(&count);
|
||||
CComVariant children[20];
|
||||
AccessibleChildren(pAcc,0,count,children,&count);
|
||||
for (int i=0;i<count;i++)
|
||||
{
|
||||
if (children[i].vt==VT_DISPATCH)
|
||||
{
|
||||
CComQIPtr<IAccessible> pChild=children[i].pdispVal;
|
||||
if (pChild)
|
||||
EnumAccChildren(pChild,pLog);
|
||||
}
|
||||
else
|
||||
AddAccChild(pAcc,children[i],pLog);
|
||||
}
|
||||
}
|
||||
|
||||
void CClassicCopyFile::GetFileInfo( IAccessible *pAcc, bool bSrc )
|
||||
{
|
||||
long count;
|
||||
pAcc->get_accChildCount(&count);
|
||||
CComVariant children[20];
|
||||
AccessibleChildren(pAcc,0,count,children,&count);
|
||||
|
||||
wchar_t fname[_MAX_PATH]=L"";
|
||||
wchar_t dir[_MAX_PATH]=L"";
|
||||
CString size;
|
||||
CString date;
|
||||
|
||||
// get the file name, directory, size and date
|
||||
for (int i=0;i<count;i++)
|
||||
{
|
||||
CComBSTR name;
|
||||
if (children[i].vt==VT_DISPATCH)
|
||||
{
|
||||
CComQIPtr<IAccessible> pChild=children[i].pdispVal;
|
||||
if (pChild)
|
||||
pChild->get_accName(CComVariant(CHILDID_SELF),&name);
|
||||
}
|
||||
else
|
||||
{
|
||||
pAcc->get_accName(children[i],&name);
|
||||
}
|
||||
switch (i)
|
||||
{
|
||||
case 2: if (wcslen(name)<_countof(fname)) wcscpy_s(fname,name); break;
|
||||
case 3: if (wcslen(name)<_countof(dir)) wcscpy_s(dir,name); break;
|
||||
case 4: size=name; break;
|
||||
case 5: date=name; break;
|
||||
}
|
||||
}
|
||||
|
||||
if (bSrc)
|
||||
{
|
||||
m_FileName=fname;
|
||||
m_SrcSize=size;
|
||||
m_SrcTime=date;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_DstSize=size;
|
||||
m_DstTime=date;
|
||||
}
|
||||
|
||||
if (!fname[0] || !dir[0]) return;
|
||||
|
||||
wchar_t fname2[_MAX_PATH];
|
||||
memcpy(fname2,fname,sizeof(fname2));
|
||||
*PathFindExtension(fname2)=0;
|
||||
|
||||
int len1=Strlen(fname2);
|
||||
// the directory text is something like "filename (directory)". we need to parse out the real directory name
|
||||
int len2=Strlen(dir);
|
||||
if (dir[0]==0x202A) len1++; // for Arabic the first character is some RTL marker. needs to be skipped
|
||||
if (dir[len1]==0x1E) len1++; // for Hebrew there is an extra control character after the file name
|
||||
if (len1+1>=len2 || dir[len1]!=L' ' || dir[len1+1]!=L'(' || dir[len2-1]!=L')') return;
|
||||
if (dir[len1+2]==0x202A) len1++; // for Hebrew the first character is some RTL marker. needs to be skipped
|
||||
if (dir[len2-2]==0x202C) len2--; // for Hebrew the last character is some RTL marker. needs to be skipped
|
||||
dir[len2-1]=0;
|
||||
|
||||
// construct the full file name
|
||||
wchar_t path[_MAX_PATH];
|
||||
_wmakepath_s(path,NULL,dir+len1+2,fname,NULL);
|
||||
|
||||
if (!bSrc)
|
||||
{
|
||||
DWORD attrib=GetFileAttributes(path);
|
||||
if (attrib!=INVALID_FILE_ATTRIBUTES)
|
||||
{
|
||||
if (attrib&FILE_ATTRIBUTE_READONLY) m_bReadOnly=true;
|
||||
if (attrib&FILE_ATTRIBUTE_SYSTEM) m_bSystem=true;
|
||||
}
|
||||
}
|
||||
|
||||
// get file icon
|
||||
HICON hIcon=NULL;
|
||||
CAbsolutePidl pidl;
|
||||
if (SUCCEEDED(SHParseDisplayName(path,NULL,&pidl,0,NULL)) && pidl)
|
||||
{
|
||||
int iconSize=GetSystemMetrics(SM_CXICON);
|
||||
HBITMAP hBitmap=NULL;
|
||||
CComPtr<IShellItemImageFactory> pFactory;
|
||||
if (SUCCEEDED(SHCreateItemFromIDList(pidl,IID_IShellItemImageFactory,(void**)&pFactory)) && pFactory)
|
||||
{
|
||||
SIZE size={iconSize,iconSize};
|
||||
if (FAILED(pFactory->GetImage(size,SIIGBF_ICONONLY,&hBitmap)))
|
||||
hBitmap=NULL;
|
||||
}
|
||||
|
||||
if (hBitmap)
|
||||
{
|
||||
HBITMAP hMonoBitmap=CreateBitmap(iconSize,iconSize,1,1,NULL);
|
||||
ICONINFO info={TRUE,0,0,hMonoBitmap,hBitmap};
|
||||
hIcon=CreateIconIndirect(&info);
|
||||
DeleteObject(hMonoBitmap);
|
||||
DeleteObject(hBitmap);
|
||||
}
|
||||
}
|
||||
if (!hIcon) return;
|
||||
|
||||
if (bSrc)
|
||||
m_SrcIcon=hIcon;
|
||||
else
|
||||
m_DstIcon=hIcon;
|
||||
}
|
||||
|
||||
const int WM_BRINGFOREGROUND=WM_USER+11;
|
||||
|
||||
INT_PTR CALLBACK CClassicCopyFile::DialogProc( HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam )
|
||||
{
|
||||
if (uMsg==WM_INITDIALOG)
|
||||
{
|
||||
SetWindowText(hwndDlg,FindTranslation(L"Copy.Title",L"Confirm File Replace"));
|
||||
CClassicCopyFile *pThis=(CClassicCopyFile*)lParam;
|
||||
wchar_t text[_MAX_PATH*2];
|
||||
if (pThis->m_bSystem)
|
||||
{
|
||||
Sprintf(text,_countof(text),FindTranslation(L"Copy.SubtitleSys",L"This folder already contains a system file named '%s'."),pThis->m_FileName);
|
||||
if (GetSettingInt(L"OverwriteAlertLevel")>=1)
|
||||
PlaySound(L".Default",NULL,SND_APPLICATION|SND_ALIAS|SND_ASYNC|SND_NODEFAULT|SND_SYSTEM);
|
||||
}
|
||||
else if (pThis->m_bReadOnly)
|
||||
{
|
||||
Sprintf(text,_countof(text),FindTranslation(L"Copy.SubtitleRO",L"This folder already contains a read-only file named '%s'."),pThis->m_FileName);
|
||||
if (GetSettingInt(L"OverwriteAlertLevel")>=2)
|
||||
PlaySound(L".Default",NULL,SND_APPLICATION|SND_ALIAS|SND_ASYNC|SND_NODEFAULT|SND_SYSTEM);
|
||||
}
|
||||
else
|
||||
Sprintf(text,_countof(text),FindTranslation(L"Copy.Subtitle",L"This folder already contains a file named '%s'."),pThis->m_FileName);
|
||||
SetDlgItemText(hwndDlg,IDC_STATICFNAME,text);
|
||||
|
||||
// load icon for file conflict (146) from Shell32.dll
|
||||
HMODULE hShell32=GetModuleHandle(L"Shell32.dll");
|
||||
pThis->m_Icon=LoadIcon(hShell32,MAKEINTRESOURCE(146));
|
||||
if (pThis->m_Icon)
|
||||
SendDlgItemMessage(hwndDlg,IDC_STATICICON1,STM_SETICON,(LPARAM)pThis->m_Icon,0);
|
||||
|
||||
// set the localized text
|
||||
SetDlgItemText(hwndDlg,IDC_STATICPROMPT1,FindTranslation(L"Copy.Prompt1",L"Do you want to replace the existing file:"));
|
||||
SetDlgItemText(hwndDlg,IDC_STATICDSTSIZE,pThis->m_DstSize);
|
||||
SetDlgItemText(hwndDlg,IDC_STATICDSTTIME,pThis->m_DstTime);
|
||||
SetDlgItemText(hwndDlg,IDC_STATICPROMPT2,FindTranslation(L"Copy.Prompt2",L"with this one?"));
|
||||
SendDlgItemMessage(hwndDlg,IDC_STATICDSTICON,STM_SETICON,(LPARAM)pThis->m_DstIcon,0);
|
||||
SetDlgItemText(hwndDlg,IDC_STATICSRCSIZE,pThis->m_SrcSize);
|
||||
SetDlgItemText(hwndDlg,IDC_STATICSRCTIME,pThis->m_SrcTime);
|
||||
SendDlgItemMessage(hwndDlg,IDC_STATICSRCICON,STM_SETICON,(LPARAM)pThis->m_SrcIcon,0);
|
||||
SetDlgItemText(hwndDlg,IDOK,FindTranslation(L"Copy.Yes",L"&Yes"));
|
||||
SetDlgItemText(hwndDlg,IDNO,FindTranslation(L"Copy.No",L"&No"));
|
||||
if (GetDlgItem(hwndDlg,IDYES))
|
||||
SetDlgItemText(hwndDlg,IDYES,FindTranslation(L"Copy.YesAll",L"Yes to &All"));
|
||||
if (GetDlgItem(hwndDlg,IDCANCEL))
|
||||
SetDlgItemText(hwndDlg,IDCANCEL,FindTranslation(L"Copy.Cancel",L"Cancel"));
|
||||
Sprintf(text,_countof(text),L"<a>%s</a>",FindTranslation(L"Copy.More",L"&More..."));
|
||||
SetDlgItemText(hwndDlg,IDC_LINKMORE,text);
|
||||
PostMessage(hwndDlg,WM_BRINGFOREGROUND,0,0);
|
||||
return TRUE;
|
||||
}
|
||||
if (uMsg==WM_BRINGFOREGROUND)
|
||||
{
|
||||
// bring window to front (sometimes on Windows7 it shows up behind Explorer)
|
||||
SetForegroundWindow(hwndDlg);
|
||||
return TRUE;
|
||||
}
|
||||
if (uMsg==WM_COMMAND && (wParam==IDOK || wParam==IDYES || wParam==IDNO || wParam==IDCANCEL))
|
||||
{
|
||||
EndDialog(hwndDlg,wParam);
|
||||
return TRUE;
|
||||
}
|
||||
if (uMsg==WM_NOTIFY)
|
||||
{
|
||||
NMHDR *pHdr=(NMHDR*)lParam;
|
||||
if (pHdr->idFrom==IDC_LINKMORE && (pHdr->code==NM_CLICK || pHdr->code==NM_RETURN))
|
||||
{
|
||||
EndDialog(hwndDlg,IDC_LINKMORE);
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// CClassicCopyFolder - this is the implementation of the Copy UI dialog box for folders
|
||||
|
||||
class CClassicCopyFolder
|
||||
{
|
||||
public:
|
||||
CClassicCopyFolder( void ) { m_Icon=NULL; m_Original=NULL; }
|
||||
~CClassicCopyFolder( void );
|
||||
|
||||
bool Run( HWND hWnd );
|
||||
|
||||
private:
|
||||
HICON m_Icon;
|
||||
HWND m_Original;
|
||||
|
||||
static INT_PTR CALLBACK DialogProc( HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam );
|
||||
};
|
||||
|
||||
CClassicCopyFolder::~CClassicCopyFolder( void )
|
||||
{
|
||||
if (m_Icon) DestroyIcon(m_Icon);
|
||||
}
|
||||
|
||||
// Show the dialog box. Returns true to suppress the original task dialog box
|
||||
bool CClassicCopyFolder::Run( HWND hWnd )
|
||||
{
|
||||
m_Original=hWnd;
|
||||
const int ID_ALLCHECK=16663;
|
||||
HWND check=GetDlgItem(hWnd,ID_ALLCHECK);
|
||||
bool bMulti=(check && (GetWindowLong(check,GWL_STYLE)&WS_VISIBLE));
|
||||
// pick the correct dialog template (for single and multiple files, for LTR and RTL)
|
||||
int dlg=bMulti?(IsLanguageRTL()?IDD_FOLDERMULTIR:IDD_FOLDERMULTI):(IsLanguageRTL()?IDD_FOLDERR:IDD_FOLDER);
|
||||
|
||||
HWND parent=GetWindow(GetAncestor(hWnd,GA_ROOT),GW_OWNER);
|
||||
|
||||
int res=(int)DialogBoxParam(g_Instance,MAKEINTRESOURCE(dlg),parent,DialogProc,(LPARAM)this);
|
||||
|
||||
if (res==IDOK) // Yes button for single folder
|
||||
{
|
||||
// Yes was pressed, proceed with the operation
|
||||
PostMessage(hWnd,WM_COMMAND,IDYES,(LPARAM)GetDlgItem(hWnd,IDYES));
|
||||
}
|
||||
else if (res==IDNO)
|
||||
{
|
||||
// No
|
||||
if (bMulti)
|
||||
{
|
||||
if (GetKeyState(VK_SHIFT)<0)
|
||||
{
|
||||
CheckDlgButton(hWnd,ID_ALLCHECK,BST_CHECKED);
|
||||
SendMessage(hWnd,WM_COMMAND,ID_ALLCHECK,(LPARAM)check);
|
||||
}
|
||||
PostMessage(hWnd,WM_COMMAND,IDNO,(LPARAM)GetDlgItem(hWnd,IDNO)); // Skip
|
||||
}
|
||||
else
|
||||
PostMessage(hWnd,WM_COMMAND,IDCANCEL,(LPARAM)GetDlgItem(hWnd,IDCANCEL)); // No
|
||||
}
|
||||
else if (res==IDYES)
|
||||
{
|
||||
// Yes to All
|
||||
CheckDlgButton(hWnd,ID_ALLCHECK,BST_CHECKED);
|
||||
SendMessage(hWnd,WM_COMMAND,ID_ALLCHECK,(LPARAM)check);
|
||||
PostMessage(hWnd,WM_COMMAND,IDYES,(LPARAM)GetDlgItem(hWnd,IDYES));
|
||||
}
|
||||
if (res==IDCANCEL)
|
||||
{
|
||||
// Cancel
|
||||
if (GetKeyState(VK_SHIFT)<0 || GetKeyState(VK_CONTROL)<0)
|
||||
return false; // // Shift+Cancel or Ctrl+Cancel was clicked - show the original dialog box
|
||||
PostMessage(hWnd,WM_COMMAND,IDCANCEL,(LPARAM)GetDlgItem(hWnd,IDCANCEL)); // No
|
||||
}
|
||||
if (res==IDC_LINKMORE)
|
||||
{
|
||||
// More... was clicked - show the original dialog box
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
INT_PTR CALLBACK CClassicCopyFolder::DialogProc( HWND hwndDlg, UINT uMsg, WPARAM wParam, LPARAM lParam )
|
||||
{
|
||||
if (uMsg==WM_INITDIALOG)
|
||||
{
|
||||
SetWindowText(hwndDlg,FindTranslation(L"Folder.Title",L"Confirm Folder Replace"));
|
||||
CClassicCopyFolder *pThis=(CClassicCopyFolder*)lParam;
|
||||
wchar_t text[2048];
|
||||
// find the link control and get its text
|
||||
HWND link=FindWindowEx(pThis->m_Original,NULL,WC_LINK,NULL);
|
||||
if (link)
|
||||
GetWindowText(link,text,_countof(text));
|
||||
else
|
||||
text[0]=0;
|
||||
Strcat(text,_countof(text),L"\r\n\r\n");
|
||||
Strcat(text,_countof(text),FindTranslation(L"Folder.Prompt",L"Do you still want to move or copy the folder?"));
|
||||
SetDlgItemText(hwndDlg,IDC_STATICFNAME,text);
|
||||
|
||||
// load icon for file conflict (146) from Shell32.dll
|
||||
HMODULE hShell32=GetModuleHandle(L"Shell32.dll");
|
||||
pThis->m_Icon=LoadIcon(hShell32,MAKEINTRESOURCE(146));
|
||||
if (pThis->m_Icon)
|
||||
SendDlgItemMessage(hwndDlg,IDC_STATICICON1,STM_SETICON,(LPARAM)pThis->m_Icon,0);
|
||||
|
||||
// set the localized text
|
||||
SetDlgItemText(hwndDlg,IDOK,FindTranslation(L"Copy.Yes",L"&Yes"));
|
||||
SetDlgItemText(hwndDlg,IDNO,FindTranslation(L"Copy.No",L"&No"));
|
||||
if (GetDlgItem(hwndDlg,IDYES))
|
||||
SetDlgItemText(hwndDlg,IDYES,FindTranslation(L"Copy.YesAll",L"Yes to &All"));
|
||||
if (GetDlgItem(hwndDlg,IDCANCEL))
|
||||
SetDlgItemText(hwndDlg,IDCANCEL,FindTranslation(L"Copy.Cancel",L"Cancel"));
|
||||
Sprintf(text,_countof(text),L"<a>%s</a>",FindTranslation(L"Copy.More",L"&More..."));
|
||||
SetDlgItemText(hwndDlg,IDC_LINKMORE,text);
|
||||
PostMessage(hwndDlg,WM_BRINGFOREGROUND,0,0);
|
||||
return TRUE;
|
||||
}
|
||||
if (uMsg==WM_BRINGFOREGROUND)
|
||||
{
|
||||
// bring window to front (sometimes on Windows7 it shows up behind Explorer)
|
||||
SetForegroundWindow(hwndDlg);
|
||||
return TRUE;
|
||||
}
|
||||
if (uMsg==WM_COMMAND && (wParam==IDOK || wParam==IDYES || wParam==IDNO || wParam==IDCANCEL))
|
||||
{
|
||||
EndDialog(hwndDlg,wParam);
|
||||
return TRUE;
|
||||
}
|
||||
if (uMsg==WM_NOTIFY)
|
||||
{
|
||||
NMHDR *pHdr=(NMHDR*)lParam;
|
||||
if (pHdr->idFrom==IDC_LINKMORE && (pHdr->code==NM_CLICK || pHdr->code==NM_RETURN))
|
||||
{
|
||||
EndDialog(hwndDlg,IDC_LINKMORE);
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static CComPtr<IAccessible> FindMoreButton( IAccessible *pAcc )
|
||||
{
|
||||
CComVariant state;
|
||||
CComVariant self(CHILDID_SELF);
|
||||
pAcc->get_accState(self,&state);
|
||||
if (!(state.intVal&(STATE_SYSTEM_UNAVAILABLE|STATE_SYSTEM_INVISIBLE)))
|
||||
{
|
||||
CComVariant role;
|
||||
pAcc->get_accRole(self,&role);
|
||||
if (role.intVal==ROLE_SYSTEM_PUSHBUTTON)
|
||||
{
|
||||
CComBSTR name;
|
||||
if (SUCCEEDED(pAcc->get_accName(self,&name)) && name && _wcsicmp(name,g_ButtonMore)==0)
|
||||
return pAcc;
|
||||
}
|
||||
}
|
||||
|
||||
CComVariant children[30];
|
||||
long count;
|
||||
AccessibleChildren(pAcc,0,_countof(children),children,&count);
|
||||
for (int i=0;i<count;i++)
|
||||
{
|
||||
if (children[i].vt==VT_DISPATCH)
|
||||
{
|
||||
CComQIPtr<IAccessible> pChild=children[i].pdispVal;
|
||||
if (pChild)
|
||||
{
|
||||
CComPtr<IAccessible> pRes=FindMoreButton(pChild);
|
||||
if (pRes) return pRes;
|
||||
}
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static LRESULT CALLBACK WindowProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData )
|
||||
{
|
||||
if (uMsg==WM_WINDOWPOSCHANGING)
|
||||
{
|
||||
WINDOWPOS *pos=(WINDOWPOS*)lParam;
|
||||
if (pos->flags&SWP_SHOWWINDOW)
|
||||
{
|
||||
wchar_t title[256];
|
||||
GetWindowText(hWnd,title,_countof(title));
|
||||
|
||||
if (_wcsicmp(title,g_TitleMove)==0 || _wcsicmp(title,g_TitleCopy)==0)
|
||||
{
|
||||
// file UI
|
||||
if (GetSettingBool(L"ReplaceFileUI"))
|
||||
{
|
||||
CString log;
|
||||
CComPtr<IAccessible> pAcc;
|
||||
HRESULT h=AccessibleObjectFromWindow(hWnd,OBJID_WINDOW,IID_IAccessible,(void**)&pAcc);
|
||||
if (SUCCEEDED(h) && pAcc)
|
||||
{
|
||||
CClassicCopyFile copy;
|
||||
if (copy.Run(hWnd,pAcc,g_bLogLevel?&log:NULL))
|
||||
{
|
||||
pos->x=pos->y=-20000;
|
||||
pos->flags&=~(SWP_SHOWWINDOW|SWP_NOMOVE);
|
||||
}
|
||||
}
|
||||
else if (g_bLogLevel)
|
||||
LogPrint(&log,L"AccessibleObjectFromWindow: error=0x%X, hWnd=0x%p",h,hWnd);
|
||||
|
||||
if (g_bLogLevel)
|
||||
{
|
||||
wchar_t fname[_MAX_PATH]=L"%LOCALAPPDATA%\\OpenShell";
|
||||
DoEnvironmentSubst(fname,_MAX_PATH);
|
||||
SHCreateDirectory(NULL,fname);
|
||||
Strcat(fname,_countof(fname),L"\\ExplorerLog.txt");
|
||||
if (!log.IsEmpty())
|
||||
{
|
||||
FILE *f;
|
||||
if (_wfopen_s(&f,fname,L"wb")==0)
|
||||
{
|
||||
fwprintf(f,L"\xFEFF");
|
||||
|
||||
OSVERSIONINFOEX ver={sizeof(ver)};
|
||||
#pragma warning(suppress:4996)
|
||||
GetVersionEx((OSVERSIONINFO*)&ver);
|
||||
fwprintf(f,L"version = %d.%d.%d - %d.%d\r\n\r\n",ver.dwMajorVersion,ver.dwMinorVersion,ver.dwBuildNumber,ver.wServicePackMajor,ver.wServicePackMinor);
|
||||
|
||||
wchar_t languages[100]={0};
|
||||
ULONG size=4; // up to 4 languages
|
||||
ULONG len=_countof(languages);
|
||||
GetUserPreferredUILanguages(MUI_LANGUAGE_NAME,&size,languages,&len);
|
||||
for (const wchar_t *lang=languages;*lang;lang+=wcslen(lang)+1)
|
||||
fwprintf(f,L"language = %s\r\n",lang);
|
||||
|
||||
fwprintf(f,L"\r\n");
|
||||
fwprintf(f,L"g_ButtonMove = '%s'\r\n",g_ButtonMove);
|
||||
fwprintf(f,L"g_ButtonDontMove = '%s'\r\n",g_ButtonDontMove);
|
||||
fwprintf(f,L"g_ButtonCopy = '%s'\r\n",g_ButtonCopy);
|
||||
fwprintf(f,L"g_ButtonDontCopy = '%s'\r\n",g_ButtonDontCopy);
|
||||
fwprintf(f,L"g_ButtonCancel = '%s'\r\n",g_ButtonCancel);
|
||||
fwprintf(f,L"\r\n");
|
||||
|
||||
fwrite((const wchar_t*)log,log.GetLength(),2,f);
|
||||
fclose(f);
|
||||
}
|
||||
}
|
||||
else
|
||||
DeleteFile(fname);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (_wcsicmp(title,g_TitleFolder)==0)
|
||||
{
|
||||
// folder UI
|
||||
if (GetSettingBool(L"ReplaceFolderUI"))
|
||||
{
|
||||
CClassicCopyFolder copy;
|
||||
if (copy.Run(hWnd))
|
||||
{
|
||||
pos->x=pos->y=-20000;
|
||||
pos->flags&=~(SWP_SHOWWINDOW|SWP_NOMOVE);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// look for progress bar
|
||||
if (GetSettingBool(L"EnableMore"))
|
||||
{
|
||||
HWND progress=FindChildWindow(hWnd,PROGRESS_CLASS);
|
||||
if (progress)
|
||||
{
|
||||
bool bDef;
|
||||
int delay=GetSettingInt(L"MoreProgressDelay",bDef);
|
||||
if (bDef)
|
||||
{
|
||||
delay=0;
|
||||
if (GetWinVersion()>=WIN_VER_WIN7)
|
||||
{
|
||||
BOOL comp;
|
||||
if (SUCCEEDED(DwmIsCompositionEnabled(&comp)) && comp)
|
||||
delay=500;
|
||||
}
|
||||
}
|
||||
SetTimer(hWnd,'CLEX',delay,NULL);
|
||||
return DefSubclassProc(hWnd,uMsg,wParam,lParam);
|
||||
}
|
||||
}
|
||||
}
|
||||
LRESULT res=DefSubclassProc(hWnd,uMsg,wParam,lParam);
|
||||
RemoveWindowSubclass(hWnd,WindowProc,uIdSubclass);
|
||||
return res;
|
||||
}
|
||||
}
|
||||
if (uMsg==WM_TIMER && wParam=='CLEX')
|
||||
{
|
||||
KillTimer(hWnd,wParam);
|
||||
|
||||
CComPtr<IAccessible> pAcc;
|
||||
HRESULT h=AccessibleObjectFromWindow(hWnd,OBJID_WINDOW,IID_IAccessible,(void**)&pAcc);
|
||||
if (SUCCEEDED(h) && pAcc)
|
||||
{
|
||||
CComPtr<IAccessible> pMore=FindMoreButton(pAcc);
|
||||
if (pMore) pMore->accDoDefaultAction(CComVariant(CHILDID_SELF));
|
||||
}
|
||||
|
||||
LRESULT res=DefSubclassProc(hWnd,uMsg,wParam,lParam);
|
||||
RemoveWindowSubclass(hWnd,WindowProc,uIdSubclass);
|
||||
return res;
|
||||
}
|
||||
return DefSubclassProc(hWnd,uMsg,wParam,lParam);
|
||||
}
|
||||
|
||||
LRESULT CALLBACK ClassicCopyHook( int nCode, WPARAM wParam, LPARAM lParam )
|
||||
{
|
||||
if (nCode==HCBT_CREATEWND)
|
||||
{
|
||||
HWND hWnd=(HWND)wParam;
|
||||
CBT_CREATEWND *create=(CBT_CREATEWND*)lParam;
|
||||
HINSTANCE hInst=(HINSTANCE)GetWindowLongPtr(hWnd,GWLP_HINSTANCE);
|
||||
if (create->lpcs->lpszName && (intptr_t)create->lpcs->lpszClass==32770 && hInst==g_hShell32)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
static LONG id;
|
||||
int i=InterlockedIncrement(&id);
|
||||
SetWindowSubclass(hWnd,WindowProc,i,0);
|
||||
}
|
||||
}
|
||||
TlsData *pTlsData=GetTlsData();
|
||||
return CallNextHookEx(pTlsData->copyHook,nCode,wParam,lParam);
|
||||
}
|
||||
|
||||
void InitClassicCopyProcess( void )
|
||||
{
|
||||
// load UI text from shell32.dll
|
||||
// the text is used to locate controls in the copy dialog by name
|
||||
g_hShell32=GetModuleHandle(L"shell32.dll");
|
||||
LoadString(g_hShell32,17027,g_TitleMove,256);
|
||||
LoadString(g_hShell32,17024,g_TitleCopy,256);
|
||||
LoadString(g_hShell32,16705,g_TitleFolder,256);
|
||||
LoadString(g_hShell32,13610,g_ButtonMove,256);
|
||||
LoadString(g_hShell32,13623,g_ButtonDontMove,256);
|
||||
LoadString(g_hShell32,13604,g_ButtonCopy,256);
|
||||
LoadString(g_hShell32,13606,g_ButtonDontCopy,256);
|
||||
LoadString(g_hShell32,13588,g_ButtonCancel,256);
|
||||
LoadString(g_hShell32,32992,g_ButtonMore,256);
|
||||
}
|
||||
|
||||
void InitClassicCopyThread( void )
|
||||
{
|
||||
TlsData *pTlsData=GetTlsData();
|
||||
if (!pTlsData->copyHook)
|
||||
pTlsData->copyHook=SetWindowsHookEx(WH_CBT,ClassicCopyHook,g_Instance,GetCurrentThreadId());
|
||||
}
|
||||
|
||||
void FreeClassicCopyThread( void )
|
||||
{
|
||||
TlsData *pTlsData=GetTlsData();
|
||||
if (pTlsData->copyHook)
|
||||
{
|
||||
UnhookWindowsHookEx(pTlsData->copyHook);
|
||||
pTlsData->copyHook=NULL;
|
||||
}
|
||||
}
|
||||
44
Src/ClassicExplorer/ClassicCopyExt.cpp
Normal file
@@ -0,0 +1,44 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// ClassicCopyExt.cpp : Implementation of CClassicCopyExt
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ClassicCopyExt.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "dllmain.h"
|
||||
|
||||
|
||||
// CClassicCopyExt - this is a dummy drag and drop handler. Its purpose is to get Explorer to load the DLL when
|
||||
// a file is being copied or moved.
|
||||
|
||||
void InitClassicCopyThread( void );
|
||||
|
||||
STDMETHODIMP CClassicCopyExt::Initialize( PCIDLIST_ABSOLUTE pidlFolder, LPDATAOBJECT pDataObj, HKEY hProgID )
|
||||
{
|
||||
InitClassicCopyThread();
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CClassicCopyExt::QueryContextMenu( HMENU hmenu, UINT uMenuIndex, UINT uidFirstCmd, UINT uidLastCmd, UINT uFlags )
|
||||
{
|
||||
return MAKE_HRESULT(SEVERITY_SUCCESS,FACILITY_NULL,0);
|
||||
}
|
||||
|
||||
STDMETHODIMP CClassicCopyExt::GetCommandString( UINT_PTR idCmd, UINT uFlags, UINT* pwReserved, LPSTR pszName, UINT cchMax )
|
||||
{
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
STDMETHODIMP CClassicCopyExt::InvokeCommand( LPCMINVOKECOMMANDINFO pCmdInfo )
|
||||
{
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
HRESULT WINAPI CClassicCopyExt::UpdateRegistry( BOOL bRegister )
|
||||
{
|
||||
if (GetWinVersion()>=WIN_VER_WIN8)
|
||||
return S_OK;
|
||||
return _AtlModule.UpdateRegistryFromResource(IDR_CLASSICCOPYEXT,bRegister);
|
||||
}
|
||||
59
Src/ClassicExplorer/ClassicCopyExt.h
Normal file
@@ -0,0 +1,59 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// ClassicCopyExt.h : Declaration of the CClassicCopyExt
|
||||
|
||||
#pragma once
|
||||
#include "resource.h" // main symbols
|
||||
|
||||
#include "ClassicExplorer_h.h"
|
||||
#include <vector>
|
||||
|
||||
// CClassicCopyExt
|
||||
|
||||
class ATL_NO_VTABLE CClassicCopyExt :
|
||||
public CComObjectRootEx<CComSingleThreadModel>,
|
||||
public CComCoClass<CClassicCopyExt, &CLSID_ClassicCopyExt>,
|
||||
public IShellExtInit,
|
||||
public IContextMenu
|
||||
|
||||
{
|
||||
public:
|
||||
CClassicCopyExt()
|
||||
{
|
||||
}
|
||||
|
||||
static HRESULT WINAPI UpdateRegistry( BOOL bRegister );
|
||||
|
||||
DECLARE_NOT_AGGREGATABLE(CClassicCopyExt)
|
||||
|
||||
BEGIN_COM_MAP(CClassicCopyExt)
|
||||
COM_INTERFACE_ENTRY(IShellExtInit)
|
||||
COM_INTERFACE_ENTRY(IContextMenu)
|
||||
END_COM_MAP()
|
||||
|
||||
|
||||
|
||||
DECLARE_PROTECT_FINAL_CONSTRUCT()
|
||||
|
||||
HRESULT FinalConstruct()
|
||||
{
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
void FinalRelease()
|
||||
{
|
||||
}
|
||||
|
||||
public:
|
||||
// IShellExtInit
|
||||
STDMETHODIMP Initialize(PCIDLIST_ABSOLUTE, LPDATAOBJECT, HKEY);
|
||||
|
||||
// IContextMenu
|
||||
STDMETHODIMP GetCommandString(UINT_PTR, UINT, UINT*, LPSTR, UINT);
|
||||
STDMETHODIMP InvokeCommand(LPCMINVOKECOMMANDINFO);
|
||||
STDMETHODIMP QueryContextMenu(HMENU, UINT, UINT, UINT, UINT);
|
||||
};
|
||||
|
||||
OBJECT_ENTRY_AUTO(__uuidof(ClassicCopyExt), CClassicCopyExt)
|
||||
58
Src/ClassicExplorer/ClassicCopyExt.rgs
Normal file
@@ -0,0 +1,58 @@
|
||||
HKCR
|
||||
{
|
||||
ClassicExplorer.ClassicCopyExt.1 = s 'ClassicCopyExt Class'
|
||||
{
|
||||
CLSID = s '{8C83ACB1-75C3-45D2-882C-EFA32333491C}'
|
||||
}
|
||||
ClassicExplorer.ClassicCopyExt = s 'ClassicCopyExt Class'
|
||||
{
|
||||
CLSID = s '{8C83ACB1-75C3-45D2-882C-EFA32333491C}'
|
||||
CurVer = s 'ClassicExplorer.ClassicCopyExt.1'
|
||||
}
|
||||
NoRemove CLSID
|
||||
{
|
||||
ForceRemove {8C83ACB1-75C3-45D2-882C-EFA32333491C} = s 'ClassicCopyExt Class'
|
||||
{
|
||||
ProgID = s 'ClassicExplorer.ClassicCopyExt.1'
|
||||
VersionIndependentProgID = s 'ClassicExplorer.ClassicCopyExt'
|
||||
ForceRemove 'Programmable'
|
||||
InprocServer32 = s '%MODULE%'
|
||||
{
|
||||
val ThreadingModel = s 'Apartment'
|
||||
}
|
||||
'TypeLib' = s '{BF8D124A-A4E0-402F-8152-4EF377E62586}'
|
||||
}
|
||||
}
|
||||
|
||||
NoRemove Directory
|
||||
{
|
||||
NoRemove shellex
|
||||
{
|
||||
NoRemove DragDropHandlers
|
||||
{
|
||||
ForceRemove ClassicCopyExt = s '{8C83ACB1-75C3-45D2-882C-EFA32333491C}'
|
||||
}
|
||||
}
|
||||
}
|
||||
NoRemove Drive
|
||||
{
|
||||
NoRemove shellex
|
||||
{
|
||||
NoRemove DragDropHandlers
|
||||
{
|
||||
ForceRemove ClassicCopyExt = s '{8C83ACB1-75C3-45D2-882C-EFA32333491C}'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
NoRemove Folder
|
||||
{
|
||||
NoRemove shellex
|
||||
{
|
||||
NoRemove DragDropHandlers
|
||||
{
|
||||
ForceRemove ClassicCopyExt = s '{8C83ACB1-75C3-45D2-882C-EFA32333491C}'
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
91
Src/ClassicExplorer/ClassicExplorer.cpp
Normal file
@@ -0,0 +1,91 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// ClassicExplorer.cpp : Implementation of DLL Exports.
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "resource.h"
|
||||
#include "ClassicExplorer_h.h"
|
||||
#include "dllmain.h"
|
||||
|
||||
// Used to determine whether the DLL can be unloaded by OLE
|
||||
STDAPI DllCanUnloadNow(void)
|
||||
{
|
||||
return _AtlModule.DllCanUnloadNow();
|
||||
}
|
||||
|
||||
extern bool g_bExplorerExe;
|
||||
|
||||
// Returns a class factory to create an object of the requested type
|
||||
STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID* ppv)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
if (!g_bExplorerExe && rclsid!=CLSID_ShareOverlay)
|
||||
return CLASS_E_CLASSNOTAVAILABLE;
|
||||
return _AtlModule.DllGetClassObject(rclsid, riid, ppv);
|
||||
}
|
||||
|
||||
|
||||
// DllRegisterServer - Adds entries to the system registry
|
||||
STDAPI DllRegisterServer(void)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
// registers object, typelib and all interfaces in typelib
|
||||
HRESULT res=_AtlModule.DllRegisterServer();
|
||||
if (SUCCEEDED(res))
|
||||
{
|
||||
// mark the extensions as compatible with the enhanced protected mode of IE10
|
||||
// they are not technically IE extensions, but it complains about them as
|
||||
// being incompatible
|
||||
CComPtr<ICatRegister> catRegister;
|
||||
catRegister.CoCreateInstance(CLSID_StdComponentCategoriesMgr);
|
||||
if (catRegister)
|
||||
{
|
||||
CATID CATID_AppContainerCompatible={0x59fb2056,0xd625,0x48d0,{0xa9,0x44,0x1a,0x85,0xb5,0xab,0x26,0x40}};
|
||||
catRegister->RegisterClassImplCategories(CLSID_ExplorerBHO,1,&CATID_AppContainerCompatible);
|
||||
catRegister->RegisterClassImplCategories(CLSID_ExplorerBand,1,&CATID_AppContainerCompatible);
|
||||
}
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
// DllUnregisterServer - Removes entries from the system registry
|
||||
STDAPI DllUnregisterServer(void)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
return _AtlModule.DllUnregisterServer();
|
||||
}
|
||||
|
||||
// DllInstall - Adds/Removes entries to the system registry per user
|
||||
// per machine.
|
||||
STDAPI DllInstall(BOOL bInstall, LPCWSTR pszCmdLine)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
HRESULT hr = E_FAIL;
|
||||
static const wchar_t szUserSwitch[] = L"user";
|
||||
|
||||
if (pszCmdLine != NULL)
|
||||
{
|
||||
if (_wcsnicmp(pszCmdLine, szUserSwitch, _countof(szUserSwitch)) == 0)
|
||||
{
|
||||
AtlSetPerUserRegistration(true);
|
||||
}
|
||||
}
|
||||
|
||||
if (bInstall)
|
||||
{
|
||||
hr = DllRegisterServer();
|
||||
if (FAILED(hr))
|
||||
{
|
||||
DllUnregisterServer();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
hr = DllUnregisterServer();
|
||||
}
|
||||
|
||||
return hr;
|
||||
}
|
||||
90
Src/ClassicExplorer/ClassicExplorer.idl
Normal file
@@ -0,0 +1,90 @@
|
||||
// ClassicExplorer.idl : IDL source for ClassicExplorer
|
||||
//
|
||||
|
||||
// This file will be processed by the MIDL tool to
|
||||
// produce the type library (ClassicExplorer.tlb) and marshalling code.
|
||||
|
||||
import "oaidl.idl";
|
||||
import "ocidl.idl";
|
||||
|
||||
[
|
||||
object,
|
||||
uuid(BC4C1B8F-0BDE-4E42-9583-E072B2A28E0D),
|
||||
dual,
|
||||
nonextensible,
|
||||
helpstring("IExplorerBand Interface"),
|
||||
pointer_default(unique)
|
||||
]
|
||||
interface IExplorerBand : IDispatch{
|
||||
};
|
||||
[
|
||||
object,
|
||||
uuid(6E00B97F-A4D4-4062-98E4-4F66FC96F32F),
|
||||
dual,
|
||||
nonextensible,
|
||||
helpstring("IClassicCopyExt Interface"),
|
||||
pointer_default(unique)
|
||||
]
|
||||
interface IClassicCopyExt : IDispatch{
|
||||
};
|
||||
[
|
||||
object,
|
||||
uuid(A1678625-A011-4B7C-A1FA-D691E4CDDB79),
|
||||
dual,
|
||||
nonextensible,
|
||||
helpstring("IExplorerBHO Interface"),
|
||||
pointer_default(unique)
|
||||
]
|
||||
interface IExplorerBHO : IDispatch{
|
||||
};
|
||||
[
|
||||
object,
|
||||
uuid(2576496C-B58A-4995-8878-8B68F9E8D1FC),
|
||||
dual,
|
||||
nonextensible,
|
||||
helpstring("IShareOverlay Interface"),
|
||||
pointer_default(unique)
|
||||
]
|
||||
interface IShareOverlay : IDispatch{
|
||||
};
|
||||
[
|
||||
uuid(BF8D124A-A4E0-402F-8152-4EF377E62586),
|
||||
version(1.0),
|
||||
helpstring("ClassicExplorer 1.0 Type Library")
|
||||
]
|
||||
library ClassicExplorerLib
|
||||
{
|
||||
importlib("stdole2.tlb");
|
||||
[
|
||||
uuid(553891B7-A0D5-4526-BE18-D3CE461D6310),
|
||||
helpstring("ExplorerBand Class")
|
||||
]
|
||||
coclass ExplorerBand
|
||||
{
|
||||
[default] interface IExplorerBand;
|
||||
};
|
||||
[
|
||||
uuid(8C83ACB1-75C3-45D2-882C-EFA32333491C),
|
||||
helpstring("ClassicCopyExt Class")
|
||||
]
|
||||
coclass ClassicCopyExt
|
||||
{
|
||||
[default] interface IClassicCopyExt;
|
||||
};
|
||||
[
|
||||
uuid(449D0D6E-2412-4E61-B68F-1CB625CD9E52),
|
||||
helpstring("ExplorerBHO Class")
|
||||
]
|
||||
coclass ExplorerBHO
|
||||
{
|
||||
[default] interface IExplorerBHO;
|
||||
};
|
||||
[
|
||||
uuid(594D4122-1F87-41E2-96C7-825FB4796516),
|
||||
helpstring("ShareOverlay Class")
|
||||
]
|
||||
coclass ShareOverlay
|
||||
{
|
||||
[default] interface IShareOverlay;
|
||||
};
|
||||
};
|
||||
676
Src/ClassicExplorer/ClassicExplorer.rc
Normal file
@@ -0,0 +1,676 @@
|
||||
// Microsoft Visual C++ generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
#define APSTUDIO_READONLY_SYMBOLS
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#include "windows.h"
|
||||
#include "winres.h"
|
||||
#include "..\Lib\resource.h"
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
|
||||
#pragma code_page(1252)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#include ""afxres.h""\r\n"
|
||||
"#include ""..\\Lib\\resource.h""\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#include ""..\\Lib\\resource.h""\r\n"
|
||||
"#include ""..\\Lib\\Lib.rc""\r\n"
|
||||
"1 TYPELIB ""ClassicExplorer.tlb""\r\0"
|
||||
END
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#include ""afxres.h""\r\n"
|
||||
"#include ""..\\Lib\\resource.h""\r\n"
|
||||
"#include ""..\\Lib\\Lib.rc""\r\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"\r\0"
|
||||
END
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#ifndef APSTUDIO_INVOKED\r\n"
|
||||
"#include ""targetver.h""\r\n"
|
||||
"#endif\r\n"
|
||||
"#include ""winres.h""\r\n"
|
||||
"#include ""..\\Lib\\resource.h""\r\n"
|
||||
"#include ""..\\Lib\\Lib.rc""\r\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"1 TYPELIB ""ClassicExplorer.tlb""\r\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Dialog
|
||||
//
|
||||
|
||||
IDD_FILE DIALOGEX 0, 0, 266, 136
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
CAPTION "Confirm File Replace"
|
||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "&Yes",IDOK,149,115,53,14
|
||||
PUSHBUTTON "&No",IDNO,206,115,53,14
|
||||
ICON "",IDC_STATICICON1,7,7,20,20
|
||||
LTEXT "This folder already contains a file called 'blah.txt'.",IDC_STATICFNAME,35,7,224,23,SS_NOPREFIX
|
||||
LTEXT "Do you want to replace the existing file:",IDC_STATICPROMPT1,35,34,224,8,SS_NOPREFIX
|
||||
ICON "",IDC_STATICDSTICON,43,46,20,20
|
||||
LTEXT "Static",IDC_STATICDSTSIZE,69,47,190,8,SS_NOPREFIX
|
||||
LTEXT "Static",IDC_STATICDSTTIME,69,57,190,8,SS_NOPREFIX
|
||||
LTEXT "with this one?",IDC_STATICPROMPT2,35,74,224,8,SS_NOPREFIX
|
||||
ICON "",IDC_STATICSRCICON,43,86,20,20
|
||||
LTEXT "Static",IDC_STATICSRCSIZE,69,87,190,8,SS_NOPREFIX
|
||||
LTEXT "Static",IDC_STATICSRCTIME,69,97,190,8,SS_NOPREFIX
|
||||
CONTROL "<a>&More...</a>",IDC_LINKMORE,"SysLink",WS_TABSTOP,7,120,57,10
|
||||
END
|
||||
|
||||
IDD_FILEMULTI DIALOGEX 0, 0, 285, 136
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
CAPTION "Confirm File Replace"
|
||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "&Yes",IDOK,55,115,53,14
|
||||
PUSHBUTTON "Yes to &All",IDYES,112,115,53,14
|
||||
PUSHBUTTON "&No",IDNO,169,115,53,14
|
||||
PUSHBUTTON "Cancel",IDCANCEL,226,115,53,14
|
||||
ICON "",IDC_STATICICON1,7,7,20,20
|
||||
LTEXT "This folder already contains a file called 'blah.txt'.",IDC_STATICFNAME,35,7,243,23,SS_NOPREFIX
|
||||
LTEXT "Do you want to replace the existing file:",IDC_STATICPROMPT1,35,34,243,8,SS_NOPREFIX
|
||||
ICON "",IDC_STATICDSTICON,43,46,20,20
|
||||
LTEXT "Static",IDC_STATICDSTSIZE,69,47,209,8,SS_NOPREFIX
|
||||
LTEXT "Static",IDC_STATICDSTTIME,69,57,209,8,SS_NOPREFIX
|
||||
LTEXT "with this one?",IDC_STATICPROMPT2,35,74,243,8,SS_NOPREFIX
|
||||
ICON "",IDC_STATICSRCICON,43,86,20,20
|
||||
LTEXT "Static",IDC_STATICSRCSIZE,69,87,209,8,SS_NOPREFIX
|
||||
LTEXT "Static",IDC_STATICSRCTIME,69,97,209,8,SS_NOPREFIX
|
||||
CONTROL "<a>&More...</a>",IDC_LINKMORE,"SysLink",WS_TABSTOP,7,120,45,10
|
||||
END
|
||||
|
||||
IDD_FILEMULTIR DIALOGEX 0, 0, 285, 136
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
EXSTYLE WS_EX_LAYOUTRTL
|
||||
CAPTION "Confirm File Replace"
|
||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "&Yes",IDOK,55,115,53,14
|
||||
PUSHBUTTON "Yes to &All",IDYES,112,115,53,14
|
||||
PUSHBUTTON "&No",IDNO,169,115,53,14
|
||||
PUSHBUTTON "Cancel",IDCANCEL,226,115,53,14
|
||||
ICON "",IDC_STATICICON1,7,7,20,20
|
||||
LTEXT "This folder already contains a file called 'blah.txt'.",IDC_STATICFNAME,35,7,243,23,SS_NOPREFIX
|
||||
LTEXT "Do you want to replace the existing file:",IDC_STATICPROMPT1,35,34,243,8,SS_NOPREFIX
|
||||
ICON "",IDC_STATICDSTICON,43,46,20,20
|
||||
LTEXT "Static",IDC_STATICDSTSIZE,69,47,209,8,SS_NOPREFIX
|
||||
LTEXT "Static",IDC_STATICDSTTIME,69,57,209,8,SS_NOPREFIX
|
||||
LTEXT "with this one?",IDC_STATICPROMPT2,35,74,243,8,SS_NOPREFIX
|
||||
ICON "",IDC_STATICSRCICON,43,86,20,20
|
||||
LTEXT "Static",IDC_STATICSRCSIZE,69,87,209,8,SS_NOPREFIX
|
||||
LTEXT "Static",IDC_STATICSRCTIME,69,97,209,8,SS_NOPREFIX
|
||||
CONTROL "<a>&More...</a>",IDC_LINKMORE,"SysLink",WS_TABSTOP,7,120,45,10
|
||||
END
|
||||
|
||||
IDD_FILER DIALOGEX 0, 0, 266, 136
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
EXSTYLE WS_EX_LAYOUTRTL
|
||||
CAPTION "Confirm File Replace"
|
||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "&Yes",IDOK,149,115,53,14
|
||||
PUSHBUTTON "&No",IDNO,206,115,53,14
|
||||
ICON "",IDC_STATICICON1,7,7,20,20
|
||||
LTEXT "This folder already contains a file called 'blah.txt'.",IDC_STATICFNAME,35,7,224,23,SS_NOPREFIX
|
||||
LTEXT "Do you want to replace the existing file:",IDC_STATICPROMPT1,35,34,224,8,SS_NOPREFIX
|
||||
ICON "",IDC_STATICDSTICON,43,46,20,20
|
||||
LTEXT "Static",IDC_STATICDSTSIZE,69,47,190,8,SS_NOPREFIX
|
||||
LTEXT "Static",IDC_STATICDSTTIME,69,57,190,8,SS_NOPREFIX
|
||||
LTEXT "with this one?",IDC_STATICPROMPT2,35,74,224,8,SS_NOPREFIX
|
||||
ICON "",IDC_STATICSRCICON,43,86,20,20
|
||||
LTEXT "Static",IDC_STATICSRCSIZE,69,87,190,8,SS_NOPREFIX
|
||||
LTEXT "Static",IDC_STATICSRCTIME,69,97,190,8,SS_NOPREFIX
|
||||
CONTROL "<a>&More...</a>",IDC_LINKMORE,"SysLink",WS_TABSTOP,7,120,57,10
|
||||
END
|
||||
|
||||
IDD_FOLDERMULTI DIALOGEX 0, 0, 285, 100
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
CAPTION "Confirm Folder Replace"
|
||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "&Yes",IDOK,55,79,53,14
|
||||
PUSHBUTTON "Yes to &All",IDYES,112,79,53,14
|
||||
PUSHBUTTON "&No",IDNO,169,79,53,14
|
||||
PUSHBUTTON "Cancel",IDCANCEL,226,79,53,14
|
||||
ICON "",IDC_STATICICON1,7,7,20,20
|
||||
LTEXT "This folder already contains a folder called 'blah'.",IDC_STATICFNAME,35,7,243,65,SS_NOPREFIX
|
||||
CONTROL "<a>&More...</a>",IDC_LINKMORE,"SysLink",WS_TABSTOP,7,84,45,10
|
||||
END
|
||||
|
||||
IDD_FOLDER DIALOGEX 0, 0, 266, 100
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
CAPTION "Confirm Folder Replace"
|
||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "&Yes",IDOK,149,79,53,14
|
||||
PUSHBUTTON "&No",IDNO,206,79,53,14
|
||||
ICON "",IDC_STATICICON1,7,7,20,20
|
||||
LTEXT "This folder already contains a folder called 'blah'.",IDC_STATICFNAME,35,7,224,65,SS_NOPREFIX
|
||||
CONTROL "<a>&More...</a>",IDC_LINKMORE,"SysLink",WS_TABSTOP,7,84,57,10
|
||||
END
|
||||
|
||||
IDD_FOLDERR DIALOGEX 0, 0, 266, 99
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
EXSTYLE WS_EX_LAYOUTRTL
|
||||
CAPTION "Confirm Folder Replace"
|
||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "&Yes",IDOK,149,78,53,14
|
||||
PUSHBUTTON "&No",IDNO,206,78,53,14
|
||||
ICON "",IDC_STATICICON1,7,7,20,20
|
||||
LTEXT "This folder already contains a folder called 'blah'.",IDC_STATICFNAME,35,7,224,65,SS_NOPREFIX
|
||||
CONTROL "<a>&More...</a>",IDC_LINKMORE,"SysLink",WS_TABSTOP,7,83,57,10
|
||||
END
|
||||
|
||||
IDD_FOLDERMULTIR DIALOGEX 0, 0, 285, 100
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_CAPTION | WS_SYSMENU
|
||||
EXSTYLE WS_EX_LAYOUTRTL
|
||||
CAPTION "Confirm Folder Replace"
|
||||
FONT 8, "MS Shell Dlg", 400, 0, 0x1
|
||||
BEGIN
|
||||
DEFPUSHBUTTON "&Yes",IDOK,55,79,53,14
|
||||
PUSHBUTTON "Yes to &All",IDYES,112,79,53,14
|
||||
PUSHBUTTON "&No",IDNO,169,79,53,14
|
||||
PUSHBUTTON "Cancel",IDCANCEL,226,79,53,14
|
||||
ICON "",IDC_STATICICON1,7,7,20,20
|
||||
LTEXT "This folder already contains a folder called 'blah'.",IDC_STATICFNAME,35,7,243,65,SS_NOPREFIX
|
||||
CONTROL "<a>&More...</a>",IDC_LINKMORE,"SysLink",WS_TABSTOP,7,84,45,10
|
||||
END
|
||||
|
||||
IDD_CUSTOMTOOLBAR DIALOGEX 0, 0, 249, 183
|
||||
STYLE DS_SETFONT | DS_CENTER | WS_POPUP | WS_CLIPCHILDREN | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME
|
||||
CAPTION "Edit Toolbar Button (%s)"
|
||||
FONT 9, "Segoe UI", 400, 0, 0x0
|
||||
BEGIN
|
||||
LTEXT "Command:",IDC_STATICCOMMAND,7,7,35,12,SS_CENTERIMAGE
|
||||
COMBOBOX IDC_COMBOCOMMAND,47,7,180,30,CBS_DROPDOWN | CBS_AUTOHSCROLL | CBS_SORT | WS_VSCROLL | WS_TABSTOP
|
||||
PUSHBUTTON "...",IDC_BUTTONCOMMAND,228,7,14,12
|
||||
LTEXT "Link:",IDC_STATICLINK,7,23,16,12,SS_CENTERIMAGE
|
||||
COMBOBOX IDC_COMBOLINK,47,23,180,30,CBS_DROPDOWN | CBS_AUTOHSCROLL | CBS_SORT | WS_VSCROLL | WS_TABSTOP
|
||||
PUSHBUTTON "...",IDC_BUTTONLINK,228,23,14,12
|
||||
LTEXT "Label:",IDC_STATICTEXT,7,41,22,12,SS_CENTERIMAGE
|
||||
EDITTEXT IDC_EDITLABEL,47,41,195,12,ES_AUTOHSCROLL
|
||||
LTEXT "Tip:",IDC_STATICINFOTIP,7,58,13,12,SS_CENTERIMAGE
|
||||
EDITTEXT IDC_EDITTIP,47,58,195,12,ES_AUTOHSCROLL
|
||||
LTEXT "Icon:",IDC_STATICICON,7,74,18,12,SS_CENTERIMAGE
|
||||
EDITTEXT IDC_EDITICON,47,74,180,12,ES_AUTOHSCROLL
|
||||
PUSHBUTTON "...",IDC_BUTTONICON,228,74,14,12
|
||||
ICON "",IDC_ICONN,9,89,20,20
|
||||
LTEXT "Disabled:",IDC_STATICICOND,7,113,35,12,SS_CENTERIMAGE
|
||||
EDITTEXT IDC_EDITICOND,47,113,180,12,ES_AUTOHSCROLL
|
||||
PUSHBUTTON "...",IDC_BUTTONICOND,228,113,14,12
|
||||
ICON "",IDC_ICOND,9,127,20,20
|
||||
PUSHBUTTON "Restore defaults",IDC_BUTTONRESET,7,162,90,14
|
||||
DEFPUSHBUTTON "OK",IDOK,135,162,50,14
|
||||
PUSHBUTTON "Cancel",IDCANCEL,192,162,50,14
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Version
|
||||
//
|
||||
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION _PRODUCT_VERSION
|
||||
PRODUCTVERSION _PRODUCT_VERSION
|
||||
FILEFLAGSMASK 0x3fL
|
||||
#ifdef _DEBUG
|
||||
FILEFLAGS 0x1L
|
||||
#else
|
||||
FILEFLAGS 0x0L
|
||||
#endif
|
||||
FILEOS 0x4L
|
||||
FILETYPE 0x2L
|
||||
FILESUBTYPE 0x0L
|
||||
BEGIN
|
||||
BLOCK "StringFileInfo"
|
||||
BEGIN
|
||||
BLOCK "040904e4"
|
||||
BEGIN
|
||||
VALUE "CompanyName", "Open-Shell"
|
||||
VALUE "FileDescription", "Adds classic Windows Explorer features"
|
||||
VALUE "FileVersion", _PRODUCT_VERSION_STR
|
||||
VALUE "InternalName", "ClassicExplorer.dll"
|
||||
VALUE "LegalCopyright", "Copyright (C) 2017-2018, The Open-Shell Team"
|
||||
VALUE "OriginalFilename", "ClassicExplorer.dll"
|
||||
VALUE "ProductName", "Open-Shell"
|
||||
VALUE "ProductVersion", _PRODUCT_VERSION_STR
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
BEGIN
|
||||
VALUE "Translation", 0x409, 1252
|
||||
END
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// REGISTRY
|
||||
//
|
||||
|
||||
IDR_CLASSICEXPLORER REGISTRY "ClassicExplorer.rgs"
|
||||
IDR_EXPLORERBAND REGISTRY "ExplorerBand.rgs"
|
||||
IDR_EXPLORERBHO REGISTRY "ExplorerBHO.rgs"
|
||||
IDR_CLASSICCOPYEXT REGISTRY "ClassicCopyExt.rgs"
|
||||
IDR_SHAREOVERLAY REGISTRY "ShareOverlay.rgs"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Icon
|
||||
//
|
||||
|
||||
// Icon with lowest ID value placed first to ensure application icon
|
||||
// remains consistent on all systems.
|
||||
IDI_APPICON ICON "..\\Setup\\OpenShell.ico"
|
||||
IDI_UP2DISABLED ICON "up2Disabled.ico"
|
||||
IDI_UP2HOT ICON "up2Hot.ico"
|
||||
IDI_UP2NORMAL ICON "up2Normal.ico"
|
||||
IDI_UP2PRESSED ICON "up2Pressed.ico"
|
||||
IDI_UP ICON "up.ico"
|
||||
IDI_UPDISABLED ICON "upDisabled.ico"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// DESIGNINFO
|
||||
//
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
GUIDELINES DESIGNINFO
|
||||
BEGIN
|
||||
IDD_CUSTOMTOOLBAR, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 242
|
||||
TOPMARGIN, 7
|
||||
BOTTOMMARGIN, 176
|
||||
END
|
||||
END
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// String Table
|
||||
//
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_APP_TITLE "Classic Explorer"
|
||||
IDS_NEW_SETTINGS1 "The new settings will take effect the next time you open an Explorer window."
|
||||
IDS_NEW_SETTINGS2 "You need to log off and back on for the new settings to take effect."
|
||||
IDS_SETTINGS_TITLE "Settings for Classic Explorer"
|
||||
IDS_SETTINGS_TITLE_VER "Settings for Classic Explorer %d.%d.%d"
|
||||
IDS_LANGUAGE_SETTINGS "Language"
|
||||
IDS_TOOLBAR_SETTINGS "Toolbar Settings"
|
||||
IDS_BIG_BUTTONS "Big buttons"
|
||||
IDS_BIG_BUTTONS_TIP "Use big buttons in the toolbar"
|
||||
IDS_SMALL_SIZE "Small icon size"
|
||||
IDS_SMALL_SIZE_TIP "Set the icon size when 'Big buttons' is unchecked. By default it is 16 for DPI<120 and 24 for DPI>=120"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_LARGE_SIZE "Large icon size"
|
||||
IDS_LARGE_SIZE_TIP "Set the icon size when 'Big buttons' is checked. By default it is 24 for DPI<120 and 32 for DPI>=120"
|
||||
IDS_MENU_SIZE "Menu icon size"
|
||||
IDS_MENU_SIZE_TIP "Set the size of the icons in the dropdown menus"
|
||||
IDS_SAME_SIZE "Same size buttons"
|
||||
IDS_SAME_SIZE_TIP "When this is checked, all toolbar buttons are the same size, determined by the widest button. Cannot be combined with 'Text is on the side'"
|
||||
IDS_LIST_MODE "Text is on the side"
|
||||
IDS_LIST_MODE_TIP "When this is checked, the toolbar is in list mode. The button text shows next to the icon instead of under the icon"
|
||||
IDS_RESIZEABLE "Resizeable toolbar"
|
||||
IDS_RESIZEABLE_TIP "When this is checked, the toolbar can be resized to be smaller than its full size. The buttons that don't fit on screen can be accessed by clicking on the small chevron button"
|
||||
IDS_BUTTONS_SETTINGS "Toolbar Buttons"
|
||||
IDS_NAVIGATION_SETTINGS "Navigation Pane"
|
||||
IDS_TREE_STYLE "Navigation pane style"
|
||||
IDS_TREE_STYLE_TIP "Pick the style for the folder tree in the navigation pane"
|
||||
IDS_XPCLASSIC "Windows XP Classic"
|
||||
IDS_XPCLASSIC_TIP "The navigation pane has lines connecting the folders"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_XPSIMPLE "Windows XP Simple"
|
||||
IDS_XPSIMPLE_TIP "The navigation pane has no lines"
|
||||
IDS_VISTA "Windows Vista"
|
||||
IDS_VISTA_TIP "The navigation pane shows little triangles to expand the folders"
|
||||
IDS_TREE_SPACING "Tree item spacing"
|
||||
IDS_TREE_SPACING_TIP "This is a number for controlling the spacing between the items in the folder tree. Use positive numbers to increase the spacing, and negative numbers to reduce the spacing"
|
||||
IDS_NO_FADE "Don't fade buttons"
|
||||
IDS_NO_FADE_TIP "When this is checked, the small triangle buttons for expanding the folder will not fade out when the mouse moves away"
|
||||
IDS_FULL_INDENT "Full-size offset for sub-folders"
|
||||
IDS_FULL_INDENT_TIP "When this is checked, the sub-folders will be offset by the full size of the icon, instead of the half of the size"
|
||||
IDS_NAVIGATE "Auto-navigate to the selected folder"
|
||||
IDS_NAVIGATE_TIP "Select if the files on the right should update to show the current folder on the left"
|
||||
IDS_NAV_DELAY "Auto-navigation delay"
|
||||
IDS_NAV_DELAY_TIP "Enter the delay (in ms) for updating the files after selecting a new folder"
|
||||
IDS_ALT_ENTER "Enable Alt+Enter in the navigation pane"
|
||||
IDS_ALT_ENTER_TIP "When this is checked, pressing Alt+Enter will show the properties of the selected folder"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_VIEWCONTENT_TIP "Shows the Content view"
|
||||
IDS_VIEWICONS1_TIP "Shows the Small Icons view"
|
||||
IDS_VIEWICONS2_TIP "Shows the Medium Icons view"
|
||||
IDS_VIEWICONS3_TIP "Shows the Large Icons view"
|
||||
IDS_VIEWICONS4_TIP "Shows the Extra Large Icons view"
|
||||
IDS_OPEN_TIP "Opens a given folder in the current window"
|
||||
IDS_CUSTOM_TIP "This is a custom button. Use the command property to launch a program, or the link property to show a folder as a drop-down menu"
|
||||
IDS_NEWFOLDER_TIP "Creates a new folder"
|
||||
IDS_SCROLLTIP "Hide scroll tooltips"
|
||||
IDS_SCROLLTIP_TIP "When this is checked, there won't be a tooltip when you are dragging the vertical scrollbar"
|
||||
IDS_NAV_DEFAULT "Default behavior"
|
||||
IDS_NAV_DEFAULT_TIP "Don't change the default behavior of Explorer"
|
||||
IDS_NAV_KBD "When using the keyboard"
|
||||
IDS_NAV_KBD_TIP "The files will update only if you select a new folder with the keyboard"
|
||||
IDS_NAV_ALWAYS "Always"
|
||||
IDS_NAV_ALWAYS_TIP "The files will update every time the selected folder changes for any reason"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_FIX_SCROLL "Fix folder scrolling"
|
||||
IDS_FIX_SCROLL_TIP "This option fixes a bug in Windows 7 that moves a folder to the bottom of the screen after it is expanded"
|
||||
IDS_TITLE_SETTINGS "Title Bar"
|
||||
IDS_SHOW_CAPTION "Show caption in the title bar"
|
||||
IDS_SHOW_CAPTION_TIP "Show the caption (the current path) in the title bar"
|
||||
IDS_SHOW_ICON "Show icon in the title bar"
|
||||
IDS_SHOW_ICON_TIP "Show the icon of the current folder in the title bar"
|
||||
IDS_NO_BREADCRUMBS "Disable breadcrumbs"
|
||||
IDS_NO_BREADCRUMBS_TIP "Disable breadcrumbs and show the full path in the address bar"
|
||||
IDS_ADDRESS_HISTORY "Address bar history"
|
||||
IDS_ADDRESS_HISTORY_TIP "Control the contents of the history dropdown"
|
||||
IDS_NORMAL_HISTORY "Normal history"
|
||||
IDS_NORMAL_HISTORY_TIP "Show the default contents as provided by Explorer (recently visited folders and websites)"
|
||||
IDS_SIMPLE_PATH "Simple path"
|
||||
IDS_SIMPLE_PATH_TIP "Show the parents of the current folder all the way to the Desktop"
|
||||
IDS_EXTENDED_PATH "Extended path"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_EXTENDED_PATH_TIP "Besides the parents, shows all immediate folders of the Desktop and Computer. This is how it works in Windows XP"
|
||||
IDS_HIDE_SEARCH "Hide Search box"
|
||||
IDS_HIDE_SEARCH_TIP "Hide the search box from the address bar"
|
||||
IDS_UP_SETTINGS "Up Button"
|
||||
IDS_SHOW_UP "Show Up button"
|
||||
IDS_SHOW_UP_TIP "Controls how the Up button is displayed"
|
||||
IDS_DONT_SHOW "Don't show"
|
||||
IDS_DONT_SHOW_TIP "The Up button is not shown"
|
||||
IDS_BEFORE_BACK "Before Back/Forward"
|
||||
IDS_BEFORE_BACK_TIP "The Up button appears before the Back/Forward buttons"
|
||||
IDS_AFTER_BACK "After Back/Forward"
|
||||
IDS_AFTER_BACK_TIP "The Up button appears after the Back/Forward buttons"
|
||||
IDS_UP_NORMAL "Normal Up button icon"
|
||||
IDS_UP_NORMAL_TIP "Pick the icon to use for the normal Up button"
|
||||
IDS_UP_HOT "Hot Up button icon"
|
||||
IDS_UP_HOT_TIP "Pick the icon to use for the hot Up button (when the mouse is over the button)"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_UP_PRESSED "Pressed Up button icon"
|
||||
IDS_UP_PRESSED_TIP "Pick the icon to use for the pressed Up button"
|
||||
IDS_UP_DISABLED "Disabled Up button icon"
|
||||
IDS_UP_DISABLED_TIP "Pick the icon to use for the disabled Up button"
|
||||
IDS_UP_SIZE "Up button size"
|
||||
IDS_UP_SIZE_TIP "Set the size for the Up button. By default it is 30 for DPI<120 and 36 for DPI>=120"
|
||||
IDS_STATUS_SETTINGS "Status Bar"
|
||||
IDS_FREE_SPACE "Show free space and file size"
|
||||
IDS_FREE_SPACE_TIP "The status bar will show the free space on the current drive and the total size of all selected files. If no files are selected, the total size of all files will be shown"
|
||||
IDS_INFO_TIP "Show detailed info for single selection"
|
||||
IDS_INFO_TIP_TIP "When a single file is selected, the status bar will show the detailed information for that file"
|
||||
IDS_FORCE_REFRESH "Force status refresh"
|
||||
IDS_FORCE_REFRESH_TIP "This is a workaround for a bug in Explorer for Windows 7. Sometimes when a new Explorer window is opened the status bar is blank. Check this option to enable the workaround"
|
||||
IDS_FILE_SETTINGS "File Operation"
|
||||
IDS_FILE_UI "Replace file conflict dialog"
|
||||
IDS_FILE_UI_TIP "When this is checked, the dialog showing file conflicts during a copy or move operation will be replaced with the old-style dialog from Windows XP"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_FOLDER_UI "Replace folder conflict dialog"
|
||||
IDS_FOLDER_UI_TIP "When this is checked, the dialog showing folder conflicts during a copy or move operation will be replaced with the old-style dialog from Windows XP"
|
||||
IDS_ALERT_LEVEL "Sound alert for file conflicts"
|
||||
IDS_ALERT_LEVEL_TIP "This setting adds a sound alert to the copy confirmation dialog when a system or read-only file is about to be overwritten"
|
||||
IDS_NO_ALERT "No alert"
|
||||
IDS_NO_ALERT_TIP "No sound is played"
|
||||
IDS_SYS_FILES "For system files"
|
||||
IDS_SYS_FILES_TIP "A sound is played when a system file is about to be overwritten"
|
||||
IDS_RO_FILES "For system and read-only files"
|
||||
IDS_RO_FILES_TIP "A sound is played when a system or a read-only file is about to be overwritten"
|
||||
IDS_MORE "Always show more details"
|
||||
IDS_MORE_TIP "When this is checked, Explorer dialogs like Copy, Move or Delete will expand to show all details by default"
|
||||
IDS_MORE_DELAY "Delay for more details"
|
||||
IDS_MORE_DELAY_TIP "Delay (in ms) for showing more details in the progress dialog. On Windows 7 with Aero if the details are shown too soon the progress dialog flickers badly. Use a delay of at least 250 ms to avoid the flicker. The delay is also useful if you want to see the details only for longer operations"
|
||||
IDS_FILE_EXPLORER "Enable only in Explorer (improves performance)"
|
||||
IDS_FILE_EXPLORER_TIP "When this is checked, the file and folder conflict dialogs will be replaced only in Explorer. Otherwise they will be replaced for all processes"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_FILEPANE_SETTINGS "File Pane"
|
||||
IDS_SHARE "Add icon overlay for shared folders"
|
||||
IDS_SHARE_TIP "When this is checked, the shared folders will get a small overlay icon"
|
||||
IDS_SHARE_ICON "Share overlay icon"
|
||||
IDS_SHARE_ICON_TIP "Set the icon to be used for the overlay"
|
||||
IDS_SHARE_EXPLORER "Show overlay only in Explorer (improves performance)"
|
||||
IDS_SHARE_EXPLORER_TIP "When this is checked, the overlay icon will be shown only in Explorer. Otherwise they will be shown in all processes"
|
||||
IDS_HEADERS "Show sort headers in all views"
|
||||
IDS_HEADERS_TIP "When this is checked, the sort headers will show in all views, not just Details"
|
||||
IDS_SCROLLBAR "Show horizontal scrollbar"
|
||||
IDS_SCROLLBAR_TIP "Select if the horizontal scrollbar will be enabled"
|
||||
IDS_SCROLLBAR_DEFAULT "Default"
|
||||
IDS_SCROLLBAR_DEFAULT_TIP
|
||||
"The scrollbar will be disabled for the 'Windows Vista' navigation pane style, and enabled for the others"
|
||||
IDS_SCROLLBAR_ON "Enabled"
|
||||
IDS_SCROLLBAR_ON_TIP "The scrollbar will show up when it is needed"
|
||||
IDS_SCROLLBAR_OFF "Disabled"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_SCROLLBAR_OFF_TIP "The scrollbar will be hidden at all times"
|
||||
IDS_COMMAND_TIP "Pick a command for the button. The command determines what the button does when clicked"
|
||||
IDS_LINK_TIP "Type a full path of a file or a folder. The folder will open like a dropdown menu. The file will be executed when the button is clicked"
|
||||
IDS_TEXT_TIP "Enter the text for the button. If the text starts with $ (like $Toolbar.Settings) it will be looked up in the file ExplorerL10N.ini"
|
||||
IDS_TIP_TIP "Enter the tooltip for the button. If the text starts with $ (like $Toolbar.Settings) it will be looked up in the file ExplorerL10N.ini"
|
||||
IDS_ICON_TIP "Enter the icon for the button. If the icon is blank, the default icon of the link will be used instead. Use either a path to a .ico file, or a combination of a .dll file and a icon ID. Use 'none' to get no icon at all"
|
||||
IDS_ICOND_TIP "Enter the disabled icon for the button. If the setting is blank, the disabled icon will be generated from the normal icon"
|
||||
IDS_RESTORE_TIP "Restores all properties (text, icon and more) to the defaults for the selected command"
|
||||
IDS_SEPARATOR_TIP "This item separates buttons in the toolbar"
|
||||
IDS_UP_TIP "Goes up to the parent folder"
|
||||
IDS_CUT_TIP "Cuts the selected files"
|
||||
IDS_COPY_TIP "Copies the selected files"
|
||||
IDS_PASTE_TIP "Pastes files from the clipboard"
|
||||
IDS_DELETE_TIP "Deletes the selected files"
|
||||
IDS_PROPERTIES_TIP "Shows properties for the selection"
|
||||
IDS_EMAIL_TIP "Emails the selected files"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_SETTINGS_TIP "Shows the Classic Explorer settings"
|
||||
IDS_REFRESH_TIP "Refreshes the Explorer view"
|
||||
IDS_STOP_TIP "Stops the current operation"
|
||||
IDS_RENAME_TIP "Renames the selected file"
|
||||
IDS_MOVETO_TIP "Moves the selection to a new place"
|
||||
IDS_COPYTO_TIP "Copies the selection to a new place"
|
||||
IDS_UNDO_TIP "Undoes the last operation"
|
||||
IDS_REDO_TIP "Redoes the last undo"
|
||||
IDS_SELECTALL_TIP "Selects all files in the folder"
|
||||
IDS_DESELECT_TIP "Deselects all"
|
||||
IDS_INVERT_TIP "Inverts the selection"
|
||||
IDS_BACK_TIP "Goes back to the previous location"
|
||||
IDS_FORWARD_TIP "Goes to the next location"
|
||||
IDS_VIEWTILES_TIP "Shows the Tiles view"
|
||||
IDS_VIEWDEATAILS_TIP "Shows the Details view"
|
||||
IDS_VIEWLIST_TIP "Shows the List view"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_ALT_D "Additional shortcut for the address bar: Alt +"
|
||||
IDS_ALT_D_TIP "Enter a letter 'A' to 'Z' to be a shortcut for the address bar. In some languages the default shortcut conflicts with a menu item"
|
||||
IDS_SORT_TIP "Sorts the folder by the given property (name, type, size or date). Use '-' before the property to sort in descending order. Read the help for more options."
|
||||
IDS_GROUP_TIP "Groups the folder by the given property (name, type, size or date). Use '-' before the property to group in descending order. Read the help for more options."
|
||||
IDS_PASTE_SHORTCUT_TIP "Creates shortcuts for the files in the clipboard"
|
||||
IDS_UP_HOTKEY "Additional shortcut for the Up button"
|
||||
IDS_UP_HOTKEY_TIP "Select a shortcut for navigating to the parent folder"
|
||||
IDS_MAP_DRIVE_TIP "Connects to a network drive"
|
||||
IDS_DISCONNECT_DRIVE_TIP "Disconnects from a network drive"
|
||||
IDS_CUSTOMIZEFOLDER_TIP "Customize this folder"
|
||||
IDS_SEPARATOR_ITEM "SEPARATOR"
|
||||
IDS_UP_ITEM "Up"
|
||||
IDS_CUT_ITEM "Cut"
|
||||
IDS_COPY_ITEM "Copy"
|
||||
IDS_PASTE_ITEM "Paste"
|
||||
IDS_PASTE_LNK_ITEM "Paste shortcut"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_DELETE_ITEM "Delete"
|
||||
IDS_PROPERTIES_ITEM "Properties"
|
||||
IDS_EMAIL_ITEM "Email"
|
||||
IDS_SETTINGS_ITEM "Settings"
|
||||
IDS_REFRESH_ITEM "Refresh"
|
||||
IDS_STOP_ITEM "Stop"
|
||||
IDS_RENAME_ITEM "Rename"
|
||||
IDS_NEWFOLDER_ITEM "New folder"
|
||||
IDS_MOVETO_ITEM "Move to"
|
||||
IDS_COPYTO_ITEM "Copy to"
|
||||
IDS_UNDO_ITEM "Undo"
|
||||
IDS_REDO_ITEM "Redo"
|
||||
IDS_SELECTALL_ITEM "Select all"
|
||||
IDS_DESELECT_ITEM "Deselect"
|
||||
IDS_INVERT_ITEM "Invert selection"
|
||||
IDS_BACK_ITEM "Back"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_FORWARD_ITEM "Forward"
|
||||
IDS_MAP_DRIVE_ITEM "Map network drive"
|
||||
IDS_DISCONNECT_ITEM "Disconnect network drive"
|
||||
IDS_CUSTOMIZE_ITEM "Customize folder"
|
||||
IDS_VIEWTILES_ITEM "View Tiles"
|
||||
IDS_VIEWDETAILS_ITEM "View Details"
|
||||
IDS_VIEWLIST_ITEM "View List"
|
||||
IDS_VIEWCONTENT_ITEM "View Content"
|
||||
IDS_VIEWICONS1_ITEM "View Small icons"
|
||||
IDS_VIEWICONS2_ITEM "View Medium icons"
|
||||
IDS_VIEWICONS3_ITEM "View Large icons"
|
||||
IDS_VIEWICONS4_ITEM "View Extra large icons"
|
||||
IDS_OPEN_ITEM "Open"
|
||||
IDS_SORYBY_ITEM "Sort by"
|
||||
IDS_GROUPBY_ITEM "Group by"
|
||||
IDS_CUSTOM_ITEM "Custom"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_SHOWSTATUSBAR "Show status bar"
|
||||
IDS_SHOWSTATUSBAR_TIP "When this is checked, Explorer will have a status bar that shows information about the total selection size, free disk space, and more"
|
||||
IDS_SHOW_ZONE "Show zone"
|
||||
IDS_SHOW_ZONE_TIP "When this is checked, the status bar will display the current security zone"
|
||||
IDS_SHARE_HIDDEN "Show hidden shares"
|
||||
IDS_SHARE_HIDDEN_TIP "When this is checked, the overlay will appear also for hidden shares ending with $"
|
||||
IDS_NAVPANE_ITEM "Navigation pane"
|
||||
IDS_NAVPANE_TIP "Toggles the navigation pane"
|
||||
IDS_DETAILSPANE_ITEM "Details pane"
|
||||
IDS_DETAILSPANE_TIP "Toggles the details pane"
|
||||
IDS_PREVIEWPANE_ITEM "Preview pane"
|
||||
IDS_PREVIEWPANE_TIP "Toggles the preview pane"
|
||||
IDS_SHOW_EXTENSIONS "Show extensions"
|
||||
IDS_SHOW_EXTENSIONS_TIP "Toggles the visibility of the file extensions"
|
||||
IDS_HIDDEN_FILES "Hidden files"
|
||||
IDS_HIDDEN_FILES_TIP "Toggles the visibility of the hidden files"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_SYSTEM_FILES "System files"
|
||||
IDS_SYSTEM_FILES_TIP "Toggles the visibility of the system files"
|
||||
IDS_ZIP_ITEM "Create zip file"
|
||||
IDS_ZIP_TIP "Creates a zip file from the selected items"
|
||||
IDS_STATUS_FONT "Status bar font"
|
||||
IDS_STATUS_FONT_TIP "Select the font to use for the status bar"
|
||||
IDS_FOLDEROPTIONS "Folder options"
|
||||
IDS_FOLDEROPTIONS_TIP "Opens the folder options dialog"
|
||||
END
|
||||
|
||||
#endif // English (U.S.) resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
#ifndef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 3 resource.
|
||||
//
|
||||
#include "..\Lib\resource.h"
|
||||
#include "..\Lib\Lib.rc"
|
||||
1 TYPELIB "ClassicExplorer.tlb"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#endif // not APSTUDIO_INVOKED
|
||||
|
||||
11
Src/ClassicExplorer/ClassicExplorer.rgs
Normal file
@@ -0,0 +1,11 @@
|
||||
HKCR
|
||||
{
|
||||
NoRemove AppID
|
||||
{
|
||||
'%APPID%' = s 'ClassicExplorer'
|
||||
'ClassicExplorer.DLL'
|
||||
{
|
||||
val AppID = s '%APPID%'
|
||||
}
|
||||
}
|
||||
}
|
||||
144
Src/ClassicExplorer/ClassicExplorer.vcxproj
Normal file
@@ -0,0 +1,144 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|x64">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|x64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Setup|Win32">
|
||||
<Configuration>Setup</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Setup|x64">
|
||||
<Configuration>Setup</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<ProjectGuid>{9AF324B7-F786-4D85-B2E1-6E51720F874E}</ProjectGuid>
|
||||
<RootNamespace>ClassicExplorer</RootNamespace>
|
||||
<Keyword>AtlProj</Keyword>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
|
||||
<UseOfAtl>Static</UseOfAtl>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<WholeProgramOptimization Condition="'$(Configuration)'!='Debug'">true</WholeProgramOptimization>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets">
|
||||
<Import Project="..\Common.props" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup Condition="'$(Platform)'=='Win32'">
|
||||
<TargetName>$(ProjectName)32</TargetName>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Platform)'=='x64'">
|
||||
<TargetName>$(ProjectName)64</TargetName>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<IgnoreImportLibrary>true</IgnoreImportLibrary>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup>
|
||||
<ClCompile>
|
||||
<PreprocessorDefinitions>_USRDLL;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ClCompile>
|
||||
<ResourceCompile>
|
||||
<AdditionalIncludeDirectories>$(IntDir);%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
</ResourceCompile>
|
||||
<Link>
|
||||
<AdditionalDependencies>oleacc.lib;comctl32.lib;uxtheme.lib;dwmapi.lib;winmm.lib;htmlhelp.lib;wininet.lib;wintrust.lib;crypt32.lib;Netapi32.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||
<ModuleDefinitionFile>$(TargetName).def</ModuleDefinitionFile>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)'!='Setup'">
|
||||
<Link>
|
||||
<RegisterOutput>true</RegisterOutput>
|
||||
<PerUserRedirection>true</PerUserRedirection>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="ClassicCopy.cpp" />
|
||||
<ClCompile Include="ClassicCopyExt.cpp" />
|
||||
<ClCompile Include="ClassicExplorer.cpp" />
|
||||
<ClCompile Include="ClassicExplorer_i.c">
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
<ClCompile Include="dllmain.cpp" />
|
||||
<ClCompile Include="ExplorerBand.cpp" />
|
||||
<ClCompile Include="ExplorerBHO.cpp" />
|
||||
<ClCompile Include="SettingsUI.cpp" />
|
||||
<ClCompile Include="ShareOverlay.cpp" />
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<PrecompiledHeader>Create</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Midl Include="ClassicExplorer.idl" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="ClassicCopyExt.rgs" />
|
||||
<None Include="ClassicExplorer.rgs" />
|
||||
<None Include="ClassicExplorer32.def" />
|
||||
<None Include="ClassicExplorer64.def" />
|
||||
<None Include="ExplorerBand.rgs" />
|
||||
<None Include="ExplorerBHO.rgs" />
|
||||
<None Include="ExplorerL10N.ini">
|
||||
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
|
||||
</None>
|
||||
<None Include="ShareOverlay.rgs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="..\Localization\English\ClassicExplorerADMX.txt" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="ClassicCopyExt.h" />
|
||||
<ClInclude Include="ClassicExplorer_h.h" />
|
||||
<ClInclude Include="dllmain.h" />
|
||||
<ClInclude Include="ExplorerBand.h" />
|
||||
<ClInclude Include="ExplorerBHO.h" />
|
||||
<ClInclude Include="Resource.h" />
|
||||
<ClInclude Include="SettingsUI.h" />
|
||||
<ClInclude Include="ShareOverlay.h" />
|
||||
<ClInclude Include="stdafx.h" />
|
||||
<ClInclude Include="targetver.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="ClassicExplorer.rc" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Image Include="..\Setup\OpenShell.ico" />
|
||||
<Image Include="up.ico" />
|
||||
<Image Include="up2Disabled.ico" />
|
||||
<Image Include="up2Hot.ico" />
|
||||
<Image Include="up2Normal.ico" />
|
||||
<Image Include="up2Pressed.ico" />
|
||||
<Image Include="upDisabled.ico" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\Lib\Lib.vcxproj">
|
||||
<Project>{d42fe717-485b-492d-884a-1999f6d51154}</Project>
|
||||
<ReferenceOutputAssembly>false</ReferenceOutputAssembly>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
149
Src/ClassicExplorer/ClassicExplorer.vcxproj.filters
Normal file
@@ -0,0 +1,149 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="Source Files">
|
||||
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
|
||||
<Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Header Files">
|
||||
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
|
||||
<Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Resource Files">
|
||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Generated Files">
|
||||
<UniqueIdentifier>{5fffcfa3-305b-4c53-b51b-b387b5702497}</UniqueIdentifier>
|
||||
<SourceControlFiles>False</SourceControlFiles>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="ClassicCopy.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ClassicCopyExt.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ClassicExplorer.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="dllmain.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ExplorerBand.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ExplorerBHO.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="SettingsUI.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ShareOverlay.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ClassicExplorer_i.c">
|
||||
<Filter>Generated Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Midl Include="ClassicExplorer.idl">
|
||||
<Filter>Source Files</Filter>
|
||||
</Midl>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="ClassicExplorer32.def">
|
||||
<Filter>Source Files</Filter>
|
||||
</None>
|
||||
<None Include="ClassicExplorer64.def">
|
||||
<Filter>Source Files</Filter>
|
||||
</None>
|
||||
<None Include="ClassicCopyExt.rgs">
|
||||
<Filter>Resource Files</Filter>
|
||||
</None>
|
||||
<None Include="ClassicExplorer.rgs">
|
||||
<Filter>Resource Files</Filter>
|
||||
</None>
|
||||
<None Include="ExplorerBand.rgs">
|
||||
<Filter>Resource Files</Filter>
|
||||
</None>
|
||||
<None Include="ExplorerBHO.rgs">
|
||||
<Filter>Resource Files</Filter>
|
||||
</None>
|
||||
<None Include="ExplorerL10N.ini">
|
||||
<Filter>Resource Files</Filter>
|
||||
</None>
|
||||
<None Include="ShareOverlay.rgs">
|
||||
<Filter>Resource Files</Filter>
|
||||
</None>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="..\Localization\English\ClassicExplorerADMX.txt">
|
||||
<Filter>Source Files</Filter>
|
||||
</Text>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="ClassicCopyExt.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="dllmain.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ExplorerBand.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ExplorerBHO.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="SettingsUI.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ShareOverlay.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="stdafx.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="targetver.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Resource.h">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ClassicExplorer_h.h">
|
||||
<Filter>Generated Files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="ClassicExplorer.rc">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ResourceCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Image Include="..\Setup\OpenShell.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="up.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="up2Disabled.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="up2Hot.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="up2Normal.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="up2Pressed.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="upDisabled.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
14
Src/ClassicExplorer/ClassicExplorer32.def
Normal file
@@ -0,0 +1,14 @@
|
||||
; ClassicExplorer.def : Declares the module parameters.
|
||||
|
||||
LIBRARY "ClassicExplorer32.DLL"
|
||||
|
||||
EXPORTS
|
||||
DllCanUnloadNow PRIVATE
|
||||
DllGetClassObject PRIVATE
|
||||
DllRegisterServer PRIVATE
|
||||
DllUnregisterServer PRIVATE
|
||||
DllInstall PRIVATE
|
||||
ShowExplorerSettings
|
||||
DllImportSettingsXml
|
||||
DllExportSettingsXml
|
||||
DllSaveAdmx
|
||||
13
Src/ClassicExplorer/ClassicExplorer64.def
Normal file
@@ -0,0 +1,13 @@
|
||||
; ClassicExplorer.def : Declares the module parameters.
|
||||
|
||||
LIBRARY "ClassicExplorer64.DLL"
|
||||
|
||||
EXPORTS
|
||||
DllCanUnloadNow PRIVATE
|
||||
DllGetClassObject PRIVATE
|
||||
DllRegisterServer PRIVATE
|
||||
DllUnregisterServer PRIVATE
|
||||
DllInstall PRIVATE
|
||||
ShowExplorerSettings
|
||||
DllImportSettingsXml
|
||||
DllExportSettingsXml
|
||||
@@ -0,0 +1,140 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include <windows.h>
|
||||
#include <commctrl.h>
|
||||
#include <shlwapi.h>
|
||||
#include <Psapi.h>
|
||||
#include "StringUtils.h"
|
||||
|
||||
// Find and activate the Settings window
|
||||
static BOOL CALLBACK FindSettingsEnum( HWND hwnd, LPARAM lParam )
|
||||
{
|
||||
wchar_t className[256];
|
||||
if (!GetClassName(hwnd,className,_countof(className)) || _wcsicmp(className,L"#32770")!=0)
|
||||
return TRUE;
|
||||
DWORD process=0;
|
||||
GetWindowThreadProcessId(hwnd,&process);
|
||||
HANDLE hProcess=OpenProcess(PROCESS_QUERY_INFORMATION|PROCESS_VM_READ,FALSE,process);
|
||||
bool bFound=false;
|
||||
if (hProcess!=INVALID_HANDLE_VALUE)
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
if (GetModuleFileNameEx(hProcess,NULL,path,_countof(path)))
|
||||
{
|
||||
if (_wcsicmp(PathFindFileName(path),L"ClassicExplorerSettings.exe")==0)
|
||||
{
|
||||
SetForegroundWindow(hwnd);
|
||||
bFound=true;
|
||||
}
|
||||
}
|
||||
CloseHandle(hProcess);
|
||||
}
|
||||
return !bFound;
|
||||
}
|
||||
|
||||
HMODULE LoadClassicExplorerDll( void )
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(NULL,path,_countof(path));
|
||||
*PathFindFileName(path)=0;
|
||||
PathAppend(path,L"ClassicExplorer32.dll");
|
||||
return LoadLibrary(path);
|
||||
}
|
||||
|
||||
// A simple program that loads ClassicExplorer32.dll and calls the ShowExplorerSettings function
|
||||
// Why not use rundll32 instead? Because it doesn't include the correct manifest for comctl32.dll
|
||||
int WINAPI wWinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpstrCmdLine, int nCmdShow )
|
||||
{
|
||||
INITCOMMONCONTROLSEX init={sizeof(init),ICC_STANDARD_CLASSES};
|
||||
InitCommonControlsEx(&init);
|
||||
|
||||
{
|
||||
const wchar_t *pXml=wcsstr(lpstrCmdLine,L"-xml ");
|
||||
if (pXml)
|
||||
{
|
||||
wchar_t xml[_MAX_PATH];
|
||||
GetToken(pXml+5,xml,_countof(xml),L" ");
|
||||
HMODULE dll=LoadClassicExplorerDll();
|
||||
if (!dll) return 1;
|
||||
typedef bool (*tImportSettingsXml)( const wchar_t *fname );
|
||||
tImportSettingsXml DllImportSettingsXml=(tImportSettingsXml)GetProcAddress(dll,"DllImportSettingsXml");
|
||||
if (!DllImportSettingsXml)
|
||||
return 1;
|
||||
CoInitialize(NULL);
|
||||
bool res=DllImportSettingsXml(xml);
|
||||
CoUninitialize();
|
||||
return res?0:1;
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
const wchar_t *pBackup=wcsstr(lpstrCmdLine,L"-backup ");
|
||||
if (pBackup)
|
||||
{
|
||||
wchar_t xml[_MAX_PATH];
|
||||
GetToken(pBackup+8,xml,_countof(xml),L" ");
|
||||
|
||||
HMODULE dll=LoadClassicExplorerDll();
|
||||
if (!dll) return 1;
|
||||
typedef bool (*tExportSettingsXml)( const wchar_t *fname );
|
||||
tExportSettingsXml DllExportSettingsXml=(tExportSettingsXml)GetProcAddress(dll,"DllExportSettingsXml");
|
||||
if (!DllExportSettingsXml)
|
||||
return 1;
|
||||
|
||||
CoInitialize(NULL);
|
||||
bool res=DllExportSettingsXml(xml);
|
||||
CoUninitialize();
|
||||
return res?0:1;
|
||||
}
|
||||
}
|
||||
|
||||
#ifndef _WIN64
|
||||
const wchar_t *pSaveAdmx=wcsstr(lpstrCmdLine,L"-saveadmx ");
|
||||
if (pSaveAdmx)
|
||||
{
|
||||
wchar_t language[100];
|
||||
GetToken(pSaveAdmx+10,language,_countof(language),L" ");
|
||||
|
||||
HMODULE dll=LoadClassicExplorerDll();
|
||||
if (!dll) return 1;
|
||||
typedef bool (*tSaveAdmx)( const char *admxFile, const char *admlFile, const char *docFile, const wchar_t *language );
|
||||
tSaveAdmx SaveAdmx=(tSaveAdmx)GetProcAddress(dll,"DllSaveAdmx");
|
||||
if (!SaveAdmx || !SaveAdmx("ClassicExplorer.admx","ClassicExplorer.adml","ClassicExplorerADMX.txt",language))
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
// prevent multiple instances from running on the same desktop
|
||||
// the assumption is that multiple desktops for the same user will have different name (but may repeat across users)
|
||||
wchar_t userName[256];
|
||||
DWORD len=_countof(userName);
|
||||
GetUserName(userName,&len);
|
||||
len=0;
|
||||
HANDLE desktop=GetThreadDesktop(GetCurrentThreadId());
|
||||
GetUserObjectInformation(desktop,UOI_NAME,NULL,0,&len);
|
||||
wchar_t *deskName=(wchar_t*)malloc(len);
|
||||
GetUserObjectInformation(desktop,UOI_NAME,deskName,len,&len);
|
||||
|
||||
wchar_t mutexName[1024];
|
||||
Sprintf(mutexName,_countof(mutexName),L"ClassicExplorerSettings.Mutex.%s.%s",userName,deskName);
|
||||
free(deskName);
|
||||
|
||||
HANDLE hMutex=CreateMutex(NULL,TRUE,mutexName);
|
||||
if (GetLastError()==ERROR_ALREADY_EXISTS || GetLastError()==ERROR_ACCESS_DENIED)
|
||||
{
|
||||
EnumWindows(FindSettingsEnum,0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
HMODULE dll=LoadClassicExplorerDll();
|
||||
if (!dll) return 1;
|
||||
|
||||
FARPROC proc=GetProcAddress(dll,"ShowExplorerSettings");
|
||||
if (!proc) return 2;
|
||||
|
||||
proc();
|
||||
return 0;
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0" xmlns:asmv3="urn:schemas-microsoft-com:asm.v3" >
|
||||
<assemblyIdentity
|
||||
version="1.0.0.0"
|
||||
processorArchitecture="X86"
|
||||
name="Open-Shell.Menu"
|
||||
type="win32"
|
||||
/>
|
||||
<description>Classic Explorer Settings</description>
|
||||
<dependency>
|
||||
<dependentAssembly>
|
||||
<assemblyIdentity
|
||||
type="win32"
|
||||
name="Microsoft.Windows.Common-Controls"
|
||||
version="6.0.0.0"
|
||||
processorArchitecture="*"
|
||||
publicKeyToken="6595b64144ccf1df"
|
||||
language="*"
|
||||
/>
|
||||
</dependentAssembly>
|
||||
</dependency>
|
||||
<asmv3:application>
|
||||
<asmv3:windowsSettings xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">
|
||||
<dpiAware>true</dpiAware>
|
||||
</asmv3:windowsSettings>
|
||||
</asmv3:application>
|
||||
<compatibility xmlns="urn:schemas-microsoft-com:compatibility.v1">
|
||||
<application>
|
||||
<!-- Windows Vista -->
|
||||
<supportedOS Id="{e2011457-1546-43c5-a5fe-008deee3d3f0}"/>
|
||||
<!-- Windows 7 -->
|
||||
<supportedOS Id="{35138b9a-5d96-4fbd-8e2d-a2440225f93a}"/>
|
||||
<!-- Windows 8 -->
|
||||
<supportedOS Id="{4a2f28e3-53b9-4441-ba9c-d69d4a4a6e38}"/>
|
||||
<!-- Windows 8.1 -->
|
||||
<supportedOS Id="{1f676c76-80e1-4239-95bb-83d0f6d0da78}"/>
|
||||
<!-- Windows 10 -->
|
||||
<supportedOS Id="{8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}"/>
|
||||
</application>
|
||||
</compatibility>
|
||||
</assembly>
|
||||
@@ -0,0 +1,111 @@
|
||||
// Microsoft Visual C++ generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
#define APSTUDIO_READONLY_SYMBOLS
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#include "winres.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
|
||||
#pragma code_page(1252)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#include ""afxres.h""\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Icon
|
||||
//
|
||||
|
||||
// Icon with lowest ID value placed first to ensure application icon
|
||||
// remains consistent on all systems.
|
||||
IDI_APPICON ICON "..\\..\\Setup\\OpenShell.ico"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Version
|
||||
//
|
||||
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION _PRODUCT_VERSION
|
||||
PRODUCTVERSION _PRODUCT_VERSION
|
||||
FILEFLAGSMASK 0x17L
|
||||
#ifdef _DEBUG
|
||||
FILEFLAGS 0x1L
|
||||
#else
|
||||
FILEFLAGS 0x0L
|
||||
#endif
|
||||
FILEOS 0x4L
|
||||
FILETYPE 0x1L
|
||||
FILESUBTYPE 0x0L
|
||||
BEGIN
|
||||
BLOCK "StringFileInfo"
|
||||
BEGIN
|
||||
BLOCK "040904b0"
|
||||
BEGIN
|
||||
VALUE "CompanyName", "Open-Shell"
|
||||
VALUE "FileDescription", "Classic Explorer Settings"
|
||||
VALUE "FileVersion", _PRODUCT_VERSION_STR
|
||||
VALUE "InternalName", "ClassicExplorerSettings"
|
||||
VALUE "LegalCopyright", "Copyright (C) 2017-2018, The Open-Shell Team"
|
||||
VALUE "OriginalFilename", "ClassicExplorerSettings.exe"
|
||||
VALUE "ProductName", "Open-Shell"
|
||||
VALUE "ProductVersion", _PRODUCT_VERSION_STR
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
BEGIN
|
||||
VALUE "Translation", 0x409, 1200
|
||||
END
|
||||
END
|
||||
|
||||
#endif // English (U.S.) resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
#ifndef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 3 resource.
|
||||
//
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#endif // not APSTUDIO_INVOKED
|
||||
|
||||
@@ -0,0 +1,74 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Setup|Win32">
|
||||
<Configuration>Setup</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<ProjectGuid>{E93271C8-0252-4A08-8227-1978C64C2D34}</ProjectGuid>
|
||||
<RootNamespace>ClassicExplorerSettings</RootNamespace>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Label="Configuration">
|
||||
<ConfigurationType>Application</ConfigurationType>
|
||||
<PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
|
||||
<UseOfAtl>Static</UseOfAtl>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<WholeProgramOptimization Condition="'$(Configuration)'!='Debug'">true</WholeProgramOptimization>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets">
|
||||
<Import Project="..\..\Common.props" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<ItemDefinitionGroup>
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<AdditionalDependencies>shlwapi.lib;comctl32.lib;psapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="ClassicExplorerSettings.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Manifest Include="ClassicExplorerSettings.manifest" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="ClassicExplorerSettings.rc" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Image Include="..\..\Setup\OpenShell.ico" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="resource.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Lib\Lib.vcxproj">
|
||||
<Project>{d42fe717-485b-492d-884a-1999f6d51154}</Project>
|
||||
<ReferenceOutputAssembly>false</ReferenceOutputAssembly>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\ClassicExplorer.vcxproj">
|
||||
<Project>{9af324b7-f786-4d85-b2e1-6e51720f874e}</Project>
|
||||
<ReferenceOutputAssembly>false</ReferenceOutputAssembly>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
16
Src/ClassicExplorer/ClassicExplorerSettings/resource.h
Normal file
@@ -0,0 +1,16 @@
|
||||
//{{NO_DEPENDENCIES}}
|
||||
// Microsoft Visual C++ generated include file.
|
||||
// Used by ClassicExplorerSettings.rc
|
||||
//
|
||||
#define IDI_APPICON 101
|
||||
|
||||
// Next default values for new objects
|
||||
//
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
#ifndef APSTUDIO_READONLY_SYMBOLS
|
||||
#define _APS_NEXT_RESOURCE_VALUE 102
|
||||
#define _APS_NEXT_COMMAND_VALUE 40001
|
||||
#define _APS_NEXT_CONTROL_VALUE 1001
|
||||
#define _APS_NEXT_SYMED_VALUE 101
|
||||
#endif
|
||||
#endif
|
||||
1576
Src/ClassicExplorer/ExplorerBHO.cpp
Normal file
191
Src/ClassicExplorer/ExplorerBHO.h
Normal file
@@ -0,0 +1,191 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// ExplorerBHO.h : Declaration of the CExplorerBHO
|
||||
|
||||
#pragma once
|
||||
#include "resource.h" // main symbols
|
||||
#include <vector>
|
||||
#include <map>
|
||||
|
||||
#include "ClassicExplorer_h.h"
|
||||
#include "ComHelper.h"
|
||||
#include <shdispid.h>
|
||||
|
||||
|
||||
// CExplorerBHO
|
||||
|
||||
class ATL_NO_VTABLE CExplorerBHO :
|
||||
public CComObjectRootEx<CComSingleThreadModel>,
|
||||
public CComCoClass<CExplorerBHO, &CLSID_ExplorerBHO>,
|
||||
public IObjectWithSiteImpl<CExplorerBHO>,
|
||||
public IDispatchImpl<IExplorerBHO, &IID_IExplorerBHO, &LIBID_ClassicExplorerLib, /*wMajor =*/ 1, /*wMinor =*/ 0>,
|
||||
public IDispEventImpl<1,CExplorerBHO,&DIID_DWebBrowserEvents2,&LIBID_SHDocVw,1,1>,
|
||||
public IDispEventImpl<2,CExplorerBHO,&DIID_DShellFolderViewEvents,&LIBID_Shell32,1,0>
|
||||
{
|
||||
public:
|
||||
typedef IDispEventImpl<1,CExplorerBHO,&DIID_DWebBrowserEvents2,&LIBID_SHDocVw,1,1> DispEvent1;
|
||||
typedef IDispEventImpl<2,CExplorerBHO,&DIID_DShellFolderViewEvents,&LIBID_Shell32,1,0> DispEvent2;
|
||||
CExplorerBHO()
|
||||
{
|
||||
m_bResetStatus=true;
|
||||
m_bForceRefresh=false;
|
||||
m_bRemapBands=false;
|
||||
m_bNoBreadcrumbs=false;
|
||||
m_TreeItemHeight=0;
|
||||
m_CurIcon=NULL;
|
||||
m_CurPath[0]=0;
|
||||
m_Rebar=NULL;
|
||||
m_TopWindow=NULL;
|
||||
m_Breadcrumbs=NULL;
|
||||
m_Progress=NULL;
|
||||
m_Status=m_Status8=NULL;
|
||||
m_DUIView=NULL;
|
||||
m_Hook=m_HookKbd=NULL;
|
||||
m_Balloon=NULL;
|
||||
m_UpButtonIndex=0;
|
||||
m_UpHotkey=0;
|
||||
m_IconNormal=m_IconHot=m_IconPressed=m_IconDisabled=NULL;
|
||||
m_NavigateMsg=0;
|
||||
m_AltD=0;
|
||||
m_FileSizeWidth=0;
|
||||
m_ZoneWidth=0;
|
||||
}
|
||||
|
||||
DECLARE_REGISTRY_RESOURCEID_V2_WITHOUT_MODULE(IDR_EXPLORERBHO, CExplorerBHO)
|
||||
|
||||
BEGIN_SINK_MAP( CExplorerBHO )
|
||||
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_DOCUMENTCOMPLETE, OnDocumentComplete)
|
||||
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_ONQUIT, OnQuit)
|
||||
SINK_ENTRY_EX(2, DIID_DShellFolderViewEvents, DISPID_SELECTIONCHANGED, OnSelChanged)
|
||||
END_SINK_MAP()
|
||||
|
||||
BEGIN_COM_MAP(CExplorerBHO)
|
||||
COM_INTERFACE_ENTRY(IExplorerBHO)
|
||||
COM_INTERFACE_ENTRY(IObjectWithSite)
|
||||
COM_INTERFACE_ENTRY(IDispatch)
|
||||
END_COM_MAP()
|
||||
|
||||
|
||||
|
||||
DECLARE_PROTECT_FINAL_CONSTRUCT()
|
||||
|
||||
HRESULT FinalConstruct()
|
||||
{
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
void FinalRelease()
|
||||
{
|
||||
}
|
||||
|
||||
// Navigation pane styles
|
||||
enum
|
||||
{
|
||||
STYLE_CLASSIC=0, // use classic XP style
|
||||
STYLE_SIMPLE=1, // use simple XP style
|
||||
STYLE_VISTA=2, // no change
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
SHOW_INFOTIP=1,
|
||||
SHOW_FREE_SPACE=2,
|
||||
SHOW_ZONE=4,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
PART_TEXT,
|
||||
PART_SIZE,
|
||||
PART_ZONE,
|
||||
};
|
||||
public:
|
||||
// IObjectWithSite
|
||||
STDMETHOD(SetSite)(IUnknown *pUnkSite);
|
||||
|
||||
// DWebBrowserEvents2
|
||||
STDMETHOD(OnDocumentComplete)( IDispatch *pDisp, VARIANT *URL );
|
||||
STDMETHOD(OnQuit)( void );
|
||||
|
||||
// DShellFolderViewEvents
|
||||
STDMETHOD(OnSelChanged)( void );
|
||||
|
||||
private:
|
||||
// Super-class the toolbar, so it has a different class name. A program called Folder Menu 3 looks for specific controls in Explorer,
|
||||
// and our extra toolbar throws it off
|
||||
class CToolbar: public CWindowImpl<CToolbar>
|
||||
{
|
||||
public:
|
||||
DECLARE_WND_SUPERCLASS(L"OpenShell.UpButton",TOOLBARCLASSNAME);
|
||||
|
||||
BEGIN_MSG_MAP( CToolbar )
|
||||
END_MSG_MAP()
|
||||
};
|
||||
|
||||
CComPtr<IShellBrowser> m_pBrowser;
|
||||
CComPtr<IWebBrowser2> m_pWebBrowser;
|
||||
CComPtr<IDispatch> m_pWebDoc;
|
||||
CComPtr<IInternetZoneManager> m_pZoneManager;
|
||||
CComPtr<IInternetSecurityManager> m_pSecurityManager;
|
||||
std::map<unsigned int,HICON> m_ZoneIconCache;
|
||||
bool m_bResetStatus;
|
||||
bool m_bForceRefresh;
|
||||
bool m_bNoBreadcrumbs;
|
||||
bool m_bRemapBands;
|
||||
int m_TreeItemHeight;
|
||||
int m_UpButtonIndex;
|
||||
int m_UpHotkey;
|
||||
CToolbar m_Toolbar;
|
||||
HWND m_TopWindow;
|
||||
HWND m_Rebar;
|
||||
HWND m_Balloon;
|
||||
HICON m_IconNormal, m_IconHot, m_IconPressed, m_IconDisabled;
|
||||
HICON m_CurIcon;
|
||||
CAbsolutePidl m_CurPidl;
|
||||
wchar_t m_CurPath[1024]; // the current path
|
||||
CWindow m_ComboBox;
|
||||
CAbsolutePidl m_NavigatePidl;
|
||||
UINT m_NavigateMsg; // private message that is posted to the progress bar to navigate to m_NavigatePidl
|
||||
HHOOK m_Hook;
|
||||
HHOOK m_HookKbd;
|
||||
HWND m_Breadcrumbs;
|
||||
HWND m_Progress;
|
||||
HWND m_Status, m_Status8;
|
||||
HWND m_DUIView;
|
||||
int m_FileSizeWidth;
|
||||
int m_ZoneWidth;
|
||||
char m_AltD;
|
||||
|
||||
struct ComboItem
|
||||
{
|
||||
PIDLIST_ABSOLUTE pidl;
|
||||
int indent;
|
||||
CString name;
|
||||
CString sortName;
|
||||
|
||||
bool operator<( const ComboItem &item ) { return _wcsicmp(sortName,item.sortName)<0; }
|
||||
};
|
||||
std::vector<ComboItem> m_ComboItems;
|
||||
void ClearComboItems( void );
|
||||
bool GetStatusText( wchar_t *buf, int size, const wchar_t *oldText, bool bShowTip, bool bShowSpace );
|
||||
void GetFileSize( wchar_t *buf, int size );
|
||||
|
||||
static int s_AutoNavDelay;
|
||||
|
||||
static LRESULT CALLBACK HookExplorer( int code, WPARAM wParam, LPARAM lParam );
|
||||
static LRESULT CALLBACK HookKeyboard( int code, WPARAM wParam, LPARAM lParam );
|
||||
static LRESULT CALLBACK SubclassTreeParentProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static LRESULT CALLBACK SubclassTreeProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static LRESULT CALLBACK SubclassStatusProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static LRESULT CALLBACK SubclassStatusProc8( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static LRESULT CALLBACK SubclassDUIViewProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static LRESULT CALLBACK SubclassRebarProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static LRESULT CALLBACK SubclassBreadcrumbProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static LRESULT CALLBACK SubclassProgressProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
};
|
||||
|
||||
OBJECT_ENTRY_AUTO(__uuidof(ExplorerBHO), CExplorerBHO)
|
||||
|
||||
bool ShowTreeProperties( HWND hwndTree );
|
||||
59
Src/ClassicExplorer/ExplorerBHO.rgs
Normal file
@@ -0,0 +1,59 @@
|
||||
HKCR
|
||||
{
|
||||
ClassicExplorer.ExplorerBHO.1 = s 'ExplorerBHO Class'
|
||||
{
|
||||
CLSID = s '{449D0D6E-2412-4E61-B68F-1CB625CD9E52}'
|
||||
}
|
||||
ClassicExplorer.ExplorerBHO = s 'ExplorerBHO Class'
|
||||
{
|
||||
CLSID = s '{449D0D6E-2412-4E61-B68F-1CB625CD9E52}'
|
||||
CurVer = s 'ClassicExplorer.ExplorerBHO.1'
|
||||
}
|
||||
NoRemove CLSID
|
||||
{
|
||||
ForceRemove {449D0D6E-2412-4E61-B68F-1CB625CD9E52} = s 'ExplorerBHO Class'
|
||||
{
|
||||
ProgID = s 'ClassicExplorer.ExplorerBHO.1'
|
||||
VersionIndependentProgID = s 'ClassicExplorer.ExplorerBHO'
|
||||
ForceRemove 'Programmable'
|
||||
InprocServer32 = s '%MODULE%'
|
||||
{
|
||||
val ThreadingModel = s 'Apartment'
|
||||
}
|
||||
'TypeLib' = s '{BF8D124A-A4E0-402F-8152-4EF377E62586}'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HKLM
|
||||
{
|
||||
NoRemove SOFTWARE
|
||||
{
|
||||
NoRemove Microsoft
|
||||
{
|
||||
NoRemove Windows
|
||||
{
|
||||
NoRemove CurrentVersion
|
||||
{
|
||||
NoRemove Explorer
|
||||
{
|
||||
NoRemove 'Browser Helper Objects'
|
||||
{
|
||||
ForceRemove '{449D0D6E-2412-4E61-B68F-1CB625CD9E52}'
|
||||
}
|
||||
}
|
||||
NoRemove Policies
|
||||
{
|
||||
NoRemove Ext
|
||||
{
|
||||
NoRemove CLSID
|
||||
{
|
||||
ForceRemove val {449D0D6E-2412-4E61-B68F-1CB625CD9E52} = s '2'
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
2285
Src/ClassicExplorer/ExplorerBand.cpp
Normal file
246
Src/ClassicExplorer/ExplorerBand.h
Normal file
@@ -0,0 +1,246 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// ExplorerBand.h : Declaration of the CExplorerBand
|
||||
|
||||
#pragma once
|
||||
#include "resource.h"
|
||||
#include "ClassicExplorer_h.h"
|
||||
#include "SettingsParser.h"
|
||||
#include <vector>
|
||||
|
||||
class CBandWindow: public CWindowImpl<CBandWindow>
|
||||
{
|
||||
public:
|
||||
|
||||
enum
|
||||
{
|
||||
ID_LAST=-1,
|
||||
ID_SEPARATOR=0,
|
||||
|
||||
// standard toolbar commands
|
||||
ID_SETTINGS=1,
|
||||
ID_GOUP,
|
||||
ID_CUT,
|
||||
ID_COPY,
|
||||
ID_PASTE,
|
||||
ID_PASTE_SHORTCUT,
|
||||
ID_DELETE,
|
||||
ID_PROPERTIES,
|
||||
ID_EMAIL,
|
||||
|
||||
ID_MOVETO,
|
||||
ID_COPYTO,
|
||||
ID_UNDO,
|
||||
ID_REDO,
|
||||
ID_SELECTALL,
|
||||
ID_DESELECT,
|
||||
ID_INVERT,
|
||||
ID_GOBACK,
|
||||
ID_GOFORWARD,
|
||||
ID_REFRESH,
|
||||
ID_STOP,
|
||||
ID_RENAME,
|
||||
ID_NEWFOLDER,
|
||||
ID_ZIPFOLDER,
|
||||
ID_NAVPANE,
|
||||
ID_DETAILSPANE,
|
||||
ID_PREVIEWPANE,
|
||||
ID_MAP_DRIVE,
|
||||
ID_DISCONNECT,
|
||||
ID_CUSTOMIZEFOLDER,
|
||||
ID_FOLDEROPTIONS,
|
||||
ID_VIEW_TILES,
|
||||
ID_VIEW_DETAILS,
|
||||
ID_VIEW_LIST,
|
||||
ID_VIEW_CONTENT,
|
||||
ID_VIEW_ICONS1,
|
||||
ID_VIEW_ICONS2,
|
||||
ID_VIEW_ICONS3,
|
||||
ID_VIEW_ICONS4,
|
||||
ID_SHOW_EXTENSIONS,
|
||||
ID_HIDDEN_FILES,
|
||||
ID_SYSTEM_FILES,
|
||||
|
||||
ID_CUSTOM=100,
|
||||
};
|
||||
|
||||
DECLARE_WND_CLASS(L"OpenShell.CBandWindow")
|
||||
|
||||
enum {
|
||||
BWM_UPDATEBUTTONS=WM_USER,
|
||||
BWM_UPDATETOOLBAR,
|
||||
};
|
||||
|
||||
BEGIN_MSG_MAP( CBandWindow )
|
||||
MESSAGE_HANDLER( WM_CREATE, OnCreate )
|
||||
MESSAGE_HANDLER( WM_DESTROY, OnDestroy )
|
||||
MESSAGE_HANDLER( WM_CLEAR, OnUpdateUI )
|
||||
MESSAGE_HANDLER( WM_COMMAND, OnCommand )
|
||||
MESSAGE_HANDLER( BWM_UPDATEBUTTONS, OnUpdateButtons )
|
||||
MESSAGE_HANDLER( BWM_UPDATETOOLBAR, OnUpdateToolbar )
|
||||
NOTIFY_CODE_HANDLER( NM_RCLICK, OnRClick )
|
||||
NOTIFY_CODE_HANDLER( TBN_GETINFOTIP, OnGetInfoTip )
|
||||
NOTIFY_CODE_HANDLER( TBN_DROPDOWN, OnDropDown )
|
||||
NOTIFY_CODE_HANDLER( RBN_CHEVRONPUSHED, OnChevron )
|
||||
END_MSG_MAP()
|
||||
|
||||
CBandWindow( void ) { m_ImgEnabled=m_ImgDisabled=NULL; m_MenuIconSize=0; }
|
||||
|
||||
HWND GetToolbar( void ) { return m_Toolbar.m_hWnd; }
|
||||
void SetBrowsers( IShellBrowser *pBrowser, IWebBrowser2 *pWebBrowser );
|
||||
void Clear( void );
|
||||
void UpdateToolbar( void );
|
||||
void EnableButton( int cmd, bool bEnable );
|
||||
void CheckButton( int cmd, bool bCheck );
|
||||
bool HasPanes( void ) const;
|
||||
bool HasFolderSettings( void ) const;
|
||||
|
||||
protected:
|
||||
// Handler prototypes:
|
||||
// LRESULT MessageHandler(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled);
|
||||
// LRESULT CommandHandler(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled);
|
||||
// LRESULT NotifyHandler(int idCtrl, LPNMHDR pnmh, BOOL& bHandled);
|
||||
LRESULT OnCreate( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnDestroy( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnUpdateUI( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnCommand( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnUpdateButtons( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnUpdateToolbar( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnRClick( int idCtrl, LPNMHDR pnmh, BOOL& bHandled );
|
||||
LRESULT OnGetInfoTip( int idCtrl, LPNMHDR pnmh, BOOL& bHandled );
|
||||
LRESULT OnDropDown( int idCtrl, LPNMHDR pnmh, BOOL& bHandled );
|
||||
LRESULT OnChevron( int idCtrl, LPNMHDR pnmh, BOOL& bHandled );
|
||||
|
||||
private:
|
||||
CWindow m_Toolbar;
|
||||
CWindow m_TreeParent;
|
||||
CComPtr<IShellBrowser> m_pBrowser;
|
||||
CComPtr<IWebBrowser2> m_pWebBrowser;
|
||||
CComPtr<IPropertyBag> m_pBrowserBag;
|
||||
HIMAGELIST m_ImgEnabled;
|
||||
HIMAGELIST m_ImgDisabled;
|
||||
int m_MenuIconSize;
|
||||
|
||||
struct StdToolbarItem
|
||||
{
|
||||
int id;
|
||||
const wchar_t *command;
|
||||
const wchar_t *link;
|
||||
const wchar_t *label; // text on the button
|
||||
const wchar_t *tip; // default tooltip
|
||||
const wchar_t *iconPath;
|
||||
const wchar_t *iconPathD;
|
||||
CString regName; // name of the registry value to check for enabled/checked state
|
||||
CString labelString, tipString; // additional storage for the strings
|
||||
const StdToolbarItem *submenu;
|
||||
mutable HBITMAP menuIcon;
|
||||
mutable HBITMAP menuIconD;
|
||||
mutable CString menuText;
|
||||
mutable bool bIconLoaded; // the menu icon is loaded
|
||||
bool bDisabled;
|
||||
bool bChecked;
|
||||
};
|
||||
|
||||
std::vector<StdToolbarItem> m_Items;
|
||||
std::vector<TBBUTTON> m_Buttons;
|
||||
CSettingsParser m_Parser;
|
||||
|
||||
void ParseToolbar( void );
|
||||
void ParseToolbarItem( const wchar_t *name, StdToolbarItem &item );
|
||||
void SendShellTabCommand( int command );
|
||||
HMENU CreateDropMenu( const StdToolbarItem *pItem );
|
||||
HMENU CreateDropMenuRec( const StdToolbarItem *pItem, std::vector<HMODULE> &modules, HMODULE hShell32 );
|
||||
void SendEmail( void );
|
||||
void SendToZip( void );
|
||||
void NewFolder( void );
|
||||
void ExecuteCommandFile( const wchar_t *pText );
|
||||
void ExecuteCustomCommand( const wchar_t *pCommand );
|
||||
void ViewByProperty( IFolderView2 *pView, const wchar_t *pProperty, bool bGroup );
|
||||
void UpdateBag( void );
|
||||
void UpdateFolderSettings( void );
|
||||
|
||||
static LRESULT CALLBACK ToolbarSubclassProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static HRESULT __stdcall BagWriteHook( IPropertyBag *pThis, LPCOLESTR pszPropName, VARIANT *pVar );
|
||||
};
|
||||
|
||||
|
||||
// CExplorerBand
|
||||
|
||||
class ATL_NO_VTABLE CExplorerBand :
|
||||
public CComObjectRootEx<CComSingleThreadModel>,
|
||||
public CComCoClass<CExplorerBand,&CLSID_ExplorerBand>,
|
||||
public IObjectWithSiteImpl<CExplorerBand>,
|
||||
public IDeskBand,
|
||||
public IDispEventImpl<1,CExplorerBand,&DIID_DWebBrowserEvents2,&LIBID_SHDocVw,1,1>
|
||||
{
|
||||
public:
|
||||
CExplorerBand( void );
|
||||
|
||||
DECLARE_REGISTRY_RESOURCEID_V2_WITHOUT_MODULE(IDR_EXPLORERBAND, CExplorerBand)
|
||||
|
||||
BEGIN_SINK_MAP( CExplorerBand )
|
||||
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_NAVIGATECOMPLETE2, OnNavigateComplete)
|
||||
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_COMMANDSTATECHANGE, OnCommandStateChange)
|
||||
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_ONQUIT, OnQuit)
|
||||
END_SINK_MAP()
|
||||
|
||||
BEGIN_COM_MAP(CExplorerBand)
|
||||
COM_INTERFACE_ENTRY( IOleWindow )
|
||||
COM_INTERFACE_ENTRY( IObjectWithSite )
|
||||
COM_INTERFACE_ENTRY_IID( IID_IDockingWindow, IDockingWindow )
|
||||
COM_INTERFACE_ENTRY_IID( IID_IDeskBand, IDeskBand )
|
||||
END_COM_MAP()
|
||||
|
||||
|
||||
|
||||
DECLARE_PROTECT_FINAL_CONSTRUCT()
|
||||
|
||||
HRESULT FinalConstruct()
|
||||
{
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
void FinalRelease()
|
||||
{
|
||||
}
|
||||
|
||||
public:
|
||||
|
||||
// IDeskBand
|
||||
STDMETHOD(GetBandInfo)( DWORD dwBandID, DWORD dwViewMode, DESKBANDINFO* pdbi );
|
||||
|
||||
// IObjectWithSite
|
||||
STDMETHOD(SetSite)( IUnknown* pUnkSite );
|
||||
|
||||
// IOleWindow
|
||||
STDMETHOD(GetWindow)( HWND* phwnd );
|
||||
STDMETHOD(ContextSensitiveHelp)( BOOL fEnterMode );
|
||||
|
||||
// IDockingWindow
|
||||
STDMETHOD(CloseDW)( unsigned long dwReserved );
|
||||
STDMETHOD(ResizeBorderDW)( const RECT* prcBorder, IUnknown* punkToolbarSite, BOOL fReserved );
|
||||
STDMETHOD(ShowDW)( BOOL fShow );
|
||||
|
||||
// DWebBrowserEvents2
|
||||
STDMETHOD(OnNavigateComplete)( IDispatch *pDisp, VARIANT *URL );
|
||||
STDMETHOD(OnCommandStateChange)( long Command, VARIANT_BOOL Enable );
|
||||
STDMETHOD(OnQuit)( void );
|
||||
|
||||
protected:
|
||||
bool m_bSubclassRebar; // the rebar needs subclassing
|
||||
bool m_bSubclassedRebar; // the rebar is subclassed
|
||||
bool m_bBandNewLine; // our band is on a new line (has RBBS_BREAK style)
|
||||
bool m_bHandleSetInfo; // mess with the RB_SETBANDINFO message
|
||||
CBandWindow m_BandWindow;
|
||||
CComPtr<IWebBrowser2> m_pWebBrowser;
|
||||
HWND m_TopWindow;
|
||||
|
||||
static LRESULT CALLBACK RebarSubclassProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
static LRESULT CALLBACK ParentSubclassProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
|
||||
friend class CBandWindow;
|
||||
};
|
||||
|
||||
OBJECT_ENTRY_AUTO(__uuidof(ExplorerBand), CExplorerBand)
|
||||
59
Src/ClassicExplorer/ExplorerBand.rgs
Normal file
@@ -0,0 +1,59 @@
|
||||
HKCR
|
||||
{
|
||||
ClassicExplorer.ExplorerBand.1 = s 'ExplorerBand Class'
|
||||
{
|
||||
CLSID = s '{553891B7-A0D5-4526-BE18-D3CE461D6310}'
|
||||
}
|
||||
ClassicExplorer.ExplorerBand = s 'ExplorerBand Class'
|
||||
{
|
||||
CLSID = s '{553891B7-A0D5-4526-BE18-D3CE461D6310}'
|
||||
CurVer = s 'ClassicExplorer.ExplorerBand.1'
|
||||
}
|
||||
NoRemove CLSID
|
||||
{
|
||||
ForceRemove {553891B7-A0D5-4526-BE18-D3CE461D6310} = s 'Classic Explorer Bar'
|
||||
{
|
||||
ProgID = s 'ClassicExplorer.ExplorerBand.1'
|
||||
VersionIndependentProgID = s 'ClassicExplorer.ExplorerBand'
|
||||
ForceRemove 'Programmable'
|
||||
InprocServer32 = s '%MODULE%'
|
||||
{
|
||||
val ThreadingModel = s 'Apartment'
|
||||
}
|
||||
'TypeLib' = s '{BF8D124A-A4E0-402F-8152-4EF377E62586}'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HKLM
|
||||
{
|
||||
NoRemove Software
|
||||
{
|
||||
NoRemove Microsoft
|
||||
{
|
||||
NoRemove 'Internet Explorer'
|
||||
{
|
||||
NoRemove Toolbar
|
||||
{
|
||||
ForceRemove val {553891B7-A0D5-4526-BE18-D3CE461D6310} = b ''
|
||||
}
|
||||
}
|
||||
NoRemove Windows
|
||||
{
|
||||
NoRemove CurrentVersion
|
||||
{
|
||||
NoRemove Policies
|
||||
{
|
||||
NoRemove Ext
|
||||
{
|
||||
NoRemove CLSID
|
||||
{
|
||||
ForceRemove val {553891B7-A0D5-4526-BE18-D3CE461D6310} = s '2'
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
2599
Src/ClassicExplorer/ExplorerL10N.ini
Normal file
765
Src/ClassicExplorer/SettingsUI.cpp
Normal file
@@ -0,0 +1,765 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ExplorerBand.h"
|
||||
#include "ExplorerBHO.h"
|
||||
#include "SettingsUI.h"
|
||||
#include "Settings.h"
|
||||
#include "SettingsUIHelper.h"
|
||||
#include "LanguageSettingsHelper.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "Translations.h"
|
||||
#include "resource.h"
|
||||
#include "dllmain.h"
|
||||
#include <dwmapi.h>
|
||||
|
||||
enum
|
||||
{
|
||||
SETTINGS_STYLE_WIN7=1,
|
||||
SETTINGS_STYLE_WIN8=2,
|
||||
SETTINGS_STYLE_MASK=SETTINGS_STYLE_WIN7|SETTINGS_STYLE_WIN8,
|
||||
};
|
||||
|
||||
static const CStdCommand g_StdCommands[]={
|
||||
{L"SEPARATOR",IDS_SEPARATOR_ITEM,IDS_SEPARATOR_TIP},
|
||||
{L"up",IDS_UP_ITEM,IDS_UP_TIP,L"UpItem",NULL,L"$Toolbar.GoUp",L",2",NULL,0,L",3"},
|
||||
{L"cut",IDS_CUT_ITEM,IDS_CUT_TIP,L"CutItem",NULL,L"$Toolbar.Cut",L"shell32.dll,16762"},
|
||||
{L"copy",IDS_COPY_ITEM,IDS_COPY_TIP,L"CopyItem",NULL,L"$Toolbar.Copy",L"shell32.dll,243"},
|
||||
{L"paste",IDS_PASTE_ITEM,IDS_PASTE_TIP,L"PasteItem",NULL,L"$Toolbar.Paste",L"shell32.dll,16763"},
|
||||
{L"paste_shortcut",IDS_PASTE_LNK_ITEM,IDS_PASTE_SHORTCUT_TIP,L"PasteShortcutItem",NULL,L"$Toolbar.PasteShortcut",L"shell32.dll,16763",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"paste_shortcut",IDS_PASTE_LNK_ITEM,IDS_PASTE_SHORTCUT_TIP,L"PasteShortcutItem",NULL,L"$Toolbar.PasteShortcut",L"imageres.dll,5301",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"delete",IDS_DELETE_ITEM,IDS_DELETE_TIP,L"DeleteItem",NULL,L"$Toolbar.Delete",L"shell32.dll,240"},
|
||||
{L"properties",IDS_PROPERTIES_ITEM,IDS_PROPERTIES_TIP,L"PropertiesItem",NULL,L"$Toolbar.Properties",L"shell32.dll,253"},
|
||||
{L"email",IDS_EMAIL_ITEM,IDS_EMAIL_TIP,L"EmailItem",NULL,L"$Toolbar.Email",L"shell32.dll,265"},
|
||||
{L"settings",IDS_SETTINGS_ITEM,IDS_SETTINGS_TIP,L"SettingsItem",NULL,L"$Toolbar.Settings",L",1"},
|
||||
{L"refresh",IDS_REFRESH_ITEM,IDS_REFRESH_TIP,L"RefreshItem",NULL,L"$Toolbar.Refresh",L"shell32.dll,16739"},
|
||||
{L"stop",IDS_STOP_ITEM,IDS_STOP_TIP,L"StopItem",NULL,L"$Toolbar.Stop",L"imageres.dll,98"},
|
||||
{L"rename",IDS_RENAME_ITEM,IDS_RENAME_TIP,L"RenameItem",NULL,L"$Toolbar.Rename",L"shell32.dll,242"},
|
||||
{L"customizefolder",IDS_CUSTOMIZE_ITEM,IDS_CUSTOMIZEFOLDER_TIP,L"CustomizeFolderItem",NULL,L"$Toolbar.CustomizeFolder",L"shell32.dll,274"},
|
||||
{L"folderoptions",IDS_FOLDEROPTIONS,IDS_FOLDEROPTIONS_TIP,L"FolderOptionsItem",NULL,L"$Toolbar.FolderOptions",L"imageres.dll,166"},
|
||||
{L"newfolder",IDS_NEWFOLDER_ITEM,IDS_NEWFOLDER_TIP,L"NewFolderItem",NULL,L"$Toolbar.NewFolder",L"shell32.dll,319"},
|
||||
{L"zipfolder",IDS_ZIP_ITEM,IDS_ZIP_TIP,L"ZipItem",NULL,L"$Toolbar.ZipFolder",L"imageres.dll,174"},
|
||||
{L"nav_pane",IDS_NAVPANE_ITEM,IDS_NAVPANE_TIP,L"NavPaneItem",NULL,L"$Toolbar.NavigationPane",L"shell32.dll,16755"},
|
||||
{L"details_pane",IDS_DETAILSPANE_ITEM,IDS_DETAILSPANE_TIP,L"DetailsPaneItem",NULL,L"$Toolbar.DetailsPane",L"shell32.dll,16759",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"details_pane",IDS_DETAILSPANE_ITEM,IDS_DETAILSPANE_TIP,L"DetailsPaneItem",NULL,L"$Toolbar.DetailsPane",L"shell32.dll,16814",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"preview_pane",IDS_PREVIEWPANE_ITEM,IDS_PREVIEWPANE_TIP,L"PreviewPaneItem",NULL,L"$Toolbar.PreviewPane",L"shell32.dll,16757"},
|
||||
{L"mapdrive",IDS_MAP_DRIVE_ITEM,IDS_MAP_DRIVE_TIP,L"MapDriveItem",NULL,L"$Toolbar.MapDrive",L"shell32.dll,16779"},
|
||||
{L"disconnect",IDS_DISCONNECT_ITEM,IDS_DISCONNECT_DRIVE_TIP,L"DisconnectItem",NULL,L"$Toolbar.DisconnectDrive",L"shell32.dll,11"},
|
||||
{L"viewtiles",IDS_VIEWTILES_ITEM,IDS_VIEWTILES_TIP,L"TilesItem",NULL,L"$Toolbar.Tiles",L"shell32.dll,62999"},
|
||||
{L"viewdetails",IDS_VIEWDETAILS_ITEM,IDS_VIEWDEATAILS_TIP,L"DetailsItem",NULL,L"$Toolbar.Details",L"shell32.dll,62998"},
|
||||
{L"viewlist",IDS_VIEWLIST_ITEM,IDS_VIEWLIST_TIP,L"ListItem",NULL,L"$Toolbar.List",L"shell32.dll,63000"},
|
||||
{L"viewcontent",IDS_VIEWCONTENT_ITEM,IDS_VIEWCONTENT_TIP,L"ContentItem",NULL,L"$Toolbar.Content",L"shell32.dll,63011"},
|
||||
{L"viewicons_small",IDS_VIEWICONS1_ITEM,IDS_VIEWICONS1_TIP,L"Icons1Item",NULL,L"$Toolbar.Small",L"shell32.dll,63010"},
|
||||
{L"viewicons_medium",IDS_VIEWICONS2_ITEM,IDS_VIEWICONS2_TIP,L"Icons2Item",NULL,L"$Toolbar.Medium",L"shell32.dll,63009"},
|
||||
{L"viewicons_large",IDS_VIEWICONS3_ITEM,IDS_VIEWICONS3_TIP,L"Icons3Item",NULL,L"$Toolbar.Large",L"shell32.dll,63008"},
|
||||
{L"viewicons_extralarge",IDS_VIEWICONS4_ITEM,IDS_VIEWICONS4_TIP,L"Icons4Item",NULL,L"$Toolbar.ExtraLarge",L"shell32.dll,63001"},
|
||||
{L"moveto",IDS_MOVETO_ITEM,IDS_MOVETO_TIP,L"MoveToItem",NULL,L"$Toolbar.MoveTo",L"",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"moveto",IDS_MOVETO_ITEM,IDS_MOVETO_TIP,L"MoveToItem",NULL,L"$Toolbar.MoveTo",L"imageres.dll,5303",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"copyto",IDS_COPYTO_ITEM,IDS_COPYTO_TIP,L"CopyToItem",NULL,L"$Toolbar.CopyTo",L"",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"copyto",IDS_COPYTO_ITEM,IDS_COPYTO_TIP,L"CopyToItem",NULL,L"$Toolbar.CopyTo",L"imageres.dll,5304",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"undo",IDS_UNDO_ITEM,IDS_UNDO_TIP,L"UndoItem",NULL,L"$Toolbar.Undo",L"",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"undo",IDS_UNDO_ITEM,IDS_UNDO_TIP,L"UndoItem",NULL,L"$Toolbar.Undo",L"imageres.dll,5315",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"redo",IDS_REDO_ITEM,IDS_REDO_TIP,L"RedoItem",NULL,L"$Toolbar.Redo",L"",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"redo",IDS_REDO_ITEM,IDS_REDO_TIP,L"RedoItem",NULL,L"$Toolbar.Redo",L"imageres.dll,5311",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"selectall",IDS_SELECTALL_ITEM,IDS_SELECTALL_TIP,L"SelectAllItem",NULL,L"$Toolbar.SelectAll",L"",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"selectall",IDS_SELECTALL_ITEM,IDS_SELECTALL_TIP,L"SelectAllItem",NULL,L"$Toolbar.SelectAll",L"imageres.dll,5308",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"deselect",IDS_DESELECT_ITEM,IDS_DESELECT_TIP,L"DeselectItem",NULL,L"$Toolbar.Deselect",L"",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"deselect",IDS_DESELECT_ITEM,IDS_DESELECT_TIP,L"DeselectItem",NULL,L"$Toolbar.Deselect",L"imageres.dll,5309",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"invertselection",IDS_INVERT_ITEM,IDS_INVERT_TIP,L"InvertItem",NULL,L"$Toolbar.InvertSelection",L"",NULL,SETTINGS_STYLE_WIN7},
|
||||
{L"invertselection",IDS_INVERT_ITEM,IDS_INVERT_TIP,L"InvertItem",NULL,L"$Toolbar.InvertSelection",L"imageres.dll,5310",NULL,SETTINGS_STYLE_WIN8},
|
||||
{L"back",IDS_BACK_ITEM,IDS_BACK_TIP,L"BackItem",NULL,L"$Toolbar.Back",L""},
|
||||
{L"forward",IDS_FORWARD_ITEM,IDS_FORWARD_TIP,L"ForwardItem",NULL,L"$Toolbar.Forward",L""},
|
||||
{L"show_extensions",IDS_SHOW_EXTENSIONS,IDS_SHOW_EXTENSIONS_TIP,L"ShowExtensionsItem",NULL,L"$Toolbar.ShowExtensions"},
|
||||
{L"hidden_files",IDS_HIDDEN_FILES,IDS_HIDDEN_FILES_TIP,L"HiddenFilesItem",NULL,L"$Toolbar.ShowHiddenFiles"},
|
||||
{L"system_files",IDS_SYSTEM_FILES,IDS_SYSTEM_FILES_TIP,L"SystemFilesItem",NULL,L"$Toolbar.ShowSystemFiles"},
|
||||
{L"open <folder name>",IDS_OPEN_ITEM,IDS_OPEN_TIP,L"OpenFolderItem",NULL,NULL,L""},
|
||||
{L"sortby <property>",IDS_SORYBY_ITEM,IDS_SORT_TIP,L"SortFolderItem",NULL,NULL,L""},
|
||||
{L"groupby <property>",IDS_GROUPBY_ITEM,IDS_GROUP_TIP,L"GroupFolderItem",NULL,NULL,L""},
|
||||
{L"",IDS_CUSTOM_ITEM,IDS_CUSTOM_TIP,L"CustomItem",NULL,NULL,L""},
|
||||
{NULL},
|
||||
};
|
||||
|
||||
static const KNOWNFOLDERID *g_CommonLinks[]=
|
||||
{
|
||||
&FOLDERID_ComputerFolder,
|
||||
&FOLDERID_DesktopRoot,
|
||||
&FOLDERID_Desktop,
|
||||
&FOLDERID_Documents,
|
||||
&FOLDERID_Downloads,
|
||||
&FOLDERID_Favorites,
|
||||
&FOLDERID_Games,
|
||||
&FOLDERID_Links,
|
||||
&FOLDERID_Music,
|
||||
&FOLDERID_Pictures,
|
||||
&FOLDERID_Videos,
|
||||
&FOLDERID_Profile,
|
||||
&FOLDERID_HomeGroup,
|
||||
&FOLDERID_Libraries,
|
||||
&FOLDERID_DocumentsLibrary,
|
||||
&FOLDERID_MusicLibrary,
|
||||
&FOLDERID_PicturesLibrary,
|
||||
&FOLDERID_VideosLibrary,
|
||||
&FOLDERID_NetworkFolder,
|
||||
NULL,
|
||||
};
|
||||
|
||||
const wchar_t *g_DefaultToolbar=
|
||||
L"Items=UpItem, NavPaneItem, FolderOptionsItem, CutItem, CopyItem, PasteItem, DeleteItem, PropertiesItem, EmailItem, SEPARATOR, SettingsItem\n"
|
||||
L"UpItem.Command=up\n"
|
||||
L"UpItem.Tip=$Toolbar.GoUp\n"
|
||||
L"UpItem.Icon=,2\n"
|
||||
L"UpItem.IconDisabled=,3\n"
|
||||
L"NavPaneItem.Command=nav_pane\n"
|
||||
L"NavPaneItem.Tip=$Toolbar.NavigationPane\n"
|
||||
L"NavPaneItem.Icon=shell32.dll,16755\n"
|
||||
L"FolderOptionsItem.Command=folderoptions\n"
|
||||
L"FolderOptionsItem.Tip=$Toolbar.FolderOptions\n"
|
||||
L"FolderOptionsItem.Icon=imageres.dll,166\n"
|
||||
L"FolderOptionsItem.Items=ShowExtensionsItem, HiddenFilesItem, SystemFilesItem\n"
|
||||
L"ShowExtensionsItem.Command=show_extensions\n"
|
||||
L"ShowExtensionsItem.Label=$Toolbar.ShowExtensions\n"
|
||||
L"ShowExtensionsItem.Icon=none\n"
|
||||
L"HiddenFilesItem.Command=hidden_files\n"
|
||||
L"HiddenFilesItem.Label=$Toolbar.ShowHiddenFiles\n"
|
||||
L"HiddenFilesItem.Icon=none\n"
|
||||
L"SystemFilesItem.Command=system_files\n"
|
||||
L"SystemFilesItem.Label=$Toolbar.ShowSystemFiles\n"
|
||||
L"SystemFilesItem.Icon=none\n"
|
||||
L"CutItem.Command=cut\n"
|
||||
L"CutItem.Tip=$Toolbar.Cut\n"
|
||||
L"CutItem.Icon=shell32.dll,16762\n"
|
||||
L"CopyItem.Command=copy\n"
|
||||
L"CopyItem.Tip=$Toolbar.Copy\n"
|
||||
L"CopyItem.Icon=shell32.dll,243\n"
|
||||
L"PasteItem.Command=paste\n"
|
||||
L"PasteItem.Tip=$Toolbar.Paste\n"
|
||||
L"PasteItem.Icon=shell32.dll,16763\n"
|
||||
L"DeleteItem.Command=delete\n"
|
||||
L"DeleteItem.Tip=$Toolbar.Delete\n"
|
||||
L"DeleteItem.Icon=shell32.dll,240\n"
|
||||
L"PropertiesItem.Command=properties\n"
|
||||
L"PropertiesItem.Tip=$Toolbar.Properties\n"
|
||||
L"PropertiesItem.Icon=shell32.dll,253\n"
|
||||
L"EmailItem.Command=email\n"
|
||||
L"EmailItem.Tip=$Toolbar.Email\n"
|
||||
L"EmailItem.Icon=shell32.dll,265\n"
|
||||
L"SettingsItem.Command=settings\n"
|
||||
L"SettingsItem.Tip=$Toolbar.Settings\n"
|
||||
L"SettingsItem.Icon=,1\n";
|
||||
|
||||
const wchar_t *g_DefaultToolbar2=
|
||||
L"Items=NavPaneItem, FolderOptionsItem, CutItem, CopyItem, PasteItem, DeleteItem, PropertiesItem, EmailItem, SEPARATOR, SettingsItem\n"
|
||||
L"NavPaneItem.Command=nav_pane\n"
|
||||
L"NavPaneItem.Tip=$Toolbar.NavigationPane\n"
|
||||
L"NavPaneItem.Icon=shell32.dll,16755\n"
|
||||
L"FolderOptionsItem.Command=folderoptions\n"
|
||||
L"FolderOptionsItem.Tip=$Toolbar.FolderOptions\n"
|
||||
L"FolderOptionsItem.Icon=imageres.dll,166\n"
|
||||
L"FolderOptionsItem.Items=ShowExtensionsItem, HiddenFilesItem, SystemFilesItem\n"
|
||||
L"ShowExtensionsItem.Command=show_extensions\n"
|
||||
L"ShowExtensionsItem.Label=$Toolbar.ShowExtensions\n"
|
||||
L"ShowExtensionsItem.Icon=none\n"
|
||||
L"HiddenFilesItem.Command=hidden_files\n"
|
||||
L"HiddenFilesItem.Label=$Toolbar.ShowHiddenFiles\n"
|
||||
L"HiddenFilesItem.Icon=none\n"
|
||||
L"SystemFilesItem.Command=system_files\n"
|
||||
L"SystemFilesItem.Label=$Toolbar.ShowSystemFiles\n"
|
||||
L"SystemFilesItem.Icon=none\n"
|
||||
L"CutItem.Command=cut\n"
|
||||
L"CutItem.Tip=$Toolbar.Cut\n"
|
||||
L"CutItem.Icon=shell32.dll,16762\n"
|
||||
L"CopyItem.Command=copy\n"
|
||||
L"CopyItem.Tip=$Toolbar.Copy\n"
|
||||
L"CopyItem.Icon=shell32.dll,243\n"
|
||||
L"PasteItem.Command=paste\n"
|
||||
L"PasteItem.Tip=$Toolbar.Paste\n"
|
||||
L"PasteItem.Icon=shell32.dll,16763\n"
|
||||
L"DeleteItem.Command=delete\n"
|
||||
L"DeleteItem.Tip=$Toolbar.Delete\n"
|
||||
L"DeleteItem.Icon=shell32.dll,240\n"
|
||||
L"PropertiesItem.Command=properties\n"
|
||||
L"PropertiesItem.Tip=$Toolbar.Properties\n"
|
||||
L"PropertiesItem.Icon=shell32.dll,253\n"
|
||||
L"EmailItem.Command=email\n"
|
||||
L"EmailItem.Tip=$Toolbar.Email\n"
|
||||
L"EmailItem.Icon=shell32.dll,265\n"
|
||||
L"SettingsItem.Command=settings\n"
|
||||
L"SettingsItem.Tip=$Toolbar.Settings\n"
|
||||
L"SettingsItem.Icon=,1\n";
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
class CEditToolbarDlg: public CEditCustomItemDlg
|
||||
{
|
||||
public:
|
||||
CEditToolbarDlg( CTreeItem *pItem, bool bNoLinks, std::vector<HMODULE> &modules ): CEditCustomItemDlg(pItem,modules) { m_bNoLinks=bNoLinks; }
|
||||
|
||||
BEGIN_MSG_MAP( CEditToolbarDlg )
|
||||
MESSAGE_HANDLER( WM_INITDIALOG, OnInitDialog )
|
||||
COMMAND_ID_HANDLER( IDOK, OnOK )
|
||||
COMMAND_ID_HANDLER( IDCANCEL, OnCancel )
|
||||
COMMAND_HANDLER( IDC_COMBOCOMMAND, CBN_KILLFOCUS, OnCommandChanged )
|
||||
COMMAND_HANDLER( IDC_COMBOCOMMAND, CBN_SELENDOK, OnCommandChanged )
|
||||
COMMAND_HANDLER( IDC_BUTTONCOMMAND, BN_CLICKED, OnBrowseCommand )
|
||||
COMMAND_HANDLER( IDC_BUTTONLINK, BN_CLICKED, OnBrowseLink )
|
||||
COMMAND_HANDLER( IDC_BUTTONICON, BN_CLICKED, OnBrowseIcon )
|
||||
COMMAND_HANDLER( IDC_BUTTONICOND, BN_CLICKED, OnBrowseIcon )
|
||||
COMMAND_HANDLER( IDC_COMBOLINK, CBN_KILLFOCUS, OnLinkChanged )
|
||||
COMMAND_HANDLER( IDC_COMBOLINK, CBN_SELENDOK, OnLinkChanged )
|
||||
COMMAND_HANDLER( IDC_EDITICON, EN_KILLFOCUS, OnIconChanged )
|
||||
COMMAND_HANDLER( IDC_EDITICOND, EN_KILLFOCUS, OnIconDChanged )
|
||||
COMMAND_HANDLER( IDC_BUTTONRESET, BN_CLICKED, OnReset )
|
||||
CHAIN_MSG_MAP( CEditCustomItemDlg )
|
||||
END_MSG_MAP()
|
||||
|
||||
virtual BEGIN_RESIZE_MAP
|
||||
RESIZE_CONTROL(IDC_COMBOCOMMAND,MOVE_SIZE_X)
|
||||
RESIZE_CONTROL(IDC_COMBOLINK,MOVE_SIZE_X)
|
||||
RESIZE_CONTROL(IDC_BUTTONCOMMAND,MOVE_MOVE_X)
|
||||
RESIZE_CONTROL(IDC_BUTTONLINK,MOVE_MOVE_X)
|
||||
RESIZE_CONTROL(IDC_EDITLABEL,MOVE_SIZE_X)
|
||||
RESIZE_CONTROL(IDC_EDITTIP,MOVE_SIZE_X)
|
||||
RESIZE_CONTROL(IDC_EDITICON,MOVE_SIZE_X)
|
||||
RESIZE_CONTROL(IDC_BUTTONICON,MOVE_MOVE_X)
|
||||
RESIZE_CONTROL(IDC_EDITICOND,MOVE_SIZE_X)
|
||||
RESIZE_CONTROL(IDC_BUTTONICOND,MOVE_MOVE_X)
|
||||
RESIZE_CONTROL(IDOK,MOVE_MOVE_X)
|
||||
RESIZE_CONTROL(IDCANCEL,MOVE_MOVE_X)
|
||||
END_RESIZE_MAP
|
||||
|
||||
protected:
|
||||
// Handler prototypes:
|
||||
// LRESULT MessageHandler(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled);
|
||||
// LRESULT CommandHandler(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled);
|
||||
// LRESULT NotifyHandler(int idCtrl, LPNMHDR pnmh, BOOL& bHandled);
|
||||
LRESULT OnInitDialog( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnOK( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
LRESULT OnCommandChanged( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
LRESULT OnLinkChanged( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
LRESULT OnIconChanged( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
LRESULT OnIconDChanged( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
LRESULT OnBrowseCommand( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
LRESULT OnBrowseLink( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
LRESULT OnBrowseIcon( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
LRESULT OnReset( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
|
||||
private:
|
||||
bool m_bNoLinks;
|
||||
int m_Style;
|
||||
};
|
||||
|
||||
LRESULT CEditToolbarDlg::OnInitDialog( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled )
|
||||
{
|
||||
m_Style=GetWinVersion()>=WIN_VER_WIN8?SETTINGS_STYLE_WIN8:SETTINGS_STYLE_WIN7;
|
||||
CWindow commands=GetDlgItem(IDC_COMBOCOMMAND);
|
||||
CWindow links=GetDlgItem(IDC_COMBOLINK);
|
||||
InitDialog(commands,g_StdCommands,m_Style,SETTINGS_STYLE_MASK,links,g_CommonLinks);
|
||||
SetDlgItemText(IDC_EDITLABEL,m_pItem->label);
|
||||
SetDlgItemText(IDC_EDITTIP,m_pItem->tip);
|
||||
SetDlgItemText(IDC_EDITICON,m_pItem->icon);
|
||||
SetDlgItemText(IDC_EDITICOND,m_pItem->iconD);
|
||||
|
||||
GetDlgItem(IDC_BUTTONRESET).EnableWindow(m_pItem->pStdCommand && *m_pItem->pStdCommand->name);
|
||||
|
||||
UpdateIcons(IDC_ICONN,IDC_ICOND);
|
||||
|
||||
CWindow tooltip=CreateWindowEx(WS_EX_TOPMOST|WS_EX_TOOLWINDOW|WS_EX_TRANSPARENT,TOOLTIPS_CLASS,NULL,WS_POPUP|TTS_NOPREFIX|TTS_ALWAYSTIP,0,0,0,0,m_hWnd,NULL,g_Instance,NULL);
|
||||
tooltip.SendMessage(TTM_SETMAXTIPWIDTH,0,GetSystemMetrics(SM_CXSCREEN)/2);
|
||||
|
||||
TOOLINFO tool={sizeof(tool),TTF_SUBCLASS|TTF_IDISHWND,m_hWnd,(UINT_PTR)(HWND)commands};
|
||||
CString str=LoadStringEx(IDS_COMMAND_TIP);
|
||||
tool.lpszText=(LPWSTR)(LPCWSTR)str;
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
tool.uId=(UINT_PTR)(HWND)commands.GetWindow(GW_CHILD);
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
|
||||
str=LoadStringEx(IDS_LINK_TIP);
|
||||
tool.lpszText=(LPWSTR)(LPCWSTR)str;
|
||||
tool.uId=(UINT_PTR)(HWND)links;
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
tool.uId=(UINT_PTR)(HWND)links.GetWindow(GW_CHILD);
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
|
||||
str=LoadStringEx(IDS_TEXT_TIP);
|
||||
tool.lpszText=(LPWSTR)(LPCWSTR)str;
|
||||
tool.uId=(UINT_PTR)(HWND)GetDlgItem(IDC_EDITLABEL);
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
|
||||
str=LoadStringEx(IDS_TIP_TIP);
|
||||
tool.lpszText=(LPWSTR)(LPCWSTR)str;
|
||||
tool.uId=(UINT_PTR)(HWND)GetDlgItem(IDC_EDITTIP);
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
|
||||
str=LoadStringEx(IDS_ICON_TIP);
|
||||
tool.lpszText=(LPWSTR)(LPCWSTR)str;
|
||||
tool.uId=(UINT_PTR)(HWND)GetDlgItem(IDC_EDITICON);
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
|
||||
str=LoadStringEx(IDS_ICOND_TIP);
|
||||
tool.lpszText=(LPWSTR)(LPCWSTR)str;
|
||||
tool.uId=(UINT_PTR)(HWND)GetDlgItem(IDC_EDITICOND);
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
|
||||
str=LoadStringEx(IDS_RESTORE_TIP);
|
||||
tool.lpszText=(LPWSTR)(LPCWSTR)str;
|
||||
tool.uId=(UINT_PTR)(HWND)GetDlgItem(IDC_BUTTONRESET);
|
||||
tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnOK( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
GetDlgItemText(IDC_EDITLABEL,m_pItem->label);
|
||||
m_pItem->label.TrimLeft();
|
||||
m_pItem->label.TrimRight();
|
||||
GetDlgItemText(IDC_EDITTIP,m_pItem->tip);
|
||||
m_pItem->tip.TrimLeft();
|
||||
m_pItem->tip.TrimRight();
|
||||
|
||||
return CEditCustomItemDlg::OnOK(wNotifyCode,wID,hWndCtl,bHandled);
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnCommandChanged( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
CString text=GetComboText(wNotifyCode,wID);
|
||||
if (text==m_pItem->command) return 0;
|
||||
m_pItem->SetCommand(text,g_StdCommands,m_Style,SETTINGS_STYLE_MASK);
|
||||
GetDlgItem(IDC_BUTTONRESET).EnableWindow(m_pItem->pStdCommand && *m_pItem->pStdCommand->name);
|
||||
UpdateIcons(IDC_ICONN,IDC_ICOND);
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnLinkChanged( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
CString text=GetComboText(wNotifyCode,wID);
|
||||
if (text==m_pItem->link) return 0;
|
||||
m_pItem->link=text;
|
||||
UpdateIcons(IDC_ICONN,IDC_ICOND);
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnIconChanged( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
CString text;
|
||||
GetDlgItemText(IDC_EDITICON,text);
|
||||
text.TrimLeft();
|
||||
text.TrimRight();
|
||||
if (text==m_pItem->icon) return 0;
|
||||
m_pItem->icon=text;
|
||||
UpdateIcons(IDC_ICONN,IDC_ICOND);
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnIconDChanged( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
CString text;
|
||||
GetDlgItemText(IDC_EDITICOND,text);
|
||||
text.TrimLeft();
|
||||
text.TrimRight();
|
||||
if (text==m_pItem->iconD) return 0;
|
||||
m_pItem->iconD=text;
|
||||
UpdateIcons(IDC_ICONN,IDC_ICOND);
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnBrowseCommand( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
wchar_t text[_MAX_PATH];
|
||||
GetDlgItemText(IDC_COMBOCOMMAND,text,_countof(text));
|
||||
if (BrowseCommandHelper(m_hWnd,text))
|
||||
{
|
||||
SetDlgItemText(IDC_COMBOCOMMAND,text);
|
||||
SendMessage(WM_COMMAND,MAKEWPARAM(IDC_COMBOCOMMAND,CBN_KILLFOCUS));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnBrowseLink( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
wchar_t text[_MAX_PATH];
|
||||
GetDlgItemText(IDC_COMBOLINK,text,_countof(text));
|
||||
if (BrowseLinkHelper(m_hWnd,text,false))
|
||||
{
|
||||
SetDlgItemText(IDC_COMBOLINK,text);
|
||||
SendMessage(WM_COMMAND,MAKEWPARAM(IDC_COMBOLINK,CBN_KILLFOCUS));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnBrowseIcon( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
wchar_t text[_MAX_PATH];
|
||||
if (wID==IDC_BUTTONICON) wID=IDC_EDITICON;
|
||||
if (wID==IDC_BUTTONICOND) wID=IDC_EDITICOND;
|
||||
GetDlgItemText(wID,text,_countof(text));
|
||||
if (wID==IDC_EDITICOND && !*text)
|
||||
GetDlgItemText(IDC_EDITICON,text,_countof(text));
|
||||
if (BrowseIconHelper(m_hWnd,text))
|
||||
{
|
||||
SetDlgItemText(wID,text);
|
||||
SendMessage(WM_COMMAND,MAKEWPARAM(wID,EN_KILLFOCUS));
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CEditToolbarDlg::OnReset( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
if (!m_pItem->pStdCommand || !*m_pItem->pStdCommand->name)
|
||||
return 0;
|
||||
m_pItem->link.Empty();
|
||||
m_pItem->label=m_pItem->pStdCommand->label;
|
||||
m_pItem->tip=m_pItem->pStdCommand->tip;
|
||||
m_pItem->icon=m_pItem->pStdCommand->icon;
|
||||
m_pItem->iconD=m_pItem->pStdCommand->iconD;
|
||||
SendDlgItemMessage(IDC_COMBOLINK,CB_SETCURSEL,-1);
|
||||
SetDlgItemText(IDC_EDITLABEL,m_pItem->label);
|
||||
SetDlgItemText(IDC_EDITTIP,m_pItem->tip);
|
||||
SetDlgItemText(IDC_EDITICON,m_pItem->icon);
|
||||
SetDlgItemText(IDC_EDITICOND,m_pItem->iconD);
|
||||
|
||||
UpdateIcons(IDC_ICONN,IDC_ICOND);
|
||||
return 0;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
class CCustomToolbarDlg: public CCustomTreeDlg
|
||||
{
|
||||
public:
|
||||
CCustomToolbarDlg( void ): CCustomTreeDlg(false,g_StdCommands,GetWinVersion()>=WIN_VER_WIN8?SETTINGS_STYLE_WIN8:SETTINGS_STYLE_WIN7,SETTINGS_STYLE_MASK) {}
|
||||
|
||||
protected:
|
||||
virtual void ParseTreeItemExtra( CTreeItem *pItem, CSettingsParser &parser );
|
||||
virtual void SerializeItemExtra( CTreeItem *pItem, std::vector<wchar_t> &stringBuilder );
|
||||
virtual bool EditItem( CTreeItem *pItem, HWND tree, HTREEITEM hItem, std::vector<HMODULE> &modules );
|
||||
};
|
||||
|
||||
void CCustomToolbarDlg::ParseTreeItemExtra( CTreeItem *pItem, CSettingsParser &parser )
|
||||
{
|
||||
wchar_t text[256];
|
||||
Sprintf(text,_countof(text),L"%s.IconDisabled",pItem->name);
|
||||
pItem->iconD=parser.FindSetting(text,L"");
|
||||
}
|
||||
|
||||
void CCustomToolbarDlg::SerializeItemExtra( CTreeItem *pItem, std::vector<wchar_t> &stringBuilder )
|
||||
{
|
||||
if (!pItem->iconD.IsEmpty())
|
||||
{
|
||||
wchar_t text[2048];
|
||||
Sprintf(text,_countof(text),L"%s.IconDisabled=%s\n",pItem->name,pItem->iconD);
|
||||
AppendString(stringBuilder,text);
|
||||
}
|
||||
}
|
||||
|
||||
bool CCustomToolbarDlg::EditItem( CTreeItem *pItem, HWND tree, HTREEITEM hItem, std::vector<HMODULE> &modules )
|
||||
{
|
||||
bool bNoLinks=(TreeView_GetParent(tree,hItem) || TreeView_GetChild(tree,hItem));
|
||||
return CEditToolbarDlg(pItem,bNoLinks,modules).Run(m_hWnd,IDD_CUSTOMTOOLBAR);
|
||||
}
|
||||
|
||||
class CCustomToolbarPanel: public ISettingsPanel
|
||||
{
|
||||
public:
|
||||
virtual HWND Create( HWND parent );
|
||||
virtual HWND Activate( CSetting *pGroup, const RECT &rect, bool bReset );
|
||||
virtual bool Validate( HWND parent ) { return true; }
|
||||
|
||||
private:
|
||||
static CCustomToolbarDlg s_Dialog;
|
||||
};
|
||||
|
||||
CCustomToolbarDlg CCustomToolbarPanel::s_Dialog;
|
||||
|
||||
HWND CCustomToolbarPanel::Create( HWND parent )
|
||||
{
|
||||
if (!s_Dialog.m_hWnd)
|
||||
s_Dialog.Create(parent,LoadDialogEx(IDD_CUSTOMTREE));
|
||||
return s_Dialog.m_hWnd;
|
||||
}
|
||||
|
||||
HWND CCustomToolbarPanel::Activate( CSetting *pGroup, const RECT &rect, bool bReset )
|
||||
{
|
||||
s_Dialog.SetGroup(pGroup,bReset);
|
||||
s_Dialog.SetWindowPos(HWND_TOP,&rect,SWP_SHOWWINDOW);
|
||||
return s_Dialog.m_hWnd;
|
||||
}
|
||||
|
||||
static CCustomToolbarPanel g_CustomToolbarPanel;
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static CSetting g_Settings[]={
|
||||
{L"Basic",CSetting::TYPE_GROUP,IDS_BASIC_SETTINGS},
|
||||
{L"EnableSettings",CSetting::TYPE_BOOL,0,0,1,CSetting::FLAG_HIDDEN|CSetting::FLAG_NOSAVE},
|
||||
{L"ProcessWhiteList",CSetting::TYPE_STRING,0,0,L"",CSetting::FLAG_HIDDEN|CSetting::FLAG_NOSAVE},
|
||||
{L"ProcessBlackList",CSetting::TYPE_STRING,0,0,L"",CSetting::FLAG_HIDDEN|CSetting::FLAG_NOSAVE},
|
||||
{L"NoInitialToolbar",CSetting::TYPE_BOOL,0,0,0,CSetting::FLAG_HIDDEN|CSetting::FLAG_NOSAVE},
|
||||
|
||||
{L"NavigationPane",CSetting::TYPE_GROUP,IDS_NAVIGATION_SETTINGS},
|
||||
{L"TreeStyle",CSetting::TYPE_INT,IDS_TREE_STYLE,IDS_TREE_STYLE_TIP,2,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"XPClassic",CSetting::TYPE_RADIO,IDS_XPCLASSIC,IDS_XPCLASSIC_TIP},
|
||||
{L"XPSimple",CSetting::TYPE_RADIO,IDS_XPSIMPLE,IDS_XPSIMPLE_TIP},
|
||||
{L"Vista",CSetting::TYPE_RADIO,IDS_VISTA,IDS_VISTA_TIP},
|
||||
{L"HScrollbar",CSetting::TYPE_INT,IDS_SCROLLBAR,IDS_SCROLLBAR_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"Default",CSetting::TYPE_RADIO,IDS_SCROLLBAR_DEFAULT,IDS_SCROLLBAR_DEFAULT_TIP},
|
||||
{L"Off",CSetting::TYPE_RADIO,IDS_SCROLLBAR_OFF,IDS_SCROLLBAR_OFF_TIP},
|
||||
{L"On",CSetting::TYPE_RADIO,IDS_SCROLLBAR_ON,IDS_SCROLLBAR_ON_TIP},
|
||||
{L"NoFadeButtons",CSetting::TYPE_BOOL,IDS_NO_FADE,IDS_NO_FADE_TIP,0,CSetting::FLAG_WARM,L"TreeStyle"},
|
||||
{L"TreeItemSpacing",CSetting::TYPE_INT,IDS_TREE_SPACING,IDS_TREE_SPACING_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"FullIndent",CSetting::TYPE_BOOL,IDS_FULL_INDENT,IDS_FULL_INDENT_TIP,0,CSetting::FLAG_WARM,L"TreeStyle"},
|
||||
{L"AutoNavigate",CSetting::TYPE_INT,IDS_NAVIGATE,IDS_NAVIGATE_TIP,0,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"Default",CSetting::TYPE_RADIO,IDS_NAV_DEFAULT,IDS_NAV_DEFAULT_TIP},
|
||||
{L"KeyboardOnly",CSetting::TYPE_RADIO,IDS_NAV_KBD,IDS_NAV_KBD_TIP},
|
||||
{L"Always",CSetting::TYPE_RADIO,IDS_NAV_ALWAYS,IDS_NAV_ALWAYS_TIP},
|
||||
{L"AutoNavDelay",CSetting::TYPE_INT,IDS_NAV_DELAY,IDS_NAV_DELAY_TIP,100,CSetting::FLAG_WARM,L"AutoNavigate"},
|
||||
{L"AltEnter",CSetting::TYPE_BOOL,IDS_ALT_ENTER,IDS_ALT_ENTER_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"FixFolderScroll",CSetting::TYPE_BOOL,IDS_FIX_SCROLL,IDS_FIX_SCROLL_TIP,1,CSetting::FLAG_WARM},
|
||||
|
||||
{L"TitleBar",CSetting::TYPE_GROUP,IDS_TITLE_SETTINGS},
|
||||
{L"ShowCaption",CSetting::TYPE_BOOL,IDS_SHOW_CAPTION,IDS_SHOW_CAPTION_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"ShowIcon",CSetting::TYPE_BOOL,IDS_SHOW_ICON,IDS_SHOW_ICON_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"DisableBreadcrumbs",CSetting::TYPE_BOOL,IDS_NO_BREADCRUMBS,IDS_NO_BREADCRUMBS_TIP,0,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"AddressBarHistory",CSetting::TYPE_INT,IDS_ADDRESS_HISTORY,IDS_ADDRESS_HISTORY_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"NormalHistory",CSetting::TYPE_RADIO,IDS_NORMAL_HISTORY,IDS_NORMAL_HISTORY_TIP},
|
||||
{L"SimplePath",CSetting::TYPE_RADIO,IDS_SIMPLE_PATH,IDS_SIMPLE_PATH_TIP},
|
||||
{L"ExtendedPath",CSetting::TYPE_RADIO,IDS_EXTENDED_PATH,IDS_EXTENDED_PATH_TIP},
|
||||
{L"HideSearch",CSetting::TYPE_BOOL,IDS_HIDE_SEARCH,IDS_HIDE_SEARCH_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"AddressAltD",CSetting::TYPE_STRING,IDS_ALT_D,IDS_ALT_D_TIP,L"",CSetting::FLAG_WARM},
|
||||
{L"UpHotkey2",CSetting::TYPE_HOTKEY_ANY,IDS_UP_HOTKEY,IDS_UP_HOTKEY_TIP,0,CSetting::FLAG_WARM},
|
||||
|
||||
{L"UpButton",CSetting::TYPE_GROUP,IDS_UP_SETTINGS},
|
||||
{L"ShowUpButton",CSetting::TYPE_INT,IDS_SHOW_UP,IDS_SHOW_UP_TIP,2,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"DontShow",CSetting::TYPE_RADIO,IDS_DONT_SHOW,IDS_DONT_SHOW_TIP},
|
||||
{L"BeforeBack",CSetting::TYPE_RADIO,IDS_BEFORE_BACK,IDS_BEFORE_BACK_TIP},
|
||||
{L"AfterBack",CSetting::TYPE_RADIO,IDS_AFTER_BACK,IDS_AFTER_BACK_TIP},
|
||||
{L"UpIconNormal",CSetting::TYPE_ICON,IDS_UP_NORMAL,IDS_UP_NORMAL_TIP,L",4",CSetting::FLAG_WARM,L"ShowUpButton"},
|
||||
{L"UpIconPressed",CSetting::TYPE_ICON,IDS_UP_PRESSED,IDS_UP_PRESSED_TIP,L",5",CSetting::FLAG_WARM,L"ShowUpButton"},
|
||||
{L"UpIconHot",CSetting::TYPE_ICON,IDS_UP_HOT,IDS_UP_HOT_TIP,L",6",CSetting::FLAG_WARM,L"ShowUpButton"},
|
||||
{L"UpIconDisabled",CSetting::TYPE_ICON,IDS_UP_DISABLED,IDS_UP_DISABLED_TIP,L",7",CSetting::FLAG_WARM,L"ShowUpButton"},
|
||||
{L"UpIconSize",CSetting::TYPE_INT,IDS_UP_SIZE,IDS_UP_SIZE_TIP,0,CSetting::FLAG_WARM,L"ShowUpButton"}, // 30 for DPI<120 and 36 for DPI>=120
|
||||
{L"UpHotkey",CSetting::TYPE_HOTKEY_ANY,IDS_UP_HOTKEY,IDS_UP_HOTKEY_TIP,0,CSetting::FLAG_WARM},
|
||||
|
||||
{L"Toolbar",CSetting::TYPE_GROUP,IDS_TOOLBAR_SETTINGS},
|
||||
{L"UseBigButtons",CSetting::TYPE_BOOL,IDS_BIG_BUTTONS,IDS_BIG_BUTTONS_TIP,1,CSetting::FLAG_WARM},
|
||||
{L"SmallIconSize",CSetting::TYPE_INT,IDS_SMALL_SIZE,IDS_SMALL_SIZE_TIP,-1,CSetting::FLAG_WARM}, // 16 for DPI<120 and 24 for DPI>=120
|
||||
{L"LargeIconSize",CSetting::TYPE_INT,IDS_LARGE_SIZE,IDS_LARGE_SIZE_TIP,-1,CSetting::FLAG_WARM}, // 24 for DPI<120 and 32 for DPI>=120
|
||||
{L"MenuIconSize",CSetting::TYPE_INT,IDS_MENU_SIZE,IDS_MENU_SIZE_TIP,16,CSetting::FLAG_WARM},
|
||||
{L"ToolbarListMode",CSetting::TYPE_BOOL,IDS_LIST_MODE,IDS_LIST_MODE_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"SameSizeButtons",CSetting::TYPE_BOOL,IDS_SAME_SIZE,IDS_SAME_SIZE_TIP,0,CSetting::FLAG_WARM,L"ToolbarListMode=0"},
|
||||
{L"ResizeableToolbar",CSetting::TYPE_BOOL,IDS_RESIZEABLE,IDS_RESIZEABLE_TIP,0,CSetting::FLAG_WARM},
|
||||
|
||||
{L"CustomToolbar",CSetting::TYPE_GROUP,IDS_BUTTONS_SETTINGS,0,0,0,NULL,NULL,&g_CustomToolbarPanel},
|
||||
{L"ToolbarItems",CSetting::TYPE_MULTISTRING,0,0,g_DefaultToolbar,CSetting::FLAG_WARM},
|
||||
|
||||
{L"StatusBar",CSetting::TYPE_GROUP,IDS_STATUS_SETTINGS},
|
||||
{L"ShowFreeSpace",CSetting::TYPE_BOOL,IDS_FREE_SPACE,IDS_FREE_SPACE_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"ShowInfoTip",CSetting::TYPE_BOOL,IDS_INFO_TIP,IDS_INFO_TIP_TIP,1,CSetting::FLAG_WARM,L"ShowFreeSpace"},
|
||||
{L"ForceRefreshWin7",CSetting::TYPE_BOOL,IDS_FORCE_REFRESH,IDS_FORCE_REFRESH_TIP,1,CSetting::FLAG_WARM,L"ShowFreeSpace"},
|
||||
|
||||
{L"StatusBar8",CSetting::TYPE_GROUP,IDS_STATUS_SETTINGS},
|
||||
{L"ShowStatusBar",CSetting::TYPE_BOOL,IDS_SHOWSTATUSBAR,IDS_SHOWSTATUSBAR_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"ShowFreeSpace2",CSetting::TYPE_BOOL,IDS_FREE_SPACE,IDS_FREE_SPACE_TIP,1,CSetting::FLAG_WARM,L"ShowStatusBar",L"ShowStatusBar"},
|
||||
{L"ShowZone",CSetting::TYPE_BOOL,IDS_SHOW_ZONE,IDS_SHOW_ZONE_TIP,1,CSetting::FLAG_WARM,L"ShowStatusBar",L"ShowStatusBar"},
|
||||
{L"ShowInfoTip2",CSetting::TYPE_BOOL,IDS_INFO_TIP,IDS_INFO_TIP_TIP,1,CSetting::FLAG_WARM,L"ShowStatusBar",L"ShowStatusBar"},
|
||||
{L"StatusBarFont",CSetting::TYPE_FONT,IDS_STATUS_FONT,IDS_STATUS_FONT_TIP,L"Segoe UI, normal, 9",CSetting::FLAG_WARM,L"ShowStatusBar",L"ShowStatusBar"},
|
||||
|
||||
{L"FilePane",CSetting::TYPE_GROUP,IDS_FILEPANE_SETTINGS},
|
||||
{L"ShareOverlay",CSetting::TYPE_BOOL,IDS_SHARE,IDS_SHARE_TIP,0,CSetting::FLAG_COLD|CSetting::FLAG_BASIC},
|
||||
{L"ShareOverlayIcon",CSetting::TYPE_ICON,IDS_SHARE_ICON,IDS_SHARE_ICON_TIP,L"%windir%\\system32\\imageres.dll,164",CSetting::FLAG_COLD,L"ShareOverlay",L"ShareOverlay"},
|
||||
{L"ShareOverlayHidden",CSetting::TYPE_BOOL,IDS_SHARE_HIDDEN,IDS_SHARE_HIDDEN_TIP,0,CSetting::FLAG_COLD,L"ShareOverlay",L"ShareOverlay"},
|
||||
{L"ShareExplorer",CSetting::TYPE_BOOL,IDS_SHARE_EXPLORER,IDS_SHARE_EXPLORER_TIP,1,CSetting::FLAG_COLD,L"ShareOverlay",L"ShareOverlay"},
|
||||
{L"ShowHeaders",CSetting::TYPE_BOOL,IDS_HEADERS,IDS_HEADERS_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"HideScrollTip",CSetting::TYPE_BOOL,IDS_SCROLLTIP,IDS_SCROLLTIP_TIP,0,CSetting::FLAG_WARM},
|
||||
|
||||
{L"FileOperation",CSetting::TYPE_GROUP,IDS_FILE_SETTINGS},
|
||||
{L"ReplaceFileUI",CSetting::TYPE_BOOL,IDS_FILE_UI,IDS_FILE_UI_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"ReplaceFolderUI",CSetting::TYPE_BOOL,IDS_FOLDER_UI,IDS_FOLDER_UI_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"OverwriteAlertLevel",CSetting::TYPE_INT,IDS_ALERT_LEVEL,IDS_ALERT_LEVEL_TIP,0,CSetting::FLAG_WARM,L"ReplaceFileUI",L"ReplaceFileUI"},
|
||||
{L"NoAlert",CSetting::TYPE_RADIO,IDS_NO_ALERT,IDS_NO_ALERT_TIP},
|
||||
{L"SystemFiles",CSetting::TYPE_RADIO,IDS_SYS_FILES,IDS_SYS_FILES_TIP},
|
||||
{L"ReadOnlyFiles",CSetting::TYPE_RADIO,IDS_RO_FILES,IDS_RO_FILES_TIP},
|
||||
{L"EnableMore",CSetting::TYPE_BOOL,IDS_MORE,IDS_MORE_TIP,0,CSetting::FLAG_WARM},
|
||||
{L"MoreProgressDelay",CSetting::TYPE_INT,IDS_MORE_DELAY,IDS_MORE_DELAY_TIP,-1,CSetting::FLAG_WARM,L"EnableMore",L"EnableMore"}, // 500 for Windows 7 Aero, and 0 otherwise
|
||||
{L"FileExplorer",CSetting::TYPE_BOOL,IDS_FILE_EXPLORER,IDS_FILE_EXPLORER_TIP,1,CSetting::FLAG_COLD},
|
||||
|
||||
{L"Language",CSetting::TYPE_GROUP,IDS_LANGUAGE_SETTINGS,0,0,0,NULL,NULL,GetLanguageSettings(COMPONENT_EXPLORER)},
|
||||
{L"Language",CSetting::TYPE_STRING,0,0,L"",CSetting::FLAG_COLD|CSetting::FLAG_SHARED},
|
||||
|
||||
{NULL}
|
||||
};
|
||||
|
||||
void UpgradeSettings( bool bShared )
|
||||
{
|
||||
}
|
||||
|
||||
void UpdateSettings( void )
|
||||
{
|
||||
HDC hdc=GetDC(NULL);
|
||||
int dpi=GetDeviceCaps(hdc,LOGPIXELSY);
|
||||
ReleaseDC(NULL,hdc);
|
||||
UpdateSetting(L"SmallIconSize",CComVariant((dpi>=120)?24:16),false);
|
||||
UpdateSetting(L"LargeIconSize",CComVariant((dpi>=120)?32:24),false);
|
||||
UpdateSetting(L"UpIconSize",CComVariant((dpi>=120)?36:30),false);
|
||||
FindSetting(L"UpHotkey2")->pLinkTo=FindSetting(L"UpHotkey");
|
||||
|
||||
if (GetWinVersion()>=WIN_VER_WIN8)
|
||||
{
|
||||
// Windows 8
|
||||
HideSettingGroup(L"StatusBar",true);
|
||||
HideSetting(L"ShowFreeSpace",true);
|
||||
FindSetting(L"ShowFreeSpace2")->pLinkTo=FindSetting(L"ShowFreeSpace");
|
||||
FindSetting(L"ShowInfoTip2")->pLinkTo=FindSetting(L"ShowInfoTip");
|
||||
|
||||
HideSettingGroup(L"UpButton",true);
|
||||
UpdateSetting(L"ShowUpButton",CComVariant(0),false); HideSetting(L"ShowUpButton",true);
|
||||
|
||||
HideSettingGroup(L"FileOperation",true);
|
||||
UpdateSetting(L"ReplaceFileUI",CComVariant(0),false); HideSetting(L"ReplaceFileUI",true);
|
||||
UpdateSetting(L"ReplaceFolderUI",CComVariant(0),false); HideSetting(L"ReplaceFolderUI",true);
|
||||
|
||||
UpdateSetting(L"ShowCaption",CComVariant(0),false); HideSetting(L"ShowCaption",true);
|
||||
UpdateSetting(L"ShowIcon",CComVariant(0),false); HideSetting(L"ShowIcon",true);
|
||||
UpdateSetting(L"FixFolderScroll",CComVariant(0),false);
|
||||
UpdateSetting(L"ToolbarItems",CComVariant(g_DefaultToolbar2),false);
|
||||
|
||||
if (GetWinVersion()>=WIN_VER_WIN10)
|
||||
{
|
||||
FindSetting(L"TreeStyle")[1].flags|=CSetting::FLAG_HIDDEN;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Windows 7
|
||||
int delay=0;
|
||||
BOOL comp;
|
||||
if (SUCCEEDED(DwmIsCompositionEnabled(&comp)) && comp)
|
||||
delay=500;
|
||||
UpdateSetting(L"MoreProgressDelay",CComVariant(delay),false);
|
||||
HideSetting(L"UpHotkey2",true);
|
||||
HideSettingGroup(L"StatusBar8",true);
|
||||
}
|
||||
|
||||
CRegKey regKey;
|
||||
wchar_t language[100]=L"";
|
||||
if (regKey.Open(HKEY_LOCAL_MACHINE,L"Software\\OpenShell\\OpenShell",KEY_READ|KEY_WOW64_64KEY)==ERROR_SUCCESS)
|
||||
{
|
||||
ULONG size=_countof(language);
|
||||
if (regKey.QueryStringValue(L"DefaultLanguage",language,&size)!=ERROR_SUCCESS)
|
||||
language[0]=0;
|
||||
}
|
||||
UpdateSetting(L"Language",language,false);
|
||||
}
|
||||
|
||||
static bool g_bCopyHook0; // initial state of the copy hook before the settings are edited
|
||||
|
||||
void InitSettings( void )
|
||||
{
|
||||
InitSettings(g_Settings,COMPONENT_EXPLORER,NULL);
|
||||
g_bCopyHook0=GetWinVersion()<WIN_VER_WIN8 && (GetSettingBool(L"ReplaceFileUI") || GetSettingBool(L"ReplaceFolderUI") || GetSettingBool(L"EnableMore"));
|
||||
}
|
||||
|
||||
void ClosingSettings( HWND hWnd, int flags, int command )
|
||||
{
|
||||
if (command==IDOK)
|
||||
{
|
||||
bool bCopyHook=GetWinVersion()<WIN_VER_WIN8 && (GetSettingBool(L"ReplaceFileUI") || GetSettingBool(L"ReplaceFolderUI") || GetSettingBool(L"EnableMore"));
|
||||
|
||||
if ((flags&CSetting::FLAG_COLD) || (bCopyHook && !g_bCopyHook0))
|
||||
MessageBox(hWnd,LoadStringEx(IDS_NEW_SETTINGS2),LoadStringEx(IDS_APP_TITLE),MB_OK|MB_ICONWARNING);
|
||||
else if (flags&CSetting::FLAG_WARM)
|
||||
MessageBox(hWnd,LoadStringEx(IDS_NEW_SETTINGS1),LoadStringEx(IDS_APP_TITLE),MB_OK|MB_ICONINFORMATION);
|
||||
}
|
||||
}
|
||||
|
||||
void SettingChangedCallback( const CSetting *pSetting )
|
||||
{
|
||||
}
|
||||
|
||||
void EditSettings( void )
|
||||
{
|
||||
STARTUPINFO startupInfo={sizeof(startupInfo)};
|
||||
PROCESS_INFORMATION processInfo;
|
||||
memset(&processInfo,0,sizeof(processInfo));
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(g_Instance,path,_countof(path));
|
||||
wchar_t *end=PathFindFileName(path);
|
||||
*end=0;
|
||||
Strcpy(end,(int)(path+_countof(path)-end),L"ClassicExplorerSettings.exe");
|
||||
if (CreateProcess(NULL,path,NULL,NULL,TRUE,0,NULL,NULL,&startupInfo,&processInfo))
|
||||
{
|
||||
CloseHandle(processInfo.hProcess);
|
||||
CloseHandle(processInfo.hThread);
|
||||
}
|
||||
}
|
||||
|
||||
void ShowSettingsMenu( HWND parent, int x, int y )
|
||||
{
|
||||
HMENU menu=CreatePopupMenu();
|
||||
AppendMenu(menu,MF_STRING,CBandWindow::ID_SETTINGS,FindTranslation(L"Toolbar.Settings",L"Classic Explorer Settings"));
|
||||
int size=16;
|
||||
HBITMAP shellBmp=NULL;
|
||||
HICON icon=(HICON)LoadImage(g_Instance,MAKEINTRESOURCE(IDI_APPICON),IMAGE_ICON,size,size,LR_DEFAULTCOLOR);
|
||||
if (icon)
|
||||
{
|
||||
shellBmp=BitmapFromIcon(icon,size,NULL,true);
|
||||
MENUITEMINFO mii={sizeof(mii)};
|
||||
mii.fMask=MIIM_BITMAP;
|
||||
mii.hbmpItem=shellBmp;
|
||||
SetMenuItemInfo(menu,CBandWindow::ID_SETTINGS,FALSE,&mii);
|
||||
}
|
||||
MENUINFO info={sizeof(info),MIM_STYLE,MNS_CHECKORBMP};
|
||||
SetMenuInfo(menu,&info);
|
||||
|
||||
DWORD pos=GetMessagePos();
|
||||
if (!GetSettingBool(L"EnableSettings"))
|
||||
EnableMenuItem(menu,0,MF_BYPOSITION|MF_GRAYED);
|
||||
int res=TrackPopupMenu(menu,TPM_RIGHTBUTTON|TPM_RETURNCMD,x,y,0,parent,NULL);
|
||||
DestroyMenu(menu);
|
||||
if (shellBmp) DeleteObject(shellBmp);
|
||||
if (res==CBandWindow::ID_SETTINGS)
|
||||
EditSettings();
|
||||
}
|
||||
|
||||
void ShowExplorerSettings( void )
|
||||
{
|
||||
WaitDllInitThread();
|
||||
if (!GetSettingBool(L"EnableSettings"))
|
||||
return;
|
||||
wchar_t title[100];
|
||||
DWORD ver=GetVersionEx(g_Instance);
|
||||
if (ver)
|
||||
Sprintf(title,_countof(title),LoadStringEx(IDS_SETTINGS_TITLE_VER),ver>>24,(ver>>16)&0xFF,ver&0xFFFF);
|
||||
else
|
||||
Sprintf(title,_countof(title),LoadStringEx(IDS_SETTINGS_TITLE));
|
||||
EditSettings(title,true,0);
|
||||
}
|
||||
|
||||
bool DllImportSettingsXml( const wchar_t *fname )
|
||||
{
|
||||
return ImportSettingsXml(fname);
|
||||
}
|
||||
|
||||
bool DllExportSettingsXml( const wchar_t *fname )
|
||||
{
|
||||
return ExportSettingsXml(fname);
|
||||
}
|
||||
|
||||
#ifndef _WIN64
|
||||
bool DllSaveAdmx( const char *admxFile, const char *admlFile, const char *docFile, const wchar_t *language )
|
||||
{
|
||||
WaitDllInitThread();
|
||||
HMODULE dll=NULL;
|
||||
if (language[0])
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetCurrentDirectory(_countof(path),path);
|
||||
PathAppend(path,language);
|
||||
PathAddExtension(path,L".dll");
|
||||
dll=LoadLibraryEx(path,NULL,LOAD_LIBRARY_AS_DATAFILE|LOAD_LIBRARY_AS_IMAGE_RESOURCE);
|
||||
}
|
||||
LoadTranslationResources(dll,NULL);
|
||||
return SaveAdmx(COMPONENT_EXPLORER,admxFile,admlFile,docFile);
|
||||
}
|
||||
#endif
|
||||
9
Src/ClassicExplorer/SettingsUI.h
Normal file
@@ -0,0 +1,9 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
void InitSettings( void );
|
||||
void EditSettings( void );
|
||||
void ShowSettingsMenu( HWND parent, int x, int y );
|
||||
134
Src/ClassicExplorer/ShareOverlay.cpp
Normal file
@@ -0,0 +1,134 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// ShareOverlay.cpp : Implementation of CShareOverlay
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ShareOverlay.h"
|
||||
|
||||
// CShareOverlay - adds an overlay icon to the shared folders
|
||||
|
||||
bool CShareOverlay::s_bEnabled=false;
|
||||
bool CShareOverlay::s_bShowHidden=false;
|
||||
int CShareOverlay::s_Index;
|
||||
wchar_t CShareOverlay::s_IconPath[_MAX_PATH];
|
||||
|
||||
CShareOverlay::CShareOverlay( void )
|
||||
{
|
||||
SHGetDesktopFolder(&m_pDesktop);
|
||||
m_pShareInfo=NULL;
|
||||
m_ShareCount=0;
|
||||
m_UpdateTime=0;
|
||||
InitializeCriticalSection(&m_Section);
|
||||
}
|
||||
|
||||
void CShareOverlay::FinalRelease( void )
|
||||
{
|
||||
DeleteCriticalSection(&m_Section);
|
||||
if (m_pShareInfo)
|
||||
NetApiBufferFree(m_pShareInfo);
|
||||
m_pShareInfo=NULL;
|
||||
}
|
||||
|
||||
void CShareOverlay::InitOverlay( const wchar_t *icon, bool showHidden )
|
||||
{
|
||||
s_bEnabled=true;
|
||||
if (icon)
|
||||
{
|
||||
Strcpy(s_IconPath,_countof(s_IconPath),icon);
|
||||
wchar_t *c=wcsrchr(s_IconPath,',');
|
||||
if (c)
|
||||
{
|
||||
*c=0;
|
||||
s_Index=-_wtol(c+1);
|
||||
}
|
||||
else
|
||||
s_Index=0;
|
||||
}
|
||||
else
|
||||
{
|
||||
Strcpy(s_IconPath,_countof(s_IconPath),L"%windir%\\system32\\imageres.dll");
|
||||
s_Index=-164;
|
||||
}
|
||||
DoEnvironmentSubst(s_IconPath,_countof(s_IconPath));
|
||||
s_bShowHidden=showHidden;
|
||||
}
|
||||
|
||||
HRESULT CShareOverlay::_InternalQueryInterface( REFIID iid, void** ppvObject )
|
||||
{
|
||||
if (iid==IID_IUnknown)
|
||||
{
|
||||
AddRef();
|
||||
*ppvObject=static_cast<IUnknown*>(this);
|
||||
return S_OK;
|
||||
}
|
||||
if (iid==IID_IShellIconOverlayIdentifier && s_bEnabled)
|
||||
{
|
||||
// only support IShellIconOverlayIdentifier if s_bEnabled is true
|
||||
AddRef();
|
||||
*ppvObject=static_cast<IShellIconOverlayIdentifier*>(this);
|
||||
return S_OK;
|
||||
}
|
||||
*ppvObject=NULL;
|
||||
return E_NOINTERFACE;
|
||||
}
|
||||
|
||||
STDMETHODIMP CShareOverlay::IsMemberOf( LPCWSTR pwszPath, DWORD dwAttrib )
|
||||
{
|
||||
EnterCriticalSection(&m_Section);
|
||||
UpdateShareInfo();
|
||||
HRESULT res=S_FALSE;
|
||||
if (m_pShareInfo)
|
||||
{
|
||||
for (DWORD i=0;i<m_ShareCount;i++)
|
||||
{
|
||||
if (!(m_pShareInfo[i].shi502_type&STYPE_SPECIAL) && _wcsicmp(pwszPath,m_pShareInfo[i].shi502_path)==0)
|
||||
{
|
||||
if (s_bShowHidden)
|
||||
{
|
||||
res=S_OK;
|
||||
break;
|
||||
}
|
||||
int len=Strlen(m_pShareInfo[i].shi502_netname);
|
||||
if (len==0 || m_pShareInfo[i].shi502_netname[len-1]!='$')
|
||||
{
|
||||
res=S_OK;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
LeaveCriticalSection(&m_Section);
|
||||
return res;
|
||||
}
|
||||
|
||||
STDMETHODIMP CShareOverlay::GetOverlayInfo( LPWSTR pwszIconFile, int cchMax, int * pIndex, DWORD * pdwFlags )
|
||||
{
|
||||
Strcpy(pwszIconFile,cchMax,s_IconPath);
|
||||
*pIndex=s_Index;
|
||||
*pdwFlags=ISIOI_ICONFILE;
|
||||
if (s_Index)
|
||||
*pdwFlags|=ISIOI_ICONINDEX;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CShareOverlay::GetPriority( int * pIPriority )
|
||||
{
|
||||
*pIPriority=0;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
void CShareOverlay::UpdateShareInfo( void )
|
||||
{
|
||||
int time=GetTickCount();
|
||||
if (time-m_UpdateTime<5000)
|
||||
return;
|
||||
m_UpdateTime=time;
|
||||
if (m_pShareInfo)
|
||||
NetApiBufferFree(m_pShareInfo);
|
||||
m_pShareInfo=NULL;
|
||||
DWORD countAll;
|
||||
if (NetShareEnum(NULL,502,(BYTE**)&m_pShareInfo,MAX_PREFERRED_LENGTH,&m_ShareCount,&countAll,NULL)!=NERR_Success)
|
||||
m_ShareCount=0;
|
||||
}
|
||||
60
Src/ClassicExplorer/ShareOverlay.h
Normal file
@@ -0,0 +1,60 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// ShareOverlay.h : Declaration of the CShareOverlay
|
||||
|
||||
#pragma once
|
||||
#include "resource.h" // main symbols
|
||||
#include <lm.h>
|
||||
|
||||
#include "ClassicExplorer_h.h"
|
||||
|
||||
// CShareOverlay
|
||||
|
||||
class ATL_NO_VTABLE CShareOverlay :
|
||||
public CComObjectRootEx<CComSingleThreadModel>,
|
||||
public CComCoClass<CShareOverlay, &CLSID_ShareOverlay>,
|
||||
public IShellIconOverlayIdentifier
|
||||
{
|
||||
public:
|
||||
CShareOverlay( void );
|
||||
|
||||
DECLARE_REGISTRY_RESOURCEID_V2_WITHOUT_MODULE(IDR_SHAREOVERLAY, CShareOverlay)
|
||||
|
||||
DECLARE_PROTECT_FINAL_CONSTRUCT()
|
||||
|
||||
HRESULT FinalConstruct( void )
|
||||
{
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
void FinalRelease( void );
|
||||
|
||||
public:
|
||||
|
||||
HRESULT _InternalQueryInterface( REFIID iid, void** ppvObject );
|
||||
|
||||
// IShellIconOverlayIdentifier
|
||||
STDMETHOD (IsMemberOf)( LPCWSTR pwszPath, DWORD dwAttrib );
|
||||
STDMETHOD (GetOverlayInfo)( LPWSTR pwszIconFile, int cchMax, int * pIndex, DWORD * pdwFlags );
|
||||
STDMETHOD (GetPriority)( int * pIPriority );
|
||||
|
||||
static void InitOverlay( const wchar_t *icon, bool showHidden );
|
||||
|
||||
private:
|
||||
CComPtr<IShellFolder> m_pDesktop;
|
||||
CRITICAL_SECTION m_Section;
|
||||
SHARE_INFO_502 *m_pShareInfo;
|
||||
DWORD m_ShareCount;
|
||||
int m_UpdateTime;
|
||||
|
||||
void UpdateShareInfo( void );
|
||||
|
||||
static bool s_bEnabled;
|
||||
static bool s_bShowHidden;
|
||||
static int s_Index;
|
||||
static wchar_t s_IconPath[_MAX_PATH];
|
||||
};
|
||||
|
||||
OBJECT_ENTRY_AUTO(__uuidof(ShareOverlay), CShareOverlay)
|
||||
49
Src/ClassicExplorer/ShareOverlay.rgs
Normal file
@@ -0,0 +1,49 @@
|
||||
HKCR
|
||||
{
|
||||
ClassicExplorer.ShareOverlay.1 = s 'ShareOverlay Class'
|
||||
{
|
||||
CLSID = s '{594D4122-1F87-41E2-96C7-825FB4796516}'
|
||||
}
|
||||
ClassicExplorer.ShareOverlay = s 'ShareOverlay Class'
|
||||
{
|
||||
CLSID = s '{594D4122-1F87-41E2-96C7-825FB4796516}'
|
||||
CurVer = s 'ClassicExplorer.ShareOverlay.1'
|
||||
}
|
||||
NoRemove CLSID
|
||||
{
|
||||
ForceRemove {594D4122-1F87-41E2-96C7-825FB4796516} = s 'ShareOverlay Class'
|
||||
{
|
||||
ProgID = s 'ClassicExplorer.ShareOverlay.1'
|
||||
VersionIndependentProgID = s 'ClassicExplorer.ShareOverlay'
|
||||
ForceRemove 'Programmable'
|
||||
InprocServer32 = s '%MODULE%'
|
||||
{
|
||||
val ThreadingModel = s 'Apartment'
|
||||
}
|
||||
'TypeLib' = s '{BF8D124A-A4E0-402F-8152-4EF377E62586}'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HKLM
|
||||
{
|
||||
NoRemove SOFTWARE
|
||||
{
|
||||
NoRemove Microsoft
|
||||
{
|
||||
NoRemove Windows
|
||||
{
|
||||
NoRemove CurrentVersion
|
||||
{
|
||||
NoRemove Explorer
|
||||
{
|
||||
NoRemove ShellIconOverlayIdentifiers
|
||||
{
|
||||
ForceRemove ShareOverlay = s '{594D4122-1F87-41E2-96C7-825FB4796516}'
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
278
Src/ClassicExplorer/dllmain.cpp
Normal file
@@ -0,0 +1,278 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// dllmain.cpp : Implementation of DllMain.
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "resource.h"
|
||||
#include "..\Lib\resource.h"
|
||||
#include "dllmain.h"
|
||||
#include "ShareOverlay.h"
|
||||
#include "SettingsUI.h"
|
||||
#include "Settings.h"
|
||||
#include "Translations.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "FNVHash.h"
|
||||
#include <uxtheme.h>
|
||||
#include <dwmapi.h>
|
||||
|
||||
#pragma comment(linker, \
|
||||
"\"/manifestdependency:type='Win32' "\
|
||||
"name='Microsoft.Windows.Common-Controls' "\
|
||||
"version='6.0.0.0' "\
|
||||
"processorArchitecture='*' "\
|
||||
"publicKeyToken='6595b64144ccf1df' "\
|
||||
"language='*'\"")
|
||||
|
||||
CClassicExplorerModule _AtlModule;
|
||||
bool g_bLogLevel;
|
||||
|
||||
void InitClassicCopyProcess( void );
|
||||
void InitClassicCopyThread( void );
|
||||
void FreeClassicCopyThread( void );
|
||||
|
||||
bool g_bHookCopyThreads;
|
||||
bool g_bExplorerExe;
|
||||
LPCWSTR g_LoadedSettingsAtom;
|
||||
|
||||
static int g_LoadDialogs[]=
|
||||
{
|
||||
IDD_SETTINGS,0x04000000,
|
||||
IDD_SETTINGSTREE,0x04000000,
|
||||
IDD_BROWSEFORICON,0x04000000,
|
||||
IDD_LANGUAGE,0x04000000,
|
||||
IDD_CUSTOMTOOLBAR,0x04000000,
|
||||
IDD_CUSTOMTREE,0x04000000,
|
||||
IDD_PROGRESS,0x04000004,
|
||||
0
|
||||
};
|
||||
|
||||
struct FindChild
|
||||
{
|
||||
const wchar_t *className;
|
||||
HWND hWnd;
|
||||
};
|
||||
|
||||
static BOOL CALLBACK EnumChildProc( HWND hwnd, LPARAM lParam )
|
||||
{
|
||||
FindChild &find=*(FindChild*)lParam;
|
||||
wchar_t name[256];
|
||||
GetClassName(hwnd,name,_countof(name));
|
||||
if (_wcsicmp(name,find.className)!=0) return TRUE;
|
||||
find.hWnd=hwnd;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
HWND FindChildWindow( HWND hwnd, const wchar_t *className )
|
||||
{
|
||||
FindChild find={className};
|
||||
EnumChildWindows(hwnd,EnumChildProc,(LPARAM)&find);
|
||||
return find.hWnd;
|
||||
}
|
||||
|
||||
static DWORD g_TlsIndex;
|
||||
|
||||
TlsData *GetTlsData( void )
|
||||
{
|
||||
void *pData=TlsGetValue(g_TlsIndex);
|
||||
if (!pData)
|
||||
{
|
||||
pData=(void*)LocalAlloc(LPTR,sizeof(TlsData));
|
||||
memset(pData,0,sizeof(TlsData));
|
||||
TlsSetValue(g_TlsIndex,pData);
|
||||
}
|
||||
return (TlsData*)pData;
|
||||
}
|
||||
|
||||
static HANDLE g_DllInitThread;
|
||||
|
||||
static DWORD CALLBACK DllInitThread( void* )
|
||||
{
|
||||
{
|
||||
g_bLogLevel=false;
|
||||
CRegKey regKey;
|
||||
if (regKey.Open(HKEY_CURRENT_USER,L"Software\\OpenShell\\ClassicExplorer\\Settings",KEY_READ|KEY_WOW64_64KEY)==ERROR_SUCCESS)
|
||||
{
|
||||
DWORD log;
|
||||
if (regKey.QueryDWORDValue(L"LogLevel",log)==ERROR_SUCCESS)
|
||||
g_bLogLevel=log!=0;
|
||||
}
|
||||
}
|
||||
InitSettings();
|
||||
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(g_Instance,path,_countof(path));
|
||||
*PathFindFileName(path)=0;
|
||||
wchar_t fname[_MAX_PATH];
|
||||
Sprintf(fname,_countof(fname),L"%sExplorerL10N.ini",path);
|
||||
CString language=GetSettingString(L"Language");
|
||||
ParseTranslations(fname,language);
|
||||
|
||||
HINSTANCE resInstance=LoadTranslationDll(language);
|
||||
|
||||
LoadTranslationResources(resInstance,g_LoadDialogs);
|
||||
|
||||
if (resInstance)
|
||||
FreeLibrary(resInstance);
|
||||
|
||||
if (GetSettingBool(L"ShareOverlay") && (g_bExplorerExe || !GetSettingBool(L"ShareExplorer")))
|
||||
CShareOverlay::InitOverlay(GetSettingString(L"ShareOverlayIcon"),GetSettingBool(L"ShareOverlayHidden"));
|
||||
return 0;
|
||||
}
|
||||
|
||||
void WaitDllInitThread( void )
|
||||
{
|
||||
ATLASSERT(g_DllInitThread);
|
||||
WaitForSingleObject(g_DllInitThread,INFINITE);
|
||||
}
|
||||
|
||||
// DLL Entry Point
|
||||
extern "C" BOOL WINAPI DllMain( HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved )
|
||||
{
|
||||
if (dwReason==DLL_PROCESS_ATTACH)
|
||||
{
|
||||
g_Instance=hInstance;
|
||||
g_TlsIndex=TlsAlloc();
|
||||
if (g_TlsIndex==TLS_OUT_OF_INDEXES)
|
||||
return FALSE; // TLS failure
|
||||
|
||||
CRegKey regSettings, regSettingsUser, regPolicy, regPolicyUser;
|
||||
bool bUpgrade=OpenSettingsKeys(COMPONENT_EXPLORER,regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
|
||||
enum
|
||||
{
|
||||
SETTING_SHARE_OVERLAY,
|
||||
SETTING_SHARE_EXPLORER,
|
||||
SETTING_FILE_EXPLORER,
|
||||
SETTING_REPLACE_FILE,
|
||||
SETTING_REPLACE_FOLDER,
|
||||
SETTING_MORE,
|
||||
SETTING_WHITE_LIST,
|
||||
SETTING_BLACK_LIST,
|
||||
};
|
||||
|
||||
CSetting settings[]={
|
||||
{L"ShareOverlay",CSetting::TYPE_BOOL,0,0,0},
|
||||
{L"ShareExplorer",CSetting::TYPE_BOOL,0,0,1},
|
||||
{L"FileExplorer",CSetting::TYPE_BOOL,0,0,1},
|
||||
{L"ReplaceFileUI",CSetting::TYPE_BOOL,0,0,1},
|
||||
{L"ReplaceFolderUI",CSetting::TYPE_BOOL,0,0,1},
|
||||
{L"EnableMore",CSetting::TYPE_BOOL,0,0,0},
|
||||
{L"ProcessWhiteList",CSetting::TYPE_STRING,0,0,L""},
|
||||
{L"ProcessBlackList",CSetting::TYPE_STRING,0,0,L""},
|
||||
{NULL}
|
||||
};
|
||||
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(NULL,path,_countof(path));
|
||||
const wchar_t *exe=PathFindFileName(path);
|
||||
g_bExplorerExe=(_wcsicmp(exe,L"explorer.exe")==0 || _wcsicmp(exe,L"verclsid.exe")==0);
|
||||
bool bReplaceUI=false;
|
||||
if (GetWinVersion()<=WIN_VER_WIN7)
|
||||
{
|
||||
settings[SETTING_REPLACE_FILE].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
settings[SETTING_REPLACE_FOLDER].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
settings[SETTING_MORE].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
bReplaceUI=(GetSettingBool(settings[SETTING_REPLACE_FILE]) || GetSettingBool(settings[SETTING_REPLACE_FOLDER]) || GetSettingBool(settings[SETTING_MORE]));
|
||||
}
|
||||
|
||||
settings[SETTING_FILE_EXPLORER].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
if (_wcsicmp(exe,L"regsvr32.exe")!=0 && _wcsicmp(exe,L"msiexec.exe")!=0 && _wcsicmp(exe,L"ClassicExplorerSettings.exe")!=0 && !g_bExplorerExe)
|
||||
{
|
||||
// some arbitrary app
|
||||
settings[SETTING_SHARE_OVERLAY].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
settings[SETTING_SHARE_EXPLORER].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
if ((!GetSettingBool(settings[SETTING_SHARE_OVERLAY]) || GetSettingBool(settings[SETTING_SHARE_EXPLORER])) && (!bReplaceUI || GetSettingBool(settings[SETTING_FILE_EXPLORER])))
|
||||
return FALSE;
|
||||
|
||||
settings[SETTING_WHITE_LIST].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
CString whiteList=GetSettingString(settings[SETTING_WHITE_LIST]);
|
||||
if (!whiteList.IsEmpty())
|
||||
{
|
||||
// check for whitelisted process names
|
||||
const wchar_t *str=whiteList;
|
||||
bool bFound=false;
|
||||
while (*str)
|
||||
{
|
||||
wchar_t token[_MAX_PATH];
|
||||
str=GetToken(str,token,_countof(token),L",;");
|
||||
wchar_t *start=token;
|
||||
while (*start==' ')
|
||||
start++;
|
||||
wchar_t *end=start+Strlen(start);
|
||||
while (end>start && end[-1]==' ')
|
||||
end--;
|
||||
*end=0;
|
||||
if (_wcsicmp(exe,start)==0)
|
||||
{
|
||||
bFound=true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!bFound)
|
||||
return FALSE;
|
||||
}
|
||||
else
|
||||
{
|
||||
settings[SETTING_BLACK_LIST].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
// check for blacklisted process names
|
||||
CString blackList=GetSettingString(settings[SETTING_BLACK_LIST]);
|
||||
const wchar_t *str=blackList;
|
||||
while (*str)
|
||||
{
|
||||
wchar_t token[_MAX_PATH];
|
||||
str=GetToken(str,token,_countof(token),L",;");
|
||||
wchar_t *start=token;
|
||||
while (*start==' ')
|
||||
start++;
|
||||
wchar_t *end=start+Strlen(start);
|
||||
while (end>start && end[-1]==' ')
|
||||
end--;
|
||||
*end=0;
|
||||
if (_wcsicmp(exe,start)==0)
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
g_LoadedSettingsAtom=(LPCWSTR)GlobalAddAtom(L"ClassicExplorer.LoadedSettings");
|
||||
|
||||
g_bHookCopyThreads=(bReplaceUI && (g_bExplorerExe || !GetSettingBool(settings[SETTING_FILE_EXPLORER])));
|
||||
if (g_bHookCopyThreads)
|
||||
{
|
||||
InitClassicCopyProcess();
|
||||
InitClassicCopyThread();
|
||||
}
|
||||
|
||||
g_DllInitThread=CreateThread(NULL,0,DllInitThread,NULL,0,NULL);
|
||||
}
|
||||
|
||||
if (dwReason==DLL_THREAD_ATTACH)
|
||||
{
|
||||
if (g_bHookCopyThreads)
|
||||
InitClassicCopyThread();
|
||||
}
|
||||
|
||||
if (dwReason==DLL_THREAD_DETACH)
|
||||
{
|
||||
void *pData=TlsGetValue(g_TlsIndex);
|
||||
if (pData)
|
||||
LocalFree((HLOCAL)pData);
|
||||
TlsSetValue(g_TlsIndex,NULL);
|
||||
if (g_bHookCopyThreads)
|
||||
FreeClassicCopyThread();
|
||||
}
|
||||
|
||||
if (dwReason==DLL_PROCESS_DETACH)
|
||||
{
|
||||
void *pData=TlsGetValue(g_TlsIndex);
|
||||
if (pData)
|
||||
LocalFree((HLOCAL)pData);
|
||||
TlsSetValue(g_TlsIndex,NULL);
|
||||
TlsFree(g_TlsIndex);
|
||||
GlobalDeleteAtom((ATOM)(uintptr_t)g_LoadedSettingsAtom);
|
||||
}
|
||||
|
||||
return _AtlModule.DllMain(dwReason, lpReserved);
|
||||
}
|
||||
44
Src/ClassicExplorer/dllmain.h
Normal file
@@ -0,0 +1,44 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
// dllmain.h : Declaration of module class.
|
||||
#pragma once
|
||||
|
||||
#include "ClassicExplorer_h.h"
|
||||
#include <vector>
|
||||
|
||||
class CClassicExplorerModule : public CAtlDllModuleT< CClassicExplorerModule >
|
||||
{
|
||||
public :
|
||||
DECLARE_LIBID(LIBID_ClassicExplorerLib)
|
||||
DECLARE_REGISTRY_APPID_RESOURCEID(IDR_CLASSICEXPLORER, "{65843E27-A491-429F-84A0-30A947E20F92}")
|
||||
};
|
||||
|
||||
extern class CClassicExplorerModule _AtlModule;
|
||||
|
||||
// Some utility functions used by various modules
|
||||
HWND FindChildWindow( HWND hwnd, const wchar_t *className );
|
||||
INT_PTR RunSettingsDialog( HWND hWndParent, DLGPROC lpDialogFunc );
|
||||
|
||||
struct TlsData
|
||||
{
|
||||
// the bho instance that runs on this thread
|
||||
class CExplorerBHO *bho;
|
||||
|
||||
// the band instance that runs on this thread
|
||||
class CExplorerBand *band;
|
||||
|
||||
// one hook for each copy thread
|
||||
HHOOK copyHook;
|
||||
|
||||
// bCopyMultiFile is true if the first dialog in this thread is multi-file (IDD_FILEMULTI)
|
||||
// if so, all the rest are multi-file. this makes the UI consistent (like the position of the Yes button doesn't change)
|
||||
bool bCopyMultiFile;
|
||||
};
|
||||
|
||||
TlsData *GetTlsData( void );
|
||||
extern LPCWSTR g_LoadedSettingsAtom;
|
||||
extern bool g_bLogLevel;
|
||||
|
||||
void WaitDllInitThread( void );
|
||||
336
Src/ClassicExplorer/resource.h
Normal file
@@ -0,0 +1,336 @@
|
||||
//{{NO_DEPENDENCIES}}
|
||||
// Microsoft Visual C++ generated include file.
|
||||
// Used by ClassicExplorer.rc
|
||||
//
|
||||
#define IDI_APPICON 1
|
||||
#define IDI_UP 2
|
||||
#define IDI_UPDISABLED 3
|
||||
#define IDI_UP2NORMAL 4
|
||||
#define IDI_UP2PRESSED 5
|
||||
#define IDI_UP2HOT 6
|
||||
#define IDI_UP2DISABLED 7
|
||||
#define IDR_CLASSICEXPLORER 101
|
||||
#define IDR_EXPLORERBAND 102
|
||||
#define IDR_EXPLORERBHO 104
|
||||
#define IDR_SHAREOVERLAY 105
|
||||
#define IDD_FILEMULTI 129
|
||||
#define IDD_FILE 130
|
||||
#define IDC_LINKMORE 204
|
||||
#define IDC_CHECKBHO 205
|
||||
#define IDC_CHECKCOPY 206
|
||||
#define IDC_STATICPROMPT1 207
|
||||
#define IDC_CHECKBIG 207
|
||||
#define IDC_STATICPROMPT2 208
|
||||
#define IDD_FILEMULTIR 208
|
||||
#define IDD_FILER 209
|
||||
#define IDC_STATICICON 209
|
||||
#define IDC_CHECK1 210
|
||||
#define IDD_FOLDERMULTI 210
|
||||
#define IDC_CHECK2 211
|
||||
#define IDD_FOLDER 211
|
||||
#define IDC_CHECK3 212
|
||||
#define IDD_FOLDERR 212
|
||||
#define IDC_CHECK4 213
|
||||
#define IDD_FOLDERMULTIR 213
|
||||
#define IDC_CHECK5 214
|
||||
#define IDC_CHECK6 215
|
||||
#define IDR_CLASSICCOPYEXT 216
|
||||
#define IDC_CHECKNOFADE 218
|
||||
#define IDC_CHECKSIZE 219
|
||||
#define IDC_CHECKAUTO 220
|
||||
#define IDC_CHECKCOPYFOLDER 221
|
||||
#define IDC_CHECK7 222
|
||||
#define IDC_CHECK8 223
|
||||
#define IDC_COMBOSTYLE 224
|
||||
#define IDC_CHECKOFFSET 225
|
||||
#define IDC_CHECKUP 226
|
||||
#define IDC_CHECKTITLE 227
|
||||
#define IDC_CHECKICON 228
|
||||
#define IDC_CHECKCRUMBS 229
|
||||
#define IDC_CHECKSHARED 230
|
||||
#define IDC_CHECKSHAREDEXP 231
|
||||
#define IDC_CHECKCOPYEXP 233
|
||||
#define IDC_CHECKMORE 234
|
||||
#define IDC_CHECKINFO 235
|
||||
#define IDC_COMBOCOMMAND 239
|
||||
#define IDC_EDITLABEL 240
|
||||
#define IDC_EDITTIP 241
|
||||
#define IDC_BUTTONLINK 242
|
||||
#define IDC_BUTTONCOMMAND 243
|
||||
#define IDC_EDITICON 245
|
||||
#define IDC_BUTTONICON 246
|
||||
#define IDC_EDITICOND 247
|
||||
#define IDC_BUTTONICOND 248
|
||||
#define IDC_STATICCOMMAND 251
|
||||
#define IDC_STATICLINK 252
|
||||
#define IDC_STATICTEXT 253
|
||||
#define IDC_STATICINFOTIP 254
|
||||
#define IDC_STATICICOND 255
|
||||
#define IDC_ICONN 256
|
||||
#define IDC_ICOND 257
|
||||
#define IDC_COMBOLINK 258
|
||||
#define IDC_STATICICON1 260
|
||||
#define IDC_BUTTONRESET 261
|
||||
#define IDC_STATICFNAME 1003
|
||||
#define IDC_STATICSRCSIZE 1004
|
||||
#define IDC_STATICSRCTIME 1005
|
||||
#define IDC_STATICDSTSIZE 1006
|
||||
#define IDC_STATICDSTTIME 1007
|
||||
#define IDC_STATICSRCICON 1008
|
||||
#define IDC_STATICDSTICON 1009
|
||||
#define IDD_CUSTOMTOOLBAR 2001
|
||||
#define IDS_APP_TITLE 2001
|
||||
#define IDS_SETTINGS_BTN 2002
|
||||
#define IDS_NEW_SETTINGS1 2003
|
||||
#define IDS_NEW_SETTINGS2 2004
|
||||
#define IDS_SETTINGS_TITLE 2005
|
||||
#define IDS_SETTINGS_TITLE_VER 2006
|
||||
#define IDS_LANGUAGE_SETTINGS 2010
|
||||
#define IDS_TOOLBAR_SETTINGS 2011
|
||||
#define IDS_BIG_BUTTONS 2012
|
||||
#define IDS_BIG_BUTTONS_TIP 2013
|
||||
#define IDS_SMALL_SIZE 2014
|
||||
#define IDS_SMALL_SIZE_TIP 2015
|
||||
#define IDS_LARGE_SIZE 2016
|
||||
#define IDS_LARGE_SIZE_TIP 2017
|
||||
#define IDS_MENU_SIZE 2018
|
||||
#define IDS_MENU_SIZE_TIP 2019
|
||||
#define IDS_SAME_SIZE 2020
|
||||
#define IDS_SAME_SIZE_TIP 2021
|
||||
#define IDS_LIST_MODE 2022
|
||||
#define IDS_LIST_MODE_TIP 2023
|
||||
#define IDS_RESIZEABLE 2024
|
||||
#define IDS_RESIZEABLE_TIP 2025
|
||||
#define IDS_BUTTONS_SETTINGS 2026
|
||||
#define IDS_NAVIGATION_SETTINGS 2027
|
||||
#define IDS_TREE_STYLE 2028
|
||||
#define IDS_TREE_STYLE_TIP 2029
|
||||
#define IDS_XPCLASSIC 2030
|
||||
#define IDS_XPCLASSIC_TIP 2031
|
||||
#define IDS_XPSIMPLE 2032
|
||||
#define IDS_XPSIMPLE_TIP 2033
|
||||
#define IDS_VISTA 2034
|
||||
#define IDS_VISTA_TIP 2035
|
||||
#define IDS_TREE_SPACING 2036
|
||||
#define IDS_TREE_SPACING_TIP 2037
|
||||
#define IDS_NO_FADE 2038
|
||||
#define IDS_NO_FADE_TIP 2039
|
||||
#define IDS_FULL_INDENT 2040
|
||||
#define IDS_FULL_INDENT_TIP 2041
|
||||
#define IDS_NAVIGATE 2042
|
||||
#define IDS_NAVIGATE_TIP 2043
|
||||
#define IDS_NAV_DELAY 2044
|
||||
#define IDS_NAV_DELAY_TIP 2045
|
||||
#define IDS_ALT_ENTER 2046
|
||||
#define IDS_ALT_ENTER_TIP 2047
|
||||
#define IDS_FIX_SCROLL 2048
|
||||
#define IDS_FIX_SCROLL_TIP 2049
|
||||
#define IDS_TITLE_SETTINGS 2050
|
||||
#define IDS_SHOW_CAPTION 2051
|
||||
#define IDS_SHOW_CAPTION_TIP 2052
|
||||
#define IDS_SHOW_ICON 2053
|
||||
#define IDS_SHOW_ICON_TIP 2054
|
||||
#define IDS_NO_BREADCRUMBS 2055
|
||||
#define IDS_NO_BREADCRUMBS_TIP 2056
|
||||
#define IDS_ADDRESS_HISTORY 2057
|
||||
#define IDS_ADDRESS_HISTORY_TIP 2058
|
||||
#define IDS_NORMAL_HISTORY 2059
|
||||
#define IDS_NORMAL_HISTORY_TIP 2060
|
||||
#define IDS_SIMPLE_PATH 2061
|
||||
#define IDS_SIMPLE_PATH_TIP 2062
|
||||
#define IDS_EXTENDED_PATH 2063
|
||||
#define IDS_EXTENDED_PATH_TIP 2064
|
||||
#define IDS_HIDE_SEARCH 2065
|
||||
#define IDS_HIDE_SEARCH_TIP 2066
|
||||
#define IDS_UP_SETTINGS 2067
|
||||
#define IDS_SHOW_UP 2068
|
||||
#define IDS_SHOW_UP_TIP 2069
|
||||
#define IDS_DONT_SHOW 2070
|
||||
#define IDS_DONT_SHOW_TIP 2071
|
||||
#define IDS_BEFORE_BACK 2072
|
||||
#define IDS_BEFORE_BACK_TIP 2073
|
||||
#define IDS_AFTER_BACK 2074
|
||||
#define IDS_AFTER_BACK_TIP 2075
|
||||
#define IDS_UP_NORMAL 2076
|
||||
#define IDS_UP_NORMAL_TIP 2077
|
||||
#define IDS_UP_HOT 2078
|
||||
#define IDS_UP_HOT_TIP 2079
|
||||
#define IDS_UP_PRESSED 2080
|
||||
#define IDS_UP_PRESSED_TIP 2081
|
||||
#define IDS_UP_DISABLED 2082
|
||||
#define IDS_UP_DISABLED_TIP 2083
|
||||
#define IDS_UP_SIZE 2084
|
||||
#define IDS_UP_SIZE_TIP 2085
|
||||
#define IDS_STATUS_SETTINGS 2086
|
||||
#define IDS_FREE_SPACE 2087
|
||||
#define IDS_FREE_SPACE_TIP 2088
|
||||
#define IDS_INFO_TIP 2089
|
||||
#define IDS_INFO_TIP_TIP 2090
|
||||
#define IDS_FORCE_REFRESH 2091
|
||||
#define IDS_FORCE_REFRESH_TIP 2092
|
||||
#define IDS_FILE_SETTINGS 2093
|
||||
#define IDS_FILE_UI 2094
|
||||
#define IDS_FILE_UI_TIP 2095
|
||||
#define IDS_FOLDER_UI 2096
|
||||
#define IDS_FOLDER_UI_TIP 2097
|
||||
#define IDS_ALERT_LEVEL 2098
|
||||
#define IDS_ALERT_LEVEL_TIP 2099
|
||||
#define IDS_NO_ALERT 2100
|
||||
#define IDS_NO_ALERT_TIP 2101
|
||||
#define IDS_SYS_FILES 2102
|
||||
#define IDS_SYS_FILES_TIP 2103
|
||||
#define IDS_RO_FILES 2104
|
||||
#define IDS_RO_FILES_TIP 2105
|
||||
#define IDS_MORE 2106
|
||||
#define IDS_MORE_TIP 2107
|
||||
#define IDS_MORE_DELAY 2108
|
||||
#define IDS_MORE_DELAY_TIP 2109
|
||||
#define IDS_FILE_EXPLORER 2110
|
||||
#define IDS_FILE_EXPLORER_TIP 2111
|
||||
#define IDS_FILEPANE_SETTINGS 2112
|
||||
#define IDS_SHARE 2113
|
||||
#define IDS_SHARE_TIP 2114
|
||||
#define IDS_SHARE_ICON 2115
|
||||
#define IDS_SHARE_ICON_TIP 2116
|
||||
#define IDS_SHARE_EXPLORER 2117
|
||||
#define IDS_SHARE_EXPLORER_TIP 2118
|
||||
#define IDS_HEADERS 2119
|
||||
#define IDS_HEADERS_TIP 2120
|
||||
#define IDS_SCROLLBAR 2121
|
||||
#define IDS_SCROLLBAR_TIP 2122
|
||||
#define IDS_SCROLLBAR_DEFAULT 2123
|
||||
#define IDS_SCROLLBAR_DEFAULT_TIP 2124
|
||||
#define IDS_SCROLLBAR_ON 2125
|
||||
#define IDS_SCROLLBAR_ON_TIP 2126
|
||||
#define IDS_SCROLLBAR_OFF 2127
|
||||
#define IDS_SCROLLBAR_OFF_TIP 2128
|
||||
#define IDS_COMMAND_TIP 2129
|
||||
#define IDS_LINK_TIP 2130
|
||||
#define IDS_TEXT_TIP 2131
|
||||
#define IDS_TIP_TIP 2132
|
||||
#define IDS_ICON_TIP 2133
|
||||
#define IDS_ICOND_TIP 2134
|
||||
#define IDS_RESTORE_TIP 2135
|
||||
#define IDS_SEPARATOR_TIP 2136
|
||||
#define IDS_UP_TIP 2137
|
||||
#define IDS_CUT_TIP 2138
|
||||
#define IDS_COPY_TIP 2139
|
||||
#define IDS_PASTE_TIP 2140
|
||||
#define IDS_DELETE_TIP 2141
|
||||
#define IDS_PROPERTIES_TIP 2142
|
||||
#define IDS_EMAIL_TIP 2143
|
||||
#define IDS_SETTINGS_TIP 2144
|
||||
#define IDS_REFRESH_TIP 2145
|
||||
#define IDS_STOP_TIP 2146
|
||||
#define IDS_RENAME_TIP 2147
|
||||
#define IDS_MOVETO_TIP 2148
|
||||
#define IDS_COPYTO_TIP 2149
|
||||
#define IDS_UNDO_TIP 2150
|
||||
#define IDS_REDO_TIP 2151
|
||||
#define IDS_SELECTALL_TIP 2152
|
||||
#define IDS_DESELECT_TIP 2153
|
||||
#define IDS_INVERT_TIP 2154
|
||||
#define IDS_BACK_TIP 2155
|
||||
#define IDS_FORWARD_TIP 2156
|
||||
#define IDS_VIEWTILES_TIP 2157
|
||||
#define IDS_VIEWDEATAILS_TIP 2158
|
||||
#define IDS_VIEWLIST_TIP 2159
|
||||
#define IDS_VIEWCONTENT_TIP 2160
|
||||
#define IDS_VIEWICONS1_TIP 2161
|
||||
#define IDS_VIEWICONS2_TIP 2162
|
||||
#define IDS_VIEWICONS3_TIP 2163
|
||||
#define IDS_VIEWICONS4_TIP 2164
|
||||
#define IDS_OPEN_TIP 2165
|
||||
#define IDS_CUSTOM_TIP 2166
|
||||
#define IDS_NEWFOLDER_TIP 2167
|
||||
#define IDS_SCROLLTIP 2168
|
||||
#define IDS_SCROLLTIP_TIP 2169
|
||||
#define IDS_NAV_DEFAULT 2170
|
||||
#define IDS_NAV_DEFAULT_TIP 2171
|
||||
#define IDS_NAV_KBD 2172
|
||||
#define IDS_NAV_KBD_TIP 2173
|
||||
#define IDS_NAV_ALWAYS 2174
|
||||
#define IDS_NAV_ALWAYS_TIP 2175
|
||||
#define IDS_ALT_D 2176
|
||||
#define IDS_ALT_D_TIP 2177
|
||||
#define IDS_SORT_TIP 2178
|
||||
#define IDS_GROUP_TIP 2179
|
||||
#define IDS_PASTE_SHORTCUT_TIP 2180
|
||||
#define IDS_UP_HOTKEY 2181
|
||||
#define IDS_UP_HOTKEY_TIP 2182
|
||||
#define IDS_MAP_DRIVE_TIP 2183
|
||||
#define IDS_DISCONNECT_DRIVE_TIP 2184
|
||||
#define IDS_CUSTOMIZEFOLDER_TIP 2185
|
||||
#define IDS_SEPARATOR_ITEM 2186
|
||||
#define IDS_UP_ITEM 2187
|
||||
#define IDS_CUT_ITEM 2188
|
||||
#define IDS_COPY_ITEM 2189
|
||||
#define IDS_PASTE_ITEM 2190
|
||||
#define IDS_PASTE_LNK_ITEM 2191
|
||||
#define IDS_DELETE_ITEM 2192
|
||||
#define IDS_PROPERTIES_ITEM 2193
|
||||
#define IDS_EMAIL_ITEM 2194
|
||||
#define IDS_SETTINGS_ITEM 2195
|
||||
#define IDS_REFRESH_ITEM 2196
|
||||
#define IDS_STOP_ITEM 2197
|
||||
#define IDS_RENAME_ITEM 2198
|
||||
#define IDS_NEWFOLDER_ITEM 2199
|
||||
#define IDS_MOVETO_ITEM 2200
|
||||
#define IDS_COPYTO_ITEM 2201
|
||||
#define IDS_UNDO_ITEM 2202
|
||||
#define IDS_REDO_ITEM 2203
|
||||
#define IDS_SELECTALL_ITEM 2204
|
||||
#define IDS_DESELECT_ITEM 2205
|
||||
#define IDS_INVERT_ITEM 2206
|
||||
#define IDS_BACK_ITEM 2207
|
||||
#define IDS_FORWARD_ITEM 2208
|
||||
#define IDS_MAP_DRIVE_ITEM 2209
|
||||
#define IDS_DISCONNECT_ITEM 2210
|
||||
#define IDS_CUSTOMIZE_ITEM 2211
|
||||
#define IDS_VIEWTILES_ITEM 2212
|
||||
#define IDS_VIEWDETAILS_ITEM 2213
|
||||
#define IDS_VIEWLIST_ITEM 2214
|
||||
#define IDS_VIEWCONTENT_ITEM 2215
|
||||
#define IDS_VIEWICONS1_ITEM 2216
|
||||
#define IDS_VIEWICONS2_ITEM 2217
|
||||
#define IDS_VIEWICONS3_ITEM 2218
|
||||
#define IDS_VIEWICONS4_ITEM 2219
|
||||
#define IDS_OPEN_ITEM 2220
|
||||
#define IDS_SORYBY_ITEM 2221
|
||||
#define IDS_GROUPBY_ITEM 2222
|
||||
#define IDS_CUSTOM_ITEM 2223
|
||||
#define IDS_SHOWSTATUSBAR 2224
|
||||
#define IDS_SHOWSTATUSBAR_TIP 2225
|
||||
#define IDS_SHOW_ZONE 2226
|
||||
#define IDS_SHOW_ZONE_TIP 2227
|
||||
#define IDS_SHARE_HIDDEN 2228
|
||||
#define IDS_SHARE_HIDDEN_TIP 2229
|
||||
#define IDS_NAVPANE_ITEM 2230
|
||||
#define IDS_NAVPANE_TIP 2231
|
||||
#define IDS_DETAILSPANE_ITEM 2232
|
||||
#define IDS_DETAILSPANE_TIP 2233
|
||||
#define IDS_PREVIEWPANE_ITEM 2234
|
||||
#define IDS_PREVIEWPANE_TIP 2235
|
||||
#define IDS_SHOW_EXTENSIONS 2236
|
||||
#define IDS_SHOW_EXTENSIONS_TIP 2237
|
||||
#define IDS_HIDDEN_FILES 2238
|
||||
#define IDS_HIDDEN_FILES_TIP 2239
|
||||
#define IDS_SYSTEM_FILES 2240
|
||||
#define IDS_SYSTEM_FILES_TIP 2241
|
||||
#define IDS_ZIP_ITEM 2242
|
||||
#define IDS_ZIP_TIP 2243
|
||||
#define IDS_STATUS_FONT 2244
|
||||
#define IDS_STATUS_FONT_TIP 2245
|
||||
#define IDS_FOLDEROPTIONS 2246
|
||||
#define IDS_FOLDEROPTIONS_TIP 2247
|
||||
|
||||
// Next default values for new objects
|
||||
//
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
#ifndef APSTUDIO_READONLY_SYMBOLS
|
||||
#define _APS_NEXT_RESOURCE_VALUE 227
|
||||
#define _APS_NEXT_COMMAND_VALUE 32769
|
||||
#define _APS_NEXT_CONTROL_VALUE 262
|
||||
#define _APS_NEXT_SYMED_VALUE 106
|
||||
#endif
|
||||
#endif
|
||||
6
Src/ClassicExplorer/stdafx.cpp
Normal file
@@ -0,0 +1,6 @@
|
||||
// stdafx.cpp : source file that includes just the standard includes
|
||||
// ClassicExplorer.pch will be the pre-compiled header
|
||||
// stdafx.obj will contain the pre-compiled type information
|
||||
|
||||
#include "stdafx.h"
|
||||
|
||||
29
Src/ClassicExplorer/stdafx.h
Normal file
@@ -0,0 +1,29 @@
|
||||
// stdafx.h : include file for standard system include files,
|
||||
// or project specific include files that are used frequently,
|
||||
// but are changed infrequently
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "targetver.h"
|
||||
|
||||
#define STRICT_TYPED_ITEMIDS
|
||||
|
||||
#define _ATL_APARTMENT_THREADED
|
||||
#define _ATL_NO_AUTOMATIC_NAMESPACE
|
||||
#define _ATL_MODULES // compatibility with /permissive-
|
||||
#define _ATL_CSTRING_EXPLICIT_CONSTRUCTORS // some CString constructors will be explicit
|
||||
|
||||
#include "resource.h"
|
||||
#include <atlbase.h>
|
||||
#include <atlcom.h>
|
||||
#include <atlctl.h>
|
||||
#include <atlstr.h>
|
||||
|
||||
using namespace ATL;
|
||||
|
||||
#include <shobjidl.h>
|
||||
#include <exdispid.h>
|
||||
#include <shlguid.h>
|
||||
#include <shlobj.h>
|
||||
|
||||
#include "StringUtils.h"
|
||||
24
Src/ClassicExplorer/targetver.h
Normal file
@@ -0,0 +1,24 @@
|
||||
#pragma once
|
||||
|
||||
// The following macros define the minimum required platform. The minimum required platform
|
||||
// is the earliest version of Windows, Internet Explorer etc. that has the necessary features to run
|
||||
// your application. The macros work by enabling all features available on platform versions up to and
|
||||
// including the version specified.
|
||||
|
||||
// Modify the following defines if you have to target a platform prior to the ones specified below.
|
||||
// Refer to MSDN for the latest info on corresponding values for different platforms.
|
||||
#ifndef WINVER // Specifies that the minimum required platform is Windows 7.
|
||||
#define WINVER 0x0602 // Change this to the appropriate value to target other versions of Windows.
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32_WINNT // Specifies that the minimum required platform is Windows 7.
|
||||
#define _WIN32_WINNT 0x0602 // Change this to the appropriate value to target other versions of Windows.
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32_WINDOWS // Specifies that the minimum required platform is Windows 98.
|
||||
#define _WIN32_WINDOWS 0x0410 // Change this to the appropriate value to target Windows Me or later.
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32_IE // Specifies that the minimum required platform is Internet Explorer 7.0.
|
||||
#define _WIN32_IE 0x0700 // Change this to the appropriate value to target other versions of IE.
|
||||
#endif
|
||||
BIN
Src/ClassicExplorer/up.ico
Normal file
|
After Width: | Height: | Size: 7.7 KiB |
BIN
Src/ClassicExplorer/up2Disabled.ico
Normal file
|
After Width: | Height: | Size: 9.1 KiB |
BIN
Src/ClassicExplorer/up2Hot.ico
Normal file
|
After Width: | Height: | Size: 9.1 KiB |
BIN
Src/ClassicExplorer/up2Normal.ico
Normal file
|
After Width: | Height: | Size: 9.1 KiB |
BIN
Src/ClassicExplorer/up2Pressed.ico
Normal file
|
After Width: | Height: | Size: 9.1 KiB |
BIN
Src/ClassicExplorer/upDisabled.ico
Normal file
|
After Width: | Height: | Size: 7.7 KiB |
257
Src/ClassicIE/ClassicIE.cpp
Normal file
@@ -0,0 +1,257 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#define STRICT_TYPED_ITEMIDS
|
||||
#define _ATL_CSTRING_EXPLICIT_CONSTRUCTORS // some CString constructors will be explicit
|
||||
#include <windows.h>
|
||||
#include <commctrl.h>
|
||||
#include <shlwapi.h>
|
||||
#include <Psapi.h>
|
||||
#include <atlstr.h>
|
||||
#include "StringUtils.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "ClassicIEDLL\ClassicIEDLL.h"
|
||||
|
||||
// Manifest to enable the 6.0 common controls
|
||||
#pragma comment(linker, \
|
||||
"\"/manifestdependency:type='Win32' "\
|
||||
"name='Microsoft.Windows.Common-Controls' "\
|
||||
"version='6.0.0.0' "\
|
||||
"processorArchitecture='*' "\
|
||||
"publicKeyToken='6595b64144ccf1df' "\
|
||||
"language='*'\"")
|
||||
|
||||
// Find and activate the Settings window
|
||||
static BOOL CALLBACK FindSettingsEnum( HWND hwnd, LPARAM lParam )
|
||||
{
|
||||
wchar_t className[256];
|
||||
if (!GetClassName(hwnd,className,_countof(className)) || _wcsicmp(className,L"#32770")!=0)
|
||||
return TRUE;
|
||||
DWORD process=0;
|
||||
GetWindowThreadProcessId(hwnd,&process);
|
||||
HANDLE hProcess=OpenProcess(PROCESS_QUERY_INFORMATION|PROCESS_VM_READ,FALSE,process);
|
||||
bool bFound=false;
|
||||
if (hProcess!=INVALID_HANDLE_VALUE)
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
if (GetModuleFileNameEx(hProcess,NULL,path,_countof(path)))
|
||||
{
|
||||
if (_wcsicmp(PathFindFileName(path),L"ClassicIE_32.exe")==0)
|
||||
{
|
||||
SetForegroundWindow(hwnd);
|
||||
bFound=true;
|
||||
}
|
||||
}
|
||||
CloseHandle(hProcess);
|
||||
}
|
||||
return !bFound;
|
||||
}
|
||||
|
||||
void ZoneConfigure( HWND hWnd, const wchar_t *url )
|
||||
{
|
||||
// use undocumented function 383 from shlwapi
|
||||
typedef void (WINAPI* FZoneConfigureW)(HWND,LPCWSTR);
|
||||
FZoneConfigureW ZoneConfigureW;
|
||||
|
||||
HMODULE hShlwapi=LoadLibrary(L"shlwapi.dll");
|
||||
if(hShlwapi)
|
||||
{
|
||||
ZoneConfigureW=(FZoneConfigureW)GetProcAddress(hShlwapi,MAKEINTRESOURCEA(383));
|
||||
if(ZoneConfigureW)
|
||||
ZoneConfigureW(hWnd,url);
|
||||
FreeLibrary(hShlwapi);
|
||||
}
|
||||
}
|
||||
|
||||
int WINAPI wWinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow )
|
||||
{
|
||||
if (wcsncmp(lpCmdLine,L"zone ",5)==0)
|
||||
{
|
||||
wchar_t token[100];
|
||||
const wchar_t *url=GetToken(lpCmdLine+5,token,_countof(token),L" ");
|
||||
ZoneConfigure((HWND)(uintptr_t)_wtol(token),url);
|
||||
return 0;
|
||||
}
|
||||
|
||||
{
|
||||
const wchar_t *pXml=wcsstr(lpCmdLine,L"-xml ");
|
||||
if (pXml)
|
||||
{
|
||||
wchar_t xml[_MAX_PATH];
|
||||
GetToken(pXml+5,xml,_countof(xml),L" ");
|
||||
CoInitialize(NULL);
|
||||
bool res=DllImportSettingsXml(xml);
|
||||
CoUninitialize();
|
||||
return res?0:1;
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
const wchar_t *pBackup=wcsstr(lpCmdLine,L"-backup ");
|
||||
if (pBackup)
|
||||
{
|
||||
wchar_t xml[_MAX_PATH];
|
||||
GetToken(pBackup+8,xml,_countof(xml),L" ");
|
||||
CoInitialize(NULL);
|
||||
bool res=DllExportSettingsXml(xml);
|
||||
CoUninitialize();
|
||||
return res?0:1;
|
||||
}
|
||||
}
|
||||
|
||||
#ifndef _WIN64
|
||||
const wchar_t *pSaveAdmx=wcsstr(lpCmdLine,L"-saveadmx ");
|
||||
if (pSaveAdmx)
|
||||
{
|
||||
wchar_t language[100];
|
||||
GetToken(pSaveAdmx+10,language,_countof(language),L" ");
|
||||
if (!DllSaveAdmx("ClassicIE.admx","ClassicIE.adml","ClassicIEADMX.txt",language))
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
WaitDllInitThread();
|
||||
|
||||
DWORD settings=GetIESettings();
|
||||
|
||||
HWND topWindow=(HWND)(uintptr_t)_wtol(lpCmdLine);
|
||||
if (topWindow)
|
||||
{
|
||||
DWORD processId;
|
||||
DWORD threadId=GetWindowThreadProcessId(topWindow,&processId);
|
||||
bool bWrongBitness=false;
|
||||
|
||||
{
|
||||
HANDLE hProcess=OpenProcess(PROCESS_QUERY_INFORMATION,FALSE,processId);
|
||||
|
||||
if (hProcess)
|
||||
{
|
||||
BOOL bWow64;
|
||||
#ifdef _WIN64
|
||||
bWrongBitness=(IsWow64Process(hProcess,&bWow64) && bWow64); // the current process is 64-bit, but the target is wow64 (32-bit)
|
||||
#else
|
||||
if (IsWow64Process(GetCurrentProcess(),&bWow64) && bWow64)
|
||||
{
|
||||
bWrongBitness=(!IsWow64Process(hProcess,&bWow64) || !bWow64); // the current process is 32-bit, but the target is 64-bit
|
||||
}
|
||||
#endif
|
||||
CloseHandle(hProcess);
|
||||
}
|
||||
}
|
||||
|
||||
if (bWrongBitness)
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(hInstance,path,_countof(path));
|
||||
PathRemoveFileSpec(path);
|
||||
#ifdef _WIN64
|
||||
PathAppend(path,L"ClassicIE_32.exe");
|
||||
#else
|
||||
PathAppend(path,L"ClassicIE_64.exe");
|
||||
#endif
|
||||
wchar_t cmdLine[1024];
|
||||
Sprintf(cmdLine,_countof(cmdLine),L"%s %s",path,lpCmdLine);
|
||||
STARTUPINFO startupInfo={sizeof(startupInfo)};
|
||||
PROCESS_INFORMATION processInfo;
|
||||
memset(&processInfo,0,sizeof(processInfo));
|
||||
if (CreateProcess(path,cmdLine,NULL,NULL,TRUE,0,NULL,NULL,&startupInfo,&processInfo))
|
||||
{
|
||||
CloseHandle(processInfo.hThread);
|
||||
CloseHandle(processInfo.hProcess);
|
||||
}
|
||||
return settings;
|
||||
}
|
||||
|
||||
CheckForNewVersionIE();
|
||||
|
||||
if (!(settings&IE_SETTING_CAPTION))
|
||||
return settings;
|
||||
|
||||
HWND caption=FindWindowEx(topWindow,NULL,L"Client Caption",NULL);
|
||||
DllLogToFile(CIE_LOG,L"exe: topWindow=%p, caption=%p",topWindow,caption);
|
||||
UINT message=RegisterWindowMessage(L"ClassicIE.Injected");
|
||||
if (caption)
|
||||
{
|
||||
if (SendMessage(caption,message,0,0)!=0)
|
||||
return settings;
|
||||
|
||||
{
|
||||
HANDLE hToken;
|
||||
if (OpenProcessToken(GetCurrentProcess(),TOKEN_ADJUST_PRIVILEGES|TOKEN_QUERY,&hToken))
|
||||
{
|
||||
TOKEN_PRIVILEGES tp={1};
|
||||
if (LookupPrivilegeValue(NULL,L"SeDebugPrivilege",&tp.Privileges[0].Luid))
|
||||
tp.Privileges[0].Attributes=SE_PRIVILEGE_ENABLED;
|
||||
AdjustTokenPrivileges(hToken,FALSE,&tp,sizeof(TOKEN_PRIVILEGES),NULL,NULL);
|
||||
CloseHandle(hToken);
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef _WIN64
|
||||
HMODULE hHookModule=GetModuleHandle(L"ClassicIEDLL_64.dll");
|
||||
#else
|
||||
HMODULE hHookModule=GetModuleHandle(L"ClassicIEDLL_32.dll");
|
||||
#endif
|
||||
|
||||
HANDLE hProcess=OpenProcess(PROCESS_ALL_ACCESS,FALSE,processId);
|
||||
if (hProcess)
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(hHookModule,path,_countof(path));
|
||||
void *remotePath=VirtualAllocEx(hProcess,NULL,sizeof(path),MEM_COMMIT,PAGE_READWRITE);
|
||||
if (remotePath)
|
||||
{
|
||||
if (WriteProcessMemory(hProcess,remotePath,path,sizeof(path),NULL))
|
||||
{
|
||||
HANDLE hThread=CreateRemoteThread(hProcess,NULL,0,(LPTHREAD_START_ROUTINE)GetProcAddress(GetModuleHandle(L"kernel32.dll"),"LoadLibraryW"),remotePath,0,NULL);
|
||||
if (hThread)
|
||||
{
|
||||
WaitForSingleObject(hThread,INFINITE);
|
||||
CloseHandle(hThread);
|
||||
}
|
||||
}
|
||||
VirtualFreeEx(hProcess,remotePath,sizeof(path),MEM_RELEASE);
|
||||
}
|
||||
CloseHandle(hProcess);
|
||||
}
|
||||
}
|
||||
return settings;
|
||||
}
|
||||
|
||||
#ifndef _WIN64
|
||||
if (*lpCmdLine)
|
||||
#endif
|
||||
return settings;
|
||||
|
||||
// if 32-bit exe is called with no arguments, show the settings
|
||||
|
||||
INITCOMMONCONTROLSEX init={sizeof(init),ICC_STANDARD_CLASSES};
|
||||
InitCommonControlsEx(&init);
|
||||
|
||||
// prevent multiple instances from running on the same desktop
|
||||
// the assumption is that multiple desktops for the same user will have different name (but may repeat across users)
|
||||
wchar_t userName[256];
|
||||
DWORD len=_countof(userName);
|
||||
GetUserName(userName,&len);
|
||||
len=0;
|
||||
HANDLE desktop=GetThreadDesktop(GetCurrentThreadId());
|
||||
GetUserObjectInformation(desktop,UOI_NAME,NULL,0,&len);
|
||||
wchar_t *deskName=(wchar_t*)malloc(len);
|
||||
GetUserObjectInformation(desktop,UOI_NAME,deskName,len,&len);
|
||||
|
||||
wchar_t mutexName[1024];
|
||||
Sprintf(mutexName,_countof(mutexName),L"ClassicIESettings.Mutex.%s.%s",userName,deskName);
|
||||
free(deskName);
|
||||
|
||||
HANDLE hMutex=CreateMutex(NULL,TRUE,mutexName);
|
||||
if (GetLastError()==ERROR_ALREADY_EXISTS || GetLastError()==ERROR_ACCESS_DENIED)
|
||||
{
|
||||
EnumWindows(FindSettingsEnum,0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
ShowIESettings();
|
||||
return 0;
|
||||
}
|
||||
22
Src/ClassicIE/ClassicIE.manifest
Normal file
@@ -0,0 +1,22 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0" xmlns:asmv3="urn:schemas-microsoft-com:asm.v3" >
|
||||
<asmv3:application>
|
||||
<asmv3:windowsSettings xmlns="http://schemas.microsoft.com/SMI/2005/WindowsSettings">
|
||||
<dpiAware>true</dpiAware>
|
||||
</asmv3:windowsSettings>
|
||||
</asmv3:application>
|
||||
<compatibility xmlns="urn:schemas-microsoft-com:compatibility.v1">
|
||||
<application>
|
||||
<!-- Windows Vista -->
|
||||
<supportedOS Id="{e2011457-1546-43c5-a5fe-008deee3d3f0}"/>
|
||||
<!-- Windows 7 -->
|
||||
<supportedOS Id="{35138b9a-5d96-4fbd-8e2d-a2440225f93a}"/>
|
||||
<!-- Windows 8 -->
|
||||
<supportedOS Id="{4a2f28e3-53b9-4441-ba9c-d69d4a4a6e38}"/>
|
||||
<!-- Windows 8.1 -->
|
||||
<supportedOS Id="{1f676c76-80e1-4239-95bb-83d0f6d0da78}"/>
|
||||
<!-- Windows 10 -->
|
||||
<supportedOS Id="{8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}"/>
|
||||
</application>
|
||||
</compatibility>
|
||||
</assembly>
|
||||
102
Src/ClassicIE/ClassicIE.rc
Normal file
@@ -0,0 +1,102 @@
|
||||
// Microsoft Visual C++ generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
#define APSTUDIO_READONLY_SYMBOLS
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#define APSTUDIO_HIDDEN_SYMBOLS
|
||||
#include "windows.h"
|
||||
#undef APSTUDIO_HIDDEN_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
|
||||
#pragma code_page(1252)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#define APSTUDIO_HIDDEN_SYMBOLS\r\n"
|
||||
"#include ""windows.h""\r\n"
|
||||
"#undef APSTUDIO_HIDDEN_SYMBOLS\r\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Version
|
||||
//
|
||||
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION _PRODUCT_VERSION
|
||||
PRODUCTVERSION _PRODUCT_VERSION
|
||||
FILEFLAGSMASK 0x17L
|
||||
#ifdef _DEBUG
|
||||
FILEFLAGS 0x1L
|
||||
#else
|
||||
FILEFLAGS 0x0L
|
||||
#endif
|
||||
FILEOS 0x4L
|
||||
FILETYPE 0x1L
|
||||
FILESUBTYPE 0x0L
|
||||
BEGIN
|
||||
BLOCK "StringFileInfo"
|
||||
BEGIN
|
||||
BLOCK "040904b0"
|
||||
BEGIN
|
||||
VALUE "CompanyName", "Open-Shell"
|
||||
VALUE "FileDescription", "Classic IE"
|
||||
VALUE "FileVersion", _PRODUCT_VERSION_STR
|
||||
VALUE "InternalName", "ClassicIE"
|
||||
VALUE "LegalCopyright", "Copyright (C) 2017-2018, The Open-Shell Team"
|
||||
VALUE "OriginalFilename", "ClassicIE.exe"
|
||||
VALUE "ProductName", "Open-Shell"
|
||||
VALUE "ProductVersion", _PRODUCT_VERSION_STR
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
BEGIN
|
||||
VALUE "Translation", 0x409, 1200
|
||||
END
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Icon
|
||||
//
|
||||
|
||||
// Icon with lowest ID value placed first to ensure application icon
|
||||
// remains consistent on all systems.
|
||||
IDI_ICON1 ICON "..\\Setup\\OpenShell.ico"
|
||||
#endif // English (U.S.) resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
95
Src/ClassicIE/ClassicIE.vcxproj
Normal file
@@ -0,0 +1,95 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|x64">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|x64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Setup|Win32">
|
||||
<Configuration>Setup</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Setup|x64">
|
||||
<Configuration>Setup</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<ProjectGuid>{65D5C193-E807-4094-AE19-19E6A310A312}</ProjectGuid>
|
||||
<RootNamespace>ClassicIE</RootNamespace>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Label="Configuration">
|
||||
<ConfigurationType>Application</ConfigurationType>
|
||||
<PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
|
||||
<UseOfAtl>Static</UseOfAtl>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<WholeProgramOptimization Condition="'$(Configuration)'!='Debug'">true</WholeProgramOptimization>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets">
|
||||
<Import Project="..\Common.props" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup Condition="'$(Platform)'=='Win32'">
|
||||
<TargetName>$(ProjectName)_32</TargetName>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Platform)'=='x64'">
|
||||
<TargetName>$(ProjectName)_64</TargetName>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup>
|
||||
<ClCompile>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<AdditionalDependencies>shlwapi.lib;comctl32.lib;psapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="ClassicIE.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Manifest Include="ClassicIE.manifest" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="ClassicIE.rc" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="..\Localization\English\ClassicIEADMX.txt" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Image Include="..\Setup\OpenShell.ico" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="Resource.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\Lib\Lib.vcxproj">
|
||||
<Project>{d42fe717-485b-492d-884a-1999f6d51154}</Project>
|
||||
<ReferenceOutputAssembly>false</ReferenceOutputAssembly>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="ClassicIEDLL\ClassicIEDLL.vcxproj">
|
||||
<Project>{bc0e6e7c-08c1-4f12-a754-4608e5a22fa8}</Project>
|
||||
<ReferenceOutputAssembly>false</ReferenceOutputAssembly>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
406
Src/ClassicIE/ClassicIEDLL/ClassicIEBHO.cpp
Normal file
@@ -0,0 +1,406 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ClassicIEDLL_h.h"
|
||||
#include "ClassicIEBHO.h"
|
||||
#include "ClassicIEDLL.h"
|
||||
#include "Settings.h"
|
||||
#include "SettingsUIHelper.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "Translations.h"
|
||||
#include "FNVHash.h"
|
||||
#include "dllmain.h"
|
||||
#include <shlguid.h>
|
||||
|
||||
static bool IsLowIntegrity( void )
|
||||
{
|
||||
bool bLow=false;
|
||||
HANDLE hToken;
|
||||
if (OpenProcessToken(GetCurrentProcess(),TOKEN_QUERY|TOKEN_QUERY_SOURCE,&hToken))
|
||||
{
|
||||
DWORD dwLengthNeeded;
|
||||
if (!GetTokenInformation(hToken,TokenIntegrityLevel,NULL,0,&dwLengthNeeded))
|
||||
{
|
||||
TOKEN_MANDATORY_LABEL *pTIL=(TOKEN_MANDATORY_LABEL*)malloc(dwLengthNeeded);
|
||||
if (pTIL)
|
||||
{
|
||||
if (GetTokenInformation(hToken,TokenIntegrityLevel,pTIL,dwLengthNeeded,&dwLengthNeeded))
|
||||
{
|
||||
DWORD dwIntegrityLevel=*GetSidSubAuthority(pTIL->Label.Sid,(DWORD)(UCHAR)(*GetSidSubAuthorityCount(pTIL->Label.Sid)-1));
|
||||
bLow=(dwIntegrityLevel<SECURITY_MANDATORY_MEDIUM_RID);
|
||||
}
|
||||
free(pTIL);
|
||||
}
|
||||
}
|
||||
CloseHandle(hToken);
|
||||
}
|
||||
return bLow;
|
||||
}
|
||||
|
||||
static DWORD StartBroker( bool bWait, const wchar_t *param )
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(g_Instance,path,_countof(path));
|
||||
PathRemoveFileSpec(path);
|
||||
#ifndef _WIN64
|
||||
BOOL bWow64;
|
||||
if (!IsWow64Process(GetCurrentProcess(),&bWow64) || !bWow64 || (GetVersionEx(GetModuleHandle(NULL))>>24)<10)
|
||||
PathAppend(path,L"ClassicIE_32.exe");
|
||||
else
|
||||
#endif
|
||||
PathAppend(path,L"ClassicIE_64.exe");
|
||||
|
||||
wchar_t cmdLine[1024];
|
||||
Sprintf(cmdLine,_countof(cmdLine),L"\"%s\" %s",path,param);
|
||||
STARTUPINFO startupInfo={sizeof(startupInfo)};
|
||||
PROCESS_INFORMATION processInfo;
|
||||
memset(&processInfo,0,sizeof(processInfo));
|
||||
DWORD res=GetIESettings();
|
||||
if (CreateProcess(path,cmdLine,NULL,NULL,TRUE,0,NULL,NULL,&startupInfo,&processInfo))
|
||||
{
|
||||
CloseHandle(processInfo.hThread);
|
||||
if (bWait)
|
||||
{
|
||||
if (WaitForSingleObject(processInfo.hProcess,2000)==WAIT_OBJECT_0)
|
||||
GetExitCodeProcess(processInfo.hProcess,&res);
|
||||
}
|
||||
CloseHandle(processInfo.hProcess);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
HRESULT STDMETHODCALLTYPE CClassicIEBHO::SetSite( IUnknown *pUnkSite )
|
||||
{
|
||||
if (m_pWebBrowser && m_dwEventCookie!=0xFEFEFEFE)
|
||||
DispEventUnadvise(m_pWebBrowser,&DIID_DWebBrowserEvents2);
|
||||
m_pWebBrowser=NULL;
|
||||
|
||||
IObjectWithSiteImpl<CClassicIEBHO>::SetSite(pUnkSite);
|
||||
if (pUnkSite)
|
||||
{
|
||||
HMODULE hFrame=GetModuleHandle(L"ieframe.dll");
|
||||
bool bLowIntegrity=IsLowIntegrity();
|
||||
m_ProtectedMode.LoadString(hFrame,bLowIntegrity?12939:12940);
|
||||
m_ProtectedMode=L" | "+m_ProtectedMode;
|
||||
// find the top window and run another process to subclass it (the top window can be in a higher-level process, so we can't subclass from here)
|
||||
LogToFile(CIE_LOG,L"SetSite");
|
||||
CComQIPtr<IServiceProvider> pProvider=pUnkSite;
|
||||
|
||||
m_Settings=0;
|
||||
|
||||
if (pProvider)
|
||||
{
|
||||
|
||||
pProvider->QueryService(SID_SShellBrowser,IID_IShellBrowser,(void**)&m_pBrowser);
|
||||
|
||||
HWND hwnd;
|
||||
HWND topWindow=NULL;
|
||||
if (m_pBrowser && SUCCEEDED(m_pBrowser->GetWindow(&hwnd)))
|
||||
{
|
||||
HWND topWindow=GetAncestor(hwnd,GA_ROOT);
|
||||
if (topWindow)
|
||||
{
|
||||
wchar_t param[100];
|
||||
Sprintf(param,_countof(param),L"%u",(DWORD)(uintptr_t)topWindow);
|
||||
m_Settings=StartBroker(bLowIntegrity,param);
|
||||
|
||||
if (m_Settings&(IE_SETTING_PROGRESS|IE_SETTING_ZONE))
|
||||
{
|
||||
m_pZoneManager.CoCreateInstance(CLSID_InternetZoneManager,NULL,CLSCTX_INPROC_SERVER);
|
||||
m_pSecurityManager.CoCreateInstance(CLSID_InternetSecurityManager,NULL,CLSCTX_INPROC_SERVER);
|
||||
|
||||
pProvider->QueryService(SID_SWebBrowserApp,IID_IWebBrowser2,(void**)&m_pWebBrowser);
|
||||
if (m_pWebBrowser)
|
||||
{
|
||||
if (m_dwEventCookie==0xFEFEFEFE) // ATL's event cookie is 0xFEFEFEFE when the sink is not advised
|
||||
DispEventAdvise(m_pWebBrowser,&DIID_DWebBrowserEvents2);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
m_pBrowser=NULL;
|
||||
m_pWebBrowser=NULL;
|
||||
m_pZoneManager=NULL;
|
||||
m_pSecurityManager=NULL;
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT WINAPI CClassicIEBHO::UpdateRegistry( BOOL bRegister )
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(g_Instance,path,_countof(path));
|
||||
PathRemoveFileSpec(path);
|
||||
|
||||
CString menu;
|
||||
menu.LoadString(IDS_SETTINGS_TITLE);
|
||||
|
||||
_ATL_REGMAP_ENTRY mapEntries[]={
|
||||
{L"MODULEPATH",path},
|
||||
{L"MENUTEXT",menu},
|
||||
{NULL,NULL}
|
||||
};
|
||||
|
||||
return _AtlModule.UpdateRegistryFromResource(IDR_CLASSICIEBHO,bRegister,mapEntries);
|
||||
}
|
||||
|
||||
LRESULT CALLBACK CClassicIEBHO::SubclassStatusProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData )
|
||||
{
|
||||
if (uMsg==SB_SETPARTS && wParam>0)
|
||||
{
|
||||
CClassicIEBHO *pThis=(CClassicIEBHO*)uIdSubclass;
|
||||
int w0=*(int*)lParam; // total width
|
||||
int w1=pThis->m_Progress<0?0:PROGRESS_WIDTH; // progress part
|
||||
int w2=pThis->m_TextWidth; // zone part
|
||||
int w=w1+w2;
|
||||
int parts[PART_COUNT];
|
||||
parts[PART_TEXT]=w0;
|
||||
if (parts[PART_TEXT]>=w+MIN_TEXT_WIDTH)
|
||||
parts[PART_TEXT]-=w;
|
||||
else if (parts[PART_TEXT]>=MIN_TEXT_WIDTH)
|
||||
parts[PART_TEXT]=MIN_TEXT_WIDTH;
|
||||
if (parts[PART_TEXT]>w0)
|
||||
parts[PART_TEXT]=w0;
|
||||
|
||||
if (parts[PART_TEXT]+w1>w0)
|
||||
w1=0;
|
||||
parts[PART_PROGRESS]=parts[PART_TEXT]+w1;
|
||||
parts[PART_ZONE]=w0;
|
||||
parts[PART_ZOOM]=-1;
|
||||
|
||||
DefSubclassProc(hWnd,SB_SETPARTS,_countof(parts),(LPARAM)parts);
|
||||
|
||||
TOOLINFO tool={sizeof(tool),TTF_SUBCLASS,hWnd};
|
||||
tool.uId=1;
|
||||
DefSubclassProc(hWnd,SB_GETRECT,PART_ZONE,(LPARAM)&tool.rect);
|
||||
SendMessage(pThis->m_Tooltip,TTM_NEWTOOLRECT,0,(LPARAM)&tool);
|
||||
|
||||
if (w1==0)
|
||||
ShowWindow(pThis->m_ProgressBar,SW_HIDE);
|
||||
else
|
||||
{
|
||||
RECT rc;
|
||||
DefSubclassProc(hWnd,SB_GETRECT,PART_PROGRESS,(LPARAM)&rc);
|
||||
rc.left+=2;
|
||||
rc.right-=2;
|
||||
rc.top+=1;
|
||||
rc.bottom-=1;
|
||||
SetWindowPos(pThis->m_ProgressBar,NULL,rc.left,rc.top,rc.right-rc.left,rc.bottom-rc.top,SWP_NOZORDER|SWP_SHOWWINDOW);
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
if (uMsg==SB_GETPARTS)
|
||||
{
|
||||
int parts[10];
|
||||
int n=(int)DefSubclassProc(hWnd,SB_GETPARTS,_countof(parts),(LPARAM)parts);
|
||||
const int *p=parts;
|
||||
if (n>2)
|
||||
{
|
||||
p+=n-2;
|
||||
n=2;
|
||||
}
|
||||
if (lParam)
|
||||
memcpy((int*)lParam,p,4*((n<(int)wParam)?n:wParam));
|
||||
return n;
|
||||
}
|
||||
|
||||
if (uMsg==SB_GETRECT)
|
||||
{
|
||||
if (wParam==1) wParam=PART_ZOOM;
|
||||
else if (wParam>PART_OFFSET) wParam-=PART_OFFSET;
|
||||
}
|
||||
|
||||
if (uMsg==SB_SETTEXT)
|
||||
{
|
||||
if (!SendMessage(hWnd,SB_ISSIMPLE,0,0))
|
||||
{
|
||||
if ((wParam&255)==1) wParam=PART_ZOOM;
|
||||
else if ((wParam&255)>PART_OFFSET) wParam-=PART_OFFSET;
|
||||
}
|
||||
}
|
||||
|
||||
if (uMsg==WM_LBUTTONDBLCLK)
|
||||
{
|
||||
POINT pt={(short)LOWORD(lParam),(short)HIWORD(lParam)};
|
||||
RECT rc;
|
||||
DefSubclassProc(hWnd,SB_GETRECT,PART_ZONE,(LPARAM)&rc);
|
||||
if (PtInRect(&rc,pt))
|
||||
{
|
||||
CClassicIEBHO *pThis=(CClassicIEBHO*)uIdSubclass;
|
||||
CComBSTR url;
|
||||
if (pThis->m_pWebBrowser && SUCCEEDED(pThis->m_pWebBrowser->get_LocationURL(&url)))
|
||||
{
|
||||
wchar_t buf[1024];
|
||||
Sprintf(buf,_countof(buf),L"zone %u %s",(unsigned)(uintptr_t)GetAncestor(hWnd,GA_ROOT),(const wchar_t*)url);
|
||||
StartBroker(false,buf);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (uMsg==SB_SIMPLE)
|
||||
{
|
||||
CClassicIEBHO *pThis=(CClassicIEBHO*)uIdSubclass;
|
||||
LRESULT res=DefSubclassProc(hWnd,uMsg,wParam,lParam);
|
||||
if (wParam)
|
||||
{
|
||||
ShowWindow(pThis->m_ProgressBar,SW_HIDE);
|
||||
}
|
||||
else
|
||||
{
|
||||
pThis->ResetParts();
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
return DefSubclassProc(hWnd,uMsg,wParam,lParam);
|
||||
}
|
||||
|
||||
void CClassicIEBHO::ResetParts( void )
|
||||
{
|
||||
int parts[256];
|
||||
int n=(int)SendMessage(m_StatusBar,SB_GETPARTS,_countof(parts),(LPARAM)parts);
|
||||
SendMessage(m_StatusBar,SB_SETPARTS,n,(LPARAM)parts);
|
||||
}
|
||||
|
||||
STDMETHODIMP CClassicIEBHO::OnNavigateComplete( IDispatch *pDisp, VARIANT *URL )
|
||||
{
|
||||
HWND status;
|
||||
if (!m_pBrowser || FAILED(m_pBrowser->GetControlWindow(FCW_STATUS,&status)))
|
||||
return S_OK;
|
||||
|
||||
if (m_StatusBar!=status)
|
||||
{
|
||||
if (m_StatusBar) RemoveWindowSubclass(m_StatusBar,SubclassStatusProc,(UINT_PTR)this);
|
||||
m_StatusBar=status;
|
||||
if (m_StatusBar)
|
||||
{
|
||||
m_TextWidth=0;
|
||||
SetWindowSubclass(m_StatusBar,SubclassStatusProc,(UINT_PTR)this,0);
|
||||
ResetParts();
|
||||
}
|
||||
}
|
||||
|
||||
if (!m_StatusBar) return S_OK;
|
||||
|
||||
if (!m_Tooltip)
|
||||
{
|
||||
m_Tooltip=CreateWindowEx(WS_EX_TOPMOST|WS_EX_TOOLWINDOW|WS_EX_TRANSPARENT,TOOLTIPS_CLASS,NULL,WS_POPUP|TTS_NOPREFIX|TTS_ALWAYSTIP,0,0,0,0,m_StatusBar,NULL,g_Instance,NULL);
|
||||
TOOLINFO tool={sizeof(tool),TTF_SUBCLASS,m_StatusBar};
|
||||
tool.uId=1;
|
||||
tool.hinst=GetModuleHandle(L"ieframe.dll");
|
||||
tool.lpszText=MAKEINTRESOURCE(12941);
|
||||
SendMessage(m_Tooltip,TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
}
|
||||
|
||||
if (!m_ProgressBar)
|
||||
{
|
||||
m_ProgressBar=CreateWindowEx(0,PROGRESS_CLASS,NULL,WS_CHILD|PBS_SMOOTH,0,0,0,0,m_StatusBar,NULL,g_Instance,NULL);
|
||||
SendMessage(m_ProgressBar,PBM_SETRANGE,0,MAKELPARAM(0,100));
|
||||
}
|
||||
|
||||
m_TextWidth=0;
|
||||
if (!(m_Settings&IE_SETTING_ZONE))
|
||||
return S_OK;
|
||||
wchar_t text[256];
|
||||
text[0]=0;
|
||||
HICON hIcon=NULL;
|
||||
if (m_pZoneManager && m_pSecurityManager && URL && URL->vt==VT_BSTR)
|
||||
{
|
||||
DWORD zone;
|
||||
ZONEATTRIBUTES attributes={sizeof(attributes)};
|
||||
if (SUCCEEDED(m_pSecurityManager->MapUrlToZone(URL->bstrVal,&zone,0)) && SUCCEEDED(m_pZoneManager->GetZoneAttributes(zone,&attributes)))
|
||||
{
|
||||
Strcpy(text,_countof(text),attributes.szDisplayName);
|
||||
if (m_Settings&IE_SETTING_PROTECTED)
|
||||
Strcat(text,_countof(text),m_ProtectedMode);
|
||||
unsigned int key=CalcFNVHash(attributes.szIconPath);
|
||||
std::map<unsigned int,HICON>::const_iterator it=m_IconCache.find(key);
|
||||
if (it!=m_IconCache.end())
|
||||
hIcon=it->second;
|
||||
else
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
wchar_t *str=wcschr(attributes.szIconPath,'#');
|
||||
if (!str) str=wcschr(attributes.szIconPath,',');
|
||||
int index=0;
|
||||
if (str)
|
||||
{
|
||||
index=_wtol(str+1);
|
||||
*str=0;
|
||||
}
|
||||
Strcpy(path,_countof(path),attributes.szIconPath);
|
||||
if (PathIsRelative(path))
|
||||
PathFindOnPath(path,NULL);
|
||||
if (index==0)
|
||||
hIcon=(HICON)LoadImage(NULL,path,IMAGE_ICON,16,16,LR_LOADFROMFILE);
|
||||
else
|
||||
{
|
||||
HMODULE hModule=LoadLibraryEx(path,NULL,LOAD_LIBRARY_AS_DATAFILE|LOAD_LIBRARY_AS_IMAGE_RESOURCE);
|
||||
if (hModule)
|
||||
{
|
||||
hIcon=(HICON)LoadImage(hModule,MAKEINTRESOURCE(index),IMAGE_ICON,16,16,0);
|
||||
FreeLibrary(hModule);
|
||||
}
|
||||
}
|
||||
m_IconCache[key]=hIcon;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (text[0])
|
||||
{
|
||||
HDC hdc=GetDC(m_StatusBar);
|
||||
HGDIOBJ font0=SelectObject(hdc,(HFONT)SendMessage(m_StatusBar,WM_GETFONT,0,0));
|
||||
SIZE size;
|
||||
GetTextExtentPoint32(hdc,text,Strlen(text),&size);
|
||||
m_TextWidth=size.cx;
|
||||
SelectObject(hdc,font0);
|
||||
ReleaseDC(m_StatusBar,hdc);
|
||||
}
|
||||
|
||||
// reset the parts to apply the new text width
|
||||
m_TextWidth+=32;
|
||||
ResetParts();
|
||||
|
||||
// set text and icon
|
||||
SendMessage(m_StatusBar,SB_SETTEXT,PART_ZONE+PART_OFFSET,(LPARAM)text);
|
||||
SendMessage(m_StatusBar,SB_SETICON,PART_ZONE,(LPARAM)hIcon);
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CClassicIEBHO::OnProgressChange( long progress, long progressMax )
|
||||
{
|
||||
if (!(m_Settings&IE_SETTING_PROGRESS))
|
||||
return S_OK;
|
||||
bool bVisible=(IsWindowVisible(m_ProgressBar)!=0);
|
||||
if (progress<0 || progressMax==0)
|
||||
{
|
||||
m_Progress=-1;
|
||||
if (!bVisible) return S_OK;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_Progress=progress*100/progressMax;
|
||||
SendMessage(m_ProgressBar,PBM_SETPOS,m_Progress,0);
|
||||
if (bVisible) return S_OK;
|
||||
}
|
||||
ResetParts();
|
||||
RedrawWindow(m_StatusBar,NULL,NULL,RDW_UPDATENOW|RDW_ALLCHILDREN);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CClassicIEBHO::OnQuit( void )
|
||||
{
|
||||
if (m_pWebBrowser && m_dwEventCookie!=0xFEFEFEFE) // ATL's event cookie is 0xFEFEFEFE, when the sink is not advised
|
||||
return DispEventUnadvise(m_pWebBrowser,&DIID_DWebBrowserEvents2);
|
||||
return S_OK;
|
||||
}
|
||||
93
Src/ClassicIE/ClassicIEDLL/ClassicIEBHO.h
Normal file
@@ -0,0 +1,93 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <exdispid.h>
|
||||
#include <shobjidl.h>
|
||||
#include <map>
|
||||
|
||||
// CClassicIEBHO
|
||||
|
||||
class ATL_NO_VTABLE CClassicIEBHO :
|
||||
public CComObjectRootEx<CComSingleThreadModel>,
|
||||
public CComCoClass<CClassicIEBHO, &CLSID_ClassicIEBHO>,
|
||||
public IObjectWithSiteImpl<CClassicIEBHO>,
|
||||
public IDispEventImpl<1,CClassicIEBHO,&DIID_DWebBrowserEvents2,&LIBID_SHDocVw,1,1>
|
||||
{
|
||||
public:
|
||||
CClassicIEBHO()
|
||||
{
|
||||
m_Settings=0;
|
||||
m_StatusBar=NULL;
|
||||
m_Tooltip=NULL;
|
||||
m_ProgressBar=NULL;
|
||||
m_TextWidth=0;
|
||||
m_Progress=-1;
|
||||
}
|
||||
|
||||
static HRESULT WINAPI UpdateRegistry( BOOL bRegister );
|
||||
|
||||
BEGIN_SINK_MAP( CClassicIEBHO )
|
||||
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_NAVIGATECOMPLETE2, OnNavigateComplete)
|
||||
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_PROGRESSCHANGE, OnProgressChange)
|
||||
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_ONQUIT, OnQuit)
|
||||
END_SINK_MAP()
|
||||
|
||||
BEGIN_COM_MAP(CClassicIEBHO)
|
||||
COM_INTERFACE_ENTRY(IObjectWithSite)
|
||||
END_COM_MAP()
|
||||
|
||||
|
||||
|
||||
DECLARE_PROTECT_FINAL_CONSTRUCT()
|
||||
|
||||
HRESULT FinalConstruct()
|
||||
{
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
// IObjectWithSite
|
||||
STDMETHOD(SetSite)(IUnknown *pUnkSite);
|
||||
|
||||
// DWebBrowserEvents2
|
||||
STDMETHOD(OnNavigateComplete)( IDispatch *pDisp, VARIANT *URL );
|
||||
STDMETHOD(OnProgressChange)( long progress, long progressMax );
|
||||
STDMETHOD(OnQuit)( void );
|
||||
|
||||
private:
|
||||
enum
|
||||
{
|
||||
PART_TEXT,
|
||||
PART_PROGRESS,
|
||||
PART_ZONE,
|
||||
PART_ZOOM,
|
||||
|
||||
PART_COUNT,
|
||||
PART_OFFSET=100,
|
||||
|
||||
PROGRESS_WIDTH=110,
|
||||
MIN_TEXT_WIDTH=100,
|
||||
};
|
||||
|
||||
CComPtr<IShellBrowser>m_pBrowser;
|
||||
CComPtr<IWebBrowser2> m_pWebBrowser;
|
||||
CComPtr<IInternetZoneManager> m_pZoneManager;
|
||||
CComPtr<IInternetSecurityManager> m_pSecurityManager;
|
||||
|
||||
DWORD m_Settings;
|
||||
HWND m_StatusBar;
|
||||
HWND m_Tooltip;
|
||||
HWND m_ProgressBar;
|
||||
CString m_ProtectedMode;
|
||||
int m_TextWidth;
|
||||
int m_Progress;
|
||||
std::map<unsigned int,HICON> m_IconCache;
|
||||
|
||||
static LRESULT CALLBACK SubclassStatusProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData );
|
||||
|
||||
void ResetParts( void );
|
||||
};
|
||||
|
||||
OBJECT_ENTRY_AUTO(__uuidof(ClassicIEBHO), CClassicIEBHO)
|
||||
108
Src/ClassicIE/ClassicIEDLL/ClassicIEBHO.rgs
Normal file
@@ -0,0 +1,108 @@
|
||||
HKCR
|
||||
{
|
||||
ClassicIE.ClassicIEBHO.1 = s 'ClassicIEBHO Class'
|
||||
{
|
||||
CLSID = s '{EA801577-E6AD-4BD5-8F71-4BE0154331A4}'
|
||||
}
|
||||
ClassicIE.ClassicIEBHO = s 'ClassicIEBHO Class'
|
||||
{
|
||||
CLSID = s '{EA801577-E6AD-4BD5-8F71-4BE0154331A4}'
|
||||
CurVer = s 'ClassicIE.ClassicIEBHO.1'
|
||||
}
|
||||
NoRemove CLSID
|
||||
{
|
||||
ForceRemove {EA801577-E6AD-4BD5-8F71-4BE0154331A4} = s 'ClassicIEBHO Class'
|
||||
{
|
||||
ProgID = s 'ClassicIE.ClassicIEBHO.1'
|
||||
VersionIndependentProgID = s 'ClassicIE.ClassicIEBHO'
|
||||
ForceRemove 'Programmable'
|
||||
InprocServer32 = s '%MODULE%'
|
||||
{
|
||||
val ThreadingModel = s 'Apartment'
|
||||
}
|
||||
'TypeLib' = s '{FDA50A1E-B8CE-49DE-8D17-B034A84AA280}'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HKLM
|
||||
{
|
||||
NoRemove SOFTWARE
|
||||
{
|
||||
NoRemove Microsoft
|
||||
{
|
||||
NoRemove Windows
|
||||
{
|
||||
NoRemove CurrentVersion
|
||||
{
|
||||
NoRemove Explorer
|
||||
{
|
||||
NoRemove 'Browser Helper Objects'
|
||||
{
|
||||
ForceRemove '{EA801577-E6AD-4BD5-8F71-4BE0154331A4}'
|
||||
{
|
||||
val NoExplorer = d '1'
|
||||
}
|
||||
}
|
||||
}
|
||||
NoRemove Policies
|
||||
{
|
||||
NoRemove Ext
|
||||
{
|
||||
NoRemove CLSID
|
||||
{
|
||||
ForceRemove val {EA801577-E6AD-4BD5-8F71-4BE0154331A4} = s '2'
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HKLM
|
||||
{
|
||||
NoRemove SOFTWARE
|
||||
{
|
||||
NoRemove Microsoft
|
||||
{
|
||||
NoRemove 'Internet Explorer'
|
||||
{
|
||||
NoRemove 'Low Rights'
|
||||
{
|
||||
NoRemove ElevationPolicy
|
||||
{
|
||||
ForceRemove '{56753E59-AF1D-4FBA-9E15-31557124ADA2}'
|
||||
{
|
||||
val AppPath = s '%MODULEPATH%'
|
||||
val AppName = s 'ClassicIE_32.exe'
|
||||
val Policy = d '3'
|
||||
}
|
||||
ForceRemove '{C0393554-9B48-458A-B91B-3F684D003B2F}'
|
||||
{
|
||||
val AppPath = s '%MODULEPATH%'
|
||||
val AppName = s 'ClassicIE_64.exe'
|
||||
val Policy = d '3'
|
||||
}
|
||||
ForceRemove '{02E6771D-8375-42B9-9F83-B4730F697900}'
|
||||
{
|
||||
val AppPath = s '%MODULEPATH%'
|
||||
val AppName = s 'Update.exe'
|
||||
val Policy = d '3'
|
||||
}
|
||||
}
|
||||
}
|
||||
NoRemove Extensions
|
||||
{
|
||||
ForceRemove '{56753E59-AF1D-4FBA-9E15-31557124ADA2}'
|
||||
{
|
||||
val CLSID = s '{1FBA04EE-3024-11d2-8F1F-0000F87ABD16}'
|
||||
val MenuText = s '%MENUTEXT%'
|
||||
val Exec = s '%MODULEPATH%\ClassicIE_32.exe'
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
85
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL.cpp
Normal file
@@ -0,0 +1,85 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "resource.h"
|
||||
#include "ClassicIEDLL_h.h"
|
||||
#include "ClassicIEDLL.h"
|
||||
#include "Settings.h"
|
||||
#include "dllmain.h"
|
||||
|
||||
// Used to determine whether the DLL can be unloaded by OLE
|
||||
STDAPI DllCanUnloadNow(void)
|
||||
{
|
||||
return _AtlModule.DllCanUnloadNow();
|
||||
}
|
||||
|
||||
|
||||
// Returns a class factory to create an object of the requested type
|
||||
STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID* ppv)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
return _AtlModule.DllGetClassObject(rclsid, riid, ppv);
|
||||
}
|
||||
|
||||
|
||||
// DllRegisterServer - Adds entries to the system registry
|
||||
STDAPI DllRegisterServer(void)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
// registers object, typelib and all interfaces in typelib
|
||||
HRESULT res=_AtlModule.DllRegisterServer();
|
||||
if (SUCCEEDED(res))
|
||||
{
|
||||
// mark the extension as compatible with the enhanced protected mode of IE10
|
||||
CComPtr<ICatRegister> catRegister;
|
||||
catRegister.CoCreateInstance(CLSID_StdComponentCategoriesMgr);
|
||||
if (catRegister)
|
||||
{
|
||||
CATID CATID_AppContainerCompatible={0x59fb2056,0xd625,0x48d0,{0xa9,0x44,0x1a,0x85,0xb5,0xab,0x26,0x40}};
|
||||
catRegister->RegisterClassImplCategories(CLSID_ClassicIEBHO,1,&CATID_AppContainerCompatible);
|
||||
}
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
// DllUnregisterServer - Removes entries from the system registry
|
||||
STDAPI DllUnregisterServer(void)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
return _AtlModule.DllUnregisterServer();
|
||||
}
|
||||
|
||||
// DllInstall - Adds/Removes entries to the system registry per user
|
||||
// per machine.
|
||||
STDAPI DllInstall(BOOL bInstall, LPCWSTR pszCmdLine)
|
||||
{
|
||||
WaitDllInitThread();
|
||||
HRESULT hr = E_FAIL;
|
||||
static const wchar_t szUserSwitch[] = L"user";
|
||||
|
||||
if (pszCmdLine != NULL)
|
||||
{
|
||||
if (_wcsnicmp(pszCmdLine, szUserSwitch, _countof(szUserSwitch)) == 0)
|
||||
{
|
||||
AtlSetPerUserRegistration(true);
|
||||
}
|
||||
}
|
||||
|
||||
if (bInstall)
|
||||
{
|
||||
hr = DllRegisterServer();
|
||||
if (FAILED(hr))
|
||||
{
|
||||
DllUnregisterServer();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
hr = DllUnregisterServer();
|
||||
}
|
||||
|
||||
return hr;
|
||||
}
|
||||
34
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL.h
Normal file
@@ -0,0 +1,34 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifdef CLASSICIEDLL_EXPORTS
|
||||
#define CSIEAPI __declspec(dllexport)
|
||||
#else
|
||||
#define CSIEAPI __declspec(dllimport)
|
||||
#endif
|
||||
|
||||
void InitClassicIE( HMODULE hModule );
|
||||
CSIEAPI void ShowIESettings( void );
|
||||
CSIEAPI DWORD GetIESettings( void );
|
||||
CSIEAPI void CheckForNewVersionIE( void );
|
||||
CSIEAPI void WaitDllInitThread( void );
|
||||
CSIEAPI void DllLogToFile( const wchar_t *location, const wchar_t *message, ... );
|
||||
|
||||
#ifndef _WIN64
|
||||
CSIEAPI bool DllSaveAdmx( const char *admxFile, const char *admlFile, const char *docFile, const wchar_t *language );
|
||||
#endif
|
||||
CSIEAPI bool DllImportSettingsXml( const wchar_t *fname );
|
||||
CSIEAPI bool DllExportSettingsXml( const wchar_t *fname );
|
||||
|
||||
enum
|
||||
{
|
||||
IE_SETTING_CAPTION=1,
|
||||
IE_SETTING_PROGRESS=2,
|
||||
IE_SETTING_ZONE=4,
|
||||
IE_SETTING_PROTECTED=8,
|
||||
};
|
||||
|
||||
#define CIE_LOG L"Software\\OpenShell\\ClassicIE\\Settings|LogLevel|%LOCALAPPDATA%\\OpenShell\\ClassicIELog.txt"
|
||||
36
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL.idl
Normal file
@@ -0,0 +1,36 @@
|
||||
// ClassicIEDLL.idl : IDL source for ClassicIEDLL
|
||||
//
|
||||
|
||||
// This file will be processed by the MIDL tool to
|
||||
// produce the type library (ClassicIEDLL.tlb) and marshalling code.
|
||||
|
||||
import "oaidl.idl";
|
||||
import "ocidl.idl";
|
||||
|
||||
[
|
||||
object,
|
||||
uuid(C698A81E-5D02-42B1-9801-5381CA8BBC2F),
|
||||
dual,
|
||||
nonextensible,
|
||||
helpstring("IClassicIEBHO Interface"),
|
||||
pointer_default(unique)
|
||||
]
|
||||
interface IClassicIEBHO : IDispatch{
|
||||
};
|
||||
[
|
||||
uuid(FDA50A1E-B8CE-49DE-8D17-B034A84AA280),
|
||||
version(1.0),
|
||||
helpstring("ClassicIE 1.0 Type Library")
|
||||
]
|
||||
library ClassicIEDLLLib
|
||||
{
|
||||
importlib("stdole2.tlb");
|
||||
[
|
||||
uuid(EA801577-E6AD-4BD5-8F71-4BE0154331A4),
|
||||
helpstring("ClassicIEBHO Class")
|
||||
]
|
||||
coclass ClassicIEBHO
|
||||
{
|
||||
[default] interface IClassicIEBHO;
|
||||
};
|
||||
};
|
||||
186
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL.rc
Normal file
@@ -0,0 +1,186 @@
|
||||
// Microsoft Visual C++ generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
#define APSTUDIO_READONLY_SYMBOLS
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#include "winres.h"
|
||||
#include "..\..\Lib\resource.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
|
||||
#pragma code_page(1252)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#include ""afxres.h""\r\n"
|
||||
"#include ""..\\..\\Lib\\resource.h""\r\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#include ""..\\..\\Lib\\resource.h""\r\n"
|
||||
"#include ""..\\..\\Lib\\Lib.rc""\r\r\n"
|
||||
"1 TYPELIB ""ClassicIEDLL.tlb""\r\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Version
|
||||
//
|
||||
|
||||
VS_VERSION_INFO VERSIONINFO
|
||||
FILEVERSION _PRODUCT_VERSION
|
||||
PRODUCTVERSION _PRODUCT_VERSION
|
||||
FILEFLAGSMASK 0x3fL
|
||||
#ifdef _DEBUG
|
||||
FILEFLAGS 0x1L
|
||||
#else
|
||||
FILEFLAGS 0x0L
|
||||
#endif
|
||||
FILEOS 0x4L
|
||||
FILETYPE 0x2L
|
||||
FILESUBTYPE 0x0L
|
||||
BEGIN
|
||||
BLOCK "StringFileInfo"
|
||||
BEGIN
|
||||
BLOCK "040904e4"
|
||||
BEGIN
|
||||
VALUE "CompanyName", "Open-Shell"
|
||||
VALUE "FileDescription", "Customizations for the title bar and status bar of IE"
|
||||
VALUE "FileVersion", _PRODUCT_VERSION_STR
|
||||
VALUE "InternalName", "ClassicIEDLL.dll"
|
||||
VALUE "LegalCopyright", "Copyright (C) 2017-2018, The Open-Shell Team"
|
||||
VALUE "OriginalFilename", "ClassicIEDLL.dll"
|
||||
VALUE "ProductName", "Open-Shell"
|
||||
VALUE "ProductVersion", _PRODUCT_VERSION_STR
|
||||
END
|
||||
END
|
||||
BLOCK "VarFileInfo"
|
||||
BEGIN
|
||||
VALUE "Translation", 0x409, 1252
|
||||
END
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// REGISTRY
|
||||
//
|
||||
|
||||
IDR_CLASSICIEDLL REGISTRY "ClassicIEDLL.rgs"
|
||||
IDR_CLASSICIEBHO REGISTRY "ClassicIEBHO.rgs"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Icon
|
||||
//
|
||||
|
||||
// Icon with lowest ID value placed first to ensure application icon
|
||||
// remains consistent on all systems.
|
||||
IDI_APPICON ICON "..\\..\\Setup\\OpenShell.ico"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Bitmap
|
||||
//
|
||||
|
||||
IDB_GLOW BITMAP "glow.bmp"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// String Table
|
||||
//
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_APP_TITLE "Classic IE"
|
||||
IDS_SETTINGS_TITLE "Classic IE Settings"
|
||||
IDS_SETTINGS_TITLE_VER "Classic IE Settings %d.%d.%d"
|
||||
IDS_NEW_SETTINGS "The new settings will take effect after you restart Internet Explorer."
|
||||
IDS_TITLE_SETTINGS "Title Bar"
|
||||
IDS_SHOW_CAPTION "Show caption in the title bar"
|
||||
IDS_SHOW_CAPTION_TIP "When this is checked, Internet Explorer will show the page title in the title bar"
|
||||
IDS_CENTER_CAPTION "Center caption"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_CENTER_CAPTION_TIP "When this is checked, the caption will be centered in the title bar"
|
||||
IDS_LANGUAGE_SETTINGS "Language"
|
||||
IDS_CAPTION_FONT "Caption font"
|
||||
IDS_CAPTION_FONT_TIP "Select the font and text size to use for the caption"
|
||||
IDS_TEXT_COLOR "Text color (RRGGBB)"
|
||||
IDS_TEXT_COLOR_TIP "Select the color for the caption text"
|
||||
IDS_MAXTEXT_COLOR "Text color (maximized) (RRGGBB)"
|
||||
IDS_MAXTEXT_COLOR_TIP "Select the color for the caption text when the window is maximized"
|
||||
IDS_INTEXT_COLOR "Text color (inactive) (RRGGBB)"
|
||||
IDS_INTEXT_COLOR_TIP "Select the color for the caption text when the window is inactive"
|
||||
IDS_MAXINTEXT_COLOR "Text color (maximized, inactive) (RRGGBB)"
|
||||
IDS_MAXINTEXT_COLOR_TIP "Select the color for the caption text when the window is maximized and inactive"
|
||||
IDS_GLOW "Text glow"
|
||||
IDS_GLOW_TIP "When this is checked, the text will have a glow around it"
|
||||
IDS_GLOW_COLOR "Glow color (RRGGBB)"
|
||||
IDS_GLOW_COLOR_TIP "Select the color for the caption glow"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_MAXGLOW "Text glow (maximized)"
|
||||
IDS_MAXGLOW_TIP "When this is checked, the text in the maximized window will have a glow around it"
|
||||
IDS_MAXGLOW_COLOR "Glow color (maximized) (RRGGBB)"
|
||||
IDS_MAXGLOW_COLOR_TIP "Select the color for the caption glow when the window is maximized"
|
||||
IDS_STATUS_SETTINGS "Status Bar"
|
||||
IDS_SHOW_PROGRESS "Show progress"
|
||||
IDS_SHOW_PROGRESS_TIP "When this is checked, the status bar will show the progress of the current page"
|
||||
IDS_SHOW_ZONE "Show zone"
|
||||
IDS_SHOW_ZONE_TIP "When this is checked, the status bar will show the current security zone"
|
||||
IDS_SHOW_PROTECTED "Show protected mode"
|
||||
IDS_SHOW_PROTECTED_TIP "When this is checked, the status bar will show if the browser is running in protected mode"
|
||||
IDS_SHOW_ICON "Show icon in the title bar"
|
||||
IDS_SHOW_ICON_TIP "When this is checked, Internet Explorer will show the page icon in the title bar"
|
||||
END
|
||||
|
||||
#endif // English (U.S.) resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
#ifndef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 3 resource.
|
||||
//
|
||||
#include "..\..\Lib\resource.h"
|
||||
#include "..\..\Lib\Lib.rc"
|
||||
|
||||
1 TYPELIB "ClassicIEDLL.tlb"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#endif // not APSTUDIO_INVOKED
|
||||
|
||||
11
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL.rgs
Normal file
@@ -0,0 +1,11 @@
|
||||
HKCR
|
||||
{
|
||||
NoRemove AppID
|
||||
{
|
||||
'%APPID%' = s 'ClassicIE'
|
||||
'ClassicIE.DLL'
|
||||
{
|
||||
val AppID = s '%APPID%'
|
||||
}
|
||||
}
|
||||
}
|
||||
122
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL.vcxproj
Normal file
@@ -0,0 +1,122 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|x64">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|x64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Setup|Win32">
|
||||
<Configuration>Setup</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Setup|x64">
|
||||
<Configuration>Setup</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<ProjectGuid>{BC0E6E7C-08C1-4F12-A754-4608E5A22FA8}</ProjectGuid>
|
||||
<RootNamespace>ClassicIEDLL</RootNamespace>
|
||||
<Keyword>AtlProj</Keyword>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
|
||||
<UseOfAtl>Static</UseOfAtl>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<WholeProgramOptimization Condition="'$(Configuration)'!='Debug'">true</WholeProgramOptimization>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets">
|
||||
<Import Project="..\..\Common.props" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup Condition="'$(Platform)'=='Win32'">
|
||||
<TargetName>$(ProjectName)_32</TargetName>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Platform)'=='x64'">
|
||||
<TargetName>$(ProjectName)_64</TargetName>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup>
|
||||
<ClCompile>
|
||||
<PreprocessorDefinitions>_USRDLL;CLASSICIEDLL_EXPORTS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ClCompile>
|
||||
<ResourceCompile>
|
||||
<AdditionalIncludeDirectories>$(IntDir);%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
</ResourceCompile>
|
||||
<Link>
|
||||
<AdditionalDependencies>uxtheme.lib;dwmapi.lib;comctl32.lib;msimg32.lib;winmm.lib;htmlhelp.lib;wininet.lib;wintrust.lib;crypt32.lib;%(AdditionalDependencies)</AdditionalDependencies>
|
||||
<ModuleDefinitionFile>$(TargetName).def</ModuleDefinitionFile>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)'!='Setup'">
|
||||
<Link>
|
||||
<RegisterOutput>true</RegisterOutput>
|
||||
<PerUserRedirection>true</PerUserRedirection>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="ClassicIEBHO.cpp" />
|
||||
<ClCompile Include="ClassicIEDLL.cpp" />
|
||||
<ClCompile Include="ClassicIEDLL_i.c">
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
<ClCompile Include="dllmain.cpp" />
|
||||
<ClCompile Include="DrawCaption.cpp" />
|
||||
<ClCompile Include="SettingsUI.cpp" />
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<PrecompiledHeader>Create</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Midl Include="ClassicIEDLL.idl" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="ClassicIEBHO.rgs" />
|
||||
<None Include="ClassicIEDLL.rgs" />
|
||||
<None Include="ClassicIEDLL_32.def" />
|
||||
<None Include="ClassicIEDLL_64.def" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="ClassicIEBHO.h" />
|
||||
<ClInclude Include="ClassicIEDLL.h" />
|
||||
<ClInclude Include="ClassicIEDLL_h.h" />
|
||||
<ClInclude Include="dllmain.h" />
|
||||
<ClInclude Include="Resource.h" />
|
||||
<ClInclude Include="SettingsUI.h" />
|
||||
<ClInclude Include="stdafx.h" />
|
||||
<ClInclude Include="targetver.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="ClassicIEDLL.rc" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Image Include="..\..\Setup\OpenShell.ico" />
|
||||
<Image Include="glow.bmp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Lib\Lib.vcxproj">
|
||||
<Project>{d42fe717-485b-492d-884a-1999f6d51154}</Project>
|
||||
<ReferenceOutputAssembly>false</ReferenceOutputAssembly>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
101
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL.vcxproj.filters
Normal file
@@ -0,0 +1,101 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="Source Files">
|
||||
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
|
||||
<Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Header Files">
|
||||
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
|
||||
<Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Resource Files">
|
||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Generated Files">
|
||||
<UniqueIdentifier>{8ffd1dbd-fd04-405c-a733-b3147c1c95e9}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="ClassicIEBHO.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ClassicIEDLL.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="dllmain.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="DrawCaption.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="SettingsUI.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ClassicIEDLL_i.c">
|
||||
<Filter>Generated Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Midl Include="ClassicIEDLL.idl">
|
||||
<Filter>Source Files</Filter>
|
||||
</Midl>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="ClassicIEDLL_32.def">
|
||||
<Filter>Source Files</Filter>
|
||||
</None>
|
||||
<None Include="ClassicIEDLL_64.def">
|
||||
<Filter>Source Files</Filter>
|
||||
</None>
|
||||
<None Include="ClassicIEBHO.rgs">
|
||||
<Filter>Resource Files</Filter>
|
||||
</None>
|
||||
<None Include="ClassicIEDLL.rgs">
|
||||
<Filter>Resource Files</Filter>
|
||||
</None>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="ClassicIEBHO.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ClassicIEDLL.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="dllmain.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Resource.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="SettingsUI.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="stdafx.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="targetver.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ClassicIEDLL_h.h">
|
||||
<Filter>Generated Files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="ClassicIEDLL.rc">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ResourceCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Image Include="..\..\Setup\OpenShell.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="glow.bmp">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
11
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL_32.def
Normal file
@@ -0,0 +1,11 @@
|
||||
; ClassicIEDLL_32.def : Declares the module parameters.
|
||||
|
||||
LIBRARY "ClassicIEDLL_32.DLL"
|
||||
|
||||
EXPORTS
|
||||
DllCanUnloadNow PRIVATE
|
||||
DllGetClassObject PRIVATE
|
||||
DllRegisterServer PRIVATE
|
||||
DllUnregisterServer PRIVATE
|
||||
DllInstall PRIVATE
|
||||
DllSaveAdmx
|
||||
10
Src/ClassicIE/ClassicIEDLL/ClassicIEDLL_64.def
Normal file
@@ -0,0 +1,10 @@
|
||||
; ClassicIEDLL.def : Declares the module parameters.
|
||||
|
||||
LIBRARY "ClassicIEDLL_64.DLL"
|
||||
|
||||
EXPORTS
|
||||
DllCanUnloadNow PRIVATE
|
||||
DllGetClassObject PRIVATE
|
||||
DllRegisterServer PRIVATE
|
||||
DllUnregisterServer PRIVATE
|
||||
DllInstall PRIVATE
|
||||
346
Src/ClassicIE/ClassicIEDLL/DrawCaption.cpp
Normal file
@@ -0,0 +1,346 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "ClassicIEDLL.h"
|
||||
#include "Settings.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "SettingsUIHelper.h"
|
||||
#include <vssym32.h>
|
||||
#include <dwmapi.h>
|
||||
|
||||
static _declspec(thread) SIZE g_SysButtonSize; // the size of the system buttons (close, minimize) for this thread's window
|
||||
static WNDPROC g_OldClassCaptionProc;
|
||||
static HBITMAP g_GlowBmp;
|
||||
static HBITMAP g_GlowBmpMax;
|
||||
static LONG g_bInjected; // the process is injected
|
||||
static int g_DPI;
|
||||
static UINT g_Message; // private message to detect if the caption is subclassed
|
||||
static ATOM g_SubclassAtom;
|
||||
|
||||
struct CustomCaption
|
||||
{
|
||||
int leftPadding;
|
||||
int topPadding;
|
||||
int iconPadding;
|
||||
};
|
||||
|
||||
static CustomCaption g_CustomCaption[3]={
|
||||
{2,3,10}, // Aero
|
||||
{4,2,10}, // Aero maximized
|
||||
{4,2,10}, // Basic
|
||||
};
|
||||
|
||||
void GetSysButtonSize( HWND hWnd )
|
||||
{
|
||||
TITLEBARINFOEX titleInfo={sizeof(titleInfo)};
|
||||
SendMessage(hWnd,WM_GETTITLEBARINFOEX,0,(LPARAM)&titleInfo);
|
||||
int buttonLeft=titleInfo.rgrect[2].left;
|
||||
if (buttonLeft>titleInfo.rgrect[5].left) buttonLeft=titleInfo.rgrect[5].left;
|
||||
int buttonRight=titleInfo.rgrect[2].right;
|
||||
if (buttonRight<titleInfo.rgrect[5].right) buttonRight=titleInfo.rgrect[5].right;
|
||||
|
||||
int w=buttonRight-buttonLeft;
|
||||
int h=titleInfo.rgrect[5].bottom-titleInfo.rgrect[5].top;
|
||||
g_SysButtonSize.cx=w;
|
||||
g_SysButtonSize.cy=h;
|
||||
}
|
||||
|
||||
// Subclasses the main IE frame to redraw the caption when the text changes
|
||||
static LRESULT CALLBACK SubclassFrameProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
|
||||
{
|
||||
if (uMsg==g_Message)
|
||||
{
|
||||
GetSysButtonSize(hWnd);
|
||||
HWND caption=FindWindowEx(hWnd,NULL,L"Client Caption",NULL);
|
||||
if (caption)
|
||||
InvalidateRect(caption,NULL,FALSE);
|
||||
return 0;
|
||||
}
|
||||
if (uMsg==WM_SETTEXT || uMsg==WM_ACTIVATE)
|
||||
{
|
||||
HWND caption=FindWindowEx(hWnd,NULL,L"Client Caption",NULL);
|
||||
if (caption)
|
||||
InvalidateRect(caption,NULL,FALSE);
|
||||
}
|
||||
if (uMsg==WM_SIZE || uMsg==WM_SETTINGCHANGE)
|
||||
{
|
||||
GetSysButtonSize(hWnd);
|
||||
if (uMsg==WM_SETTINGCHANGE)
|
||||
{
|
||||
CSettingsLockWrite lock;
|
||||
UpdateSettings();
|
||||
}
|
||||
}
|
||||
while (1)
|
||||
{
|
||||
WNDPROC proc=(WNDPROC)GetProp(hWnd,MAKEINTATOM(g_SubclassAtom));
|
||||
if (proc)
|
||||
return CallWindowProc(proc,hWnd,uMsg,wParam,lParam);
|
||||
}
|
||||
}
|
||||
|
||||
static LRESULT DefCaptionProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
|
||||
{
|
||||
while (1)
|
||||
{
|
||||
WNDPROC proc=(WNDPROC)GetProp(hWnd,MAKEINTATOM(g_SubclassAtom));
|
||||
if (proc)
|
||||
return CallWindowProc(proc,hWnd,uMsg,wParam,lParam);
|
||||
}
|
||||
}
|
||||
|
||||
// Subclasses the caption window to draw the icon and the text
|
||||
static LRESULT CALLBACK SubclassCaptionProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
|
||||
{
|
||||
if (uMsg==g_Message)
|
||||
return 1;
|
||||
if (uMsg==WM_ERASEBKGND)
|
||||
return 0;
|
||||
if (uMsg==WM_PAINT)
|
||||
{
|
||||
HTHEME theme=OpenThemeData(hWnd,L"Window");
|
||||
if (!theme) return DefCaptionProc(hWnd,uMsg,wParam,lParam);
|
||||
|
||||
// get the icon and the text from the parent
|
||||
HWND parent=GetParent(hWnd);
|
||||
wchar_t caption[256];
|
||||
GetWindowText(parent,caption,_countof(caption));
|
||||
HICON hIcon=(HICON)SendMessage(parent,WM_GETICON,ICON_SMALL,0);
|
||||
int iconSize=GetSystemMetrics(SM_CXSMICON);
|
||||
|
||||
bool bMaximized=IsZoomed(parent)!=0;
|
||||
bool bActive=(parent==GetActiveWindow());
|
||||
RECT rc;
|
||||
GetClientRect(hWnd,&rc);
|
||||
|
||||
if (!g_DPI)
|
||||
{
|
||||
HDC hdc=GetDC(NULL);
|
||||
g_DPI=GetDeviceCaps(hdc,LOGPIXELSY);
|
||||
ReleaseDC(NULL,hdc);
|
||||
}
|
||||
|
||||
// create a font from the user settings
|
||||
HFONT font=CreateFontSetting(GetSettingString(L"CaptionFont"),g_DPI);
|
||||
if (!font)
|
||||
{
|
||||
LOGFONT lFont;
|
||||
GetThemeSysFont(theme,TMT_CAPTIONFONT,&lFont);
|
||||
font=CreateFontIndirect(&lFont);
|
||||
}
|
||||
|
||||
bool bIcon=GetSettingBool(L"ShowIcon");
|
||||
bool bCenter=GetSettingBool(L"CenterCaption");
|
||||
bool bGlow=GetSettingBool(bMaximized?L"MaxGlow":L"Glow");
|
||||
|
||||
DTTOPTS opts={sizeof(opts),DTT_COMPOSITED|DTT_TEXTCOLOR};
|
||||
opts.crText=GetSettingInt(bMaximized?(bActive?L"MaxColor":L"InactiveMaxColor"):(bActive?L"TextColor":L"InactiveColor"))&0xFFFFFF;
|
||||
|
||||
BOOL bComposition;
|
||||
if (SUCCEEDED(DwmIsCompositionEnabled(&bComposition)) && bComposition)
|
||||
{
|
||||
// Aero Theme
|
||||
PAINTSTRUCT ps;
|
||||
HDC hdc=BeginPaint(hWnd,&ps);
|
||||
|
||||
BP_PAINTPARAMS paintParams={sizeof(paintParams),BPPF_ERASE};
|
||||
HDC hdcPaint=NULL;
|
||||
HPAINTBUFFER hBufferedPaint=BeginBufferedPaint(hdc,&ps.rcPaint,BPBF_TOPDOWNDIB,&paintParams,&hdcPaint);
|
||||
if (hdcPaint)
|
||||
{
|
||||
// exclude the caption buttons
|
||||
rc.right-=g_SysButtonSize.cx+5;
|
||||
if (GetWinVersion()==WIN_VER_VISTA) rc.bottom++;
|
||||
if (!bMaximized)
|
||||
{
|
||||
rc.left+=g_CustomCaption[0].leftPadding;
|
||||
int y=g_CustomCaption[0].topPadding;
|
||||
if (y>rc.bottom-iconSize) y=rc.bottom-iconSize;
|
||||
if (bIcon)
|
||||
{
|
||||
DrawIconEx(hdcPaint,rc.left,y,hIcon,iconSize,iconSize,0,NULL,DI_NORMAL|DI_NOMIRROR);
|
||||
rc.left+=iconSize;
|
||||
}
|
||||
rc.left+=g_CustomCaption[0].iconPadding;
|
||||
rc.bottom++;
|
||||
}
|
||||
else
|
||||
{
|
||||
// when the window is maximized, the caption bar is partially off-screen, so align the icon to the bottom
|
||||
rc.left+=g_CustomCaption[1].leftPadding;
|
||||
if (bIcon)
|
||||
{
|
||||
DrawIconEx(hdcPaint,rc.left,rc.bottom-iconSize-g_CustomCaption[1].topPadding,hIcon,iconSize,iconSize,0,NULL,DI_NORMAL|DI_NOMIRROR);
|
||||
rc.left+=iconSize;
|
||||
}
|
||||
rc.left+=g_CustomCaption[1].iconPadding;
|
||||
if (GetWinVersion()>=WIN_VER_WIN10)
|
||||
rc.bottom++;
|
||||
}
|
||||
if (GetWinVersion()<WIN_VER_WIN10)
|
||||
rc.top=rc.bottom-g_SysButtonSize.cy;
|
||||
HFONT font0=(HFONT)SelectObject(hdcPaint,font);
|
||||
RECT rcText={0,0,0,0};
|
||||
opts.dwFlags|=DTT_CALCRECT;
|
||||
DrawThemeTextEx(theme,hdcPaint,0,0,caption,-1,DT_VCENTER|DT_NOPREFIX|DT_SINGLELINE|DT_CALCRECT,&rcText,&opts);
|
||||
int textWidth=rcText.right-rcText.left;
|
||||
if (bCenter && textWidth<rc.right-rc.left)
|
||||
{
|
||||
rc.left+=(rc.right-rc.left-textWidth)/2;
|
||||
}
|
||||
if (textWidth>rc.right-rc.left)
|
||||
textWidth=rc.right-rc.left;
|
||||
opts.dwFlags&=~DTT_CALCRECT;
|
||||
|
||||
if (bGlow)
|
||||
{
|
||||
HDC hSrc=CreateCompatibleDC(hdcPaint);
|
||||
HGDIOBJ bmp0=SelectObject(hSrc,bMaximized?g_GlowBmpMax:g_GlowBmp);
|
||||
BLENDFUNCTION func={AC_SRC_OVER,0,255,AC_SRC_ALPHA};
|
||||
AlphaBlend(hdcPaint,rc.left-11,rc.top,11,rc.bottom-rc.top,hSrc,0,0,11,24,func);
|
||||
AlphaBlend(hdcPaint,rc.left,rc.top,textWidth,rc.bottom-rc.top,hSrc,11,0,2,24,func);
|
||||
AlphaBlend(hdcPaint,rc.left+textWidth,rc.top,11,rc.bottom-rc.top,hSrc,13,0,11,24,func);
|
||||
SelectObject(hSrc,bmp0);
|
||||
DeleteDC(hSrc);
|
||||
}
|
||||
DrawThemeTextEx(theme,hdcPaint,0,0,caption,-1,DT_VCENTER|DT_NOPREFIX|DT_SINGLELINE|DT_END_ELLIPSIS,&rc,&opts);
|
||||
SelectObject(hdcPaint,font0);
|
||||
|
||||
EndBufferedPaint(hBufferedPaint,TRUE);
|
||||
}
|
||||
EndPaint(hWnd,&ps);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Basic Theme
|
||||
|
||||
// first draw the caption bar
|
||||
DefCaptionProc(hWnd,uMsg,wParam,lParam);
|
||||
|
||||
// then draw the caption directly in the window DC
|
||||
HDC hdc=GetWindowDC(hWnd);
|
||||
|
||||
// exclude the caption buttons
|
||||
rc.right-=g_SysButtonSize.cx+5;
|
||||
rc.top=rc.bottom-g_SysButtonSize.cy;
|
||||
|
||||
rc.left+=g_CustomCaption[2].leftPadding;
|
||||
if (bIcon)
|
||||
{
|
||||
DrawIconEx(hdc,rc.left,rc.bottom-iconSize-g_CustomCaption[2].topPadding,hIcon,iconSize,iconSize,0,NULL,DI_NORMAL|DI_NOMIRROR);
|
||||
rc.left+=iconSize;
|
||||
}
|
||||
rc.left+=g_CustomCaption[2].iconPadding;
|
||||
|
||||
HFONT font0=(HFONT)SelectObject(hdc,font);
|
||||
RECT rcText={0,0,0,0};
|
||||
opts.dwFlags|=DTT_CALCRECT;
|
||||
DrawThemeTextEx(theme,hdc,0,0,caption,-1,DT_VCENTER|DT_NOPREFIX|DT_SINGLELINE|DT_CALCRECT,&rcText,&opts);
|
||||
int textWidth=rcText.right-rcText.left;
|
||||
if (bCenter && textWidth<rc.right-rc.left)
|
||||
{
|
||||
rc.left+=(rc.right-rc.left-textWidth)/2;
|
||||
}
|
||||
if (textWidth>rc.right-rc.left)
|
||||
textWidth=rc.right-rc.left;
|
||||
opts.dwFlags&=~DTT_CALCRECT;
|
||||
|
||||
if (bGlow)
|
||||
{
|
||||
HDC hSrc=CreateCompatibleDC(hdc);
|
||||
HGDIOBJ bmp0=SelectObject(hSrc,bMaximized?g_GlowBmpMax:g_GlowBmp);
|
||||
BLENDFUNCTION func={AC_SRC_OVER,0,255,AC_SRC_ALPHA};
|
||||
AlphaBlend(hdc,rc.left-11,rc.top,11,rc.bottom-rc.top,hSrc,0,0,11,24,func);
|
||||
AlphaBlend(hdc,rc.left,rc.top,textWidth,rc.bottom-rc.top,hSrc,11,0,2,24,func);
|
||||
AlphaBlend(hdc,rc.left+textWidth,rc.top,11,rc.bottom-rc.top,hSrc,13,0,11,24,func);
|
||||
SelectObject(hSrc,bmp0);
|
||||
DeleteDC(hSrc);
|
||||
}
|
||||
DrawThemeTextEx(theme,hdc,0,0,caption,-1,DT_VCENTER|DT_NOPREFIX|DT_SINGLELINE|DT_END_ELLIPSIS,&rc,&opts);
|
||||
SelectObject(hdc,font0);
|
||||
|
||||
ReleaseDC(hWnd,hdc);
|
||||
}
|
||||
|
||||
DeleteObject(font);
|
||||
CloseThemeData(theme);
|
||||
return 0;
|
||||
}
|
||||
return DefCaptionProc(hWnd,uMsg,wParam,lParam);
|
||||
}
|
||||
|
||||
// Replacement proc for the "Client Caption" class that hooks the main frame and the caption windows
|
||||
static LRESULT CALLBACK ClassCaptionProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
|
||||
{
|
||||
if (uMsg==WM_CREATE)
|
||||
{
|
||||
WNDPROC proc=(WNDPROC)SetWindowLongPtr(hWnd,GWLP_WNDPROC,(LONG_PTR)SubclassCaptionProc);
|
||||
SetProp(hWnd,MAKEINTATOM(g_SubclassAtom),(HANDLE)proc);
|
||||
HWND frame=GetParent(hWnd);
|
||||
proc=(WNDPROC)SetWindowLongPtr(frame,GWLP_WNDPROC,(LONG_PTR)SubclassFrameProc);
|
||||
SetProp(frame,MAKEINTATOM(g_SubclassAtom),(HANDLE)proc);
|
||||
PostMessage(frame,g_Message,0,0);
|
||||
}
|
||||
return CallWindowProc(g_OldClassCaptionProc,hWnd,uMsg,wParam,lParam);
|
||||
}
|
||||
|
||||
static BOOL CALLBACK EnumTopWindows( HWND hwnd, LPARAM lParam )
|
||||
{
|
||||
DWORD processId;
|
||||
DWORD threadId=GetWindowThreadProcessId(hwnd,&processId);
|
||||
if (processId==GetCurrentProcessId())
|
||||
{
|
||||
HWND caption=FindWindowEx(hwnd,NULL,L"Client Caption",NULL);
|
||||
if (caption)
|
||||
{
|
||||
LogToFile(CIE_LOG,L"InitClassicIE: caption=%p",caption);
|
||||
if (!g_OldClassCaptionProc)
|
||||
g_OldClassCaptionProc=(WNDPROC)SetClassLongPtr(caption,GCLP_WNDPROC,(LONG_PTR)ClassCaptionProc);
|
||||
WNDPROC proc=(WNDPROC)SetWindowLongPtr(caption,GWLP_WNDPROC,(LONG_PTR)SubclassCaptionProc);
|
||||
SetProp(caption,MAKEINTATOM(g_SubclassAtom),(HANDLE)proc);
|
||||
proc=(WNDPROC)SetWindowLongPtr(hwnd,GWLP_WNDPROC,(LONG_PTR)SubclassFrameProc);
|
||||
SetProp(hwnd,MAKEINTATOM(g_SubclassAtom),(HANDLE)proc);
|
||||
PostMessage(hwnd,g_Message,0,0);
|
||||
}
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void InitClassicIE( HMODULE hModule )
|
||||
{
|
||||
CRegKey regKey;
|
||||
if (regKey.Open(HKEY_CURRENT_USER,GetSettingsRegPath())==ERROR_SUCCESS)
|
||||
{
|
||||
DWORD val;
|
||||
if (regKey.QueryDWORDValue(L"CustomAero",val)==ERROR_SUCCESS)
|
||||
{
|
||||
g_CustomCaption[0].leftPadding=(val&255);
|
||||
g_CustomCaption[0].topPadding=((val>>8)&255);
|
||||
g_CustomCaption[0].iconPadding=((val>>16)&255);
|
||||
}
|
||||
if (regKey.QueryDWORDValue(L"CustomAeroMax",val)==ERROR_SUCCESS)
|
||||
{
|
||||
g_CustomCaption[1].leftPadding=(val&255);
|
||||
g_CustomCaption[1].topPadding=((val>>8)&255);
|
||||
g_CustomCaption[1].iconPadding=((val>>16)&255);
|
||||
}
|
||||
if (regKey.QueryDWORDValue(L"CustomBasic",val)==ERROR_SUCCESS)
|
||||
{
|
||||
g_CustomCaption[2].leftPadding=(val&255);
|
||||
g_CustomCaption[2].topPadding=((val>>8)&255);
|
||||
g_CustomCaption[2].iconPadding=((val>>16)&255);
|
||||
}
|
||||
}
|
||||
|
||||
g_Message=RegisterWindowMessage(L"ClassicIE.Injected");
|
||||
g_SubclassAtom=GlobalAddAtom(L"ClassicIE.Subclass");
|
||||
ChangeWindowMessageFilter(g_Message,MSGFLT_ADD);
|
||||
g_GlowBmp=(HBITMAP)LoadImage(g_Instance,MAKEINTRESOURCE(IDB_GLOW),IMAGE_BITMAP,0,0,LR_CREATEDIBSECTION);
|
||||
PremultiplyBitmap(g_GlowBmp,GetSettingInt(L"GlowColor"));
|
||||
g_GlowBmpMax=(HBITMAP)LoadImage(g_Instance,MAKEINTRESOURCE(IDB_GLOW),IMAGE_BITMAP,0,0,LR_CREATEDIBSECTION);
|
||||
PremultiplyBitmap(g_GlowBmpMax,GetSettingInt(L"MaxGlowColor"));
|
||||
|
||||
EnumWindows(EnumTopWindows,0);
|
||||
}
|
||||
172
Src/ClassicIE/ClassicIEDLL/SettingsUI.cpp
Normal file
@@ -0,0 +1,172 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "Settings.h"
|
||||
#include "SettingsUIHelper.h"
|
||||
#include "LanguageSettingsHelper.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "Translations.h"
|
||||
#include "resource.h"
|
||||
#include "dllmain.h"
|
||||
#include "ClassicIEDLL.h"
|
||||
#include <dwmapi.h>
|
||||
#include <vssym32.h>
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static CSetting g_Settings[]={
|
||||
{L"Basic",CSetting::TYPE_GROUP,IDS_BASIC_SETTINGS},
|
||||
{L"EnableSettings",CSetting::TYPE_BOOL,0,0,1,CSetting::FLAG_HIDDEN|CSetting::FLAG_NOSAVE},
|
||||
|
||||
{L"TitleBar",CSetting::TYPE_GROUP,IDS_TITLE_SETTINGS},
|
||||
{L"ShowCaption",CSetting::TYPE_BOOL,IDS_SHOW_CAPTION,IDS_SHOW_CAPTION_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"ShowIcon",CSetting::TYPE_BOOL,IDS_SHOW_ICON,IDS_SHOW_ICON_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC,L"ShowCaption"},
|
||||
{L"CenterCaption",CSetting::TYPE_BOOL,IDS_CENTER_CAPTION,IDS_CENTER_CAPTION_TIP,0,CSetting::FLAG_WARM|CSetting::FLAG_BASIC,L"ShowCaption"},
|
||||
{L"CaptionFont",CSetting::TYPE_FONT,IDS_CAPTION_FONT,IDS_CAPTION_FONT_TIP,L"Segoe UI, normal, 9",CSetting::FLAG_WARM,L"ShowCaption"},
|
||||
{L"TextColor",CSetting::TYPE_COLOR,IDS_TEXT_COLOR,IDS_TEXT_COLOR_TIP,0,CSetting::FLAG_WARM,L"ShowCaption"},
|
||||
{L"MaxColor",CSetting::TYPE_COLOR,IDS_MAXTEXT_COLOR,IDS_MAXTEXT_COLOR_TIP,0,CSetting::FLAG_WARM|(1<<24),L"ShowCaption"},
|
||||
{L"InactiveColor",CSetting::TYPE_COLOR,IDS_INTEXT_COLOR,IDS_INTEXT_COLOR_TIP,0,CSetting::FLAG_WARM|(2<<24),L"ShowCaption"},
|
||||
{L"InactiveMaxColor",CSetting::TYPE_COLOR,IDS_MAXINTEXT_COLOR,IDS_MAXINTEXT_COLOR_TIP,0,CSetting::FLAG_WARM|(3<<24),L"ShowCaption"},
|
||||
{L"Glow",CSetting::TYPE_BOOL,IDS_GLOW,IDS_GLOW_TIP,0,CSetting::FLAG_WARM,L"ShowCaption"},
|
||||
{L"GlowColor",CSetting::TYPE_COLOR,IDS_GLOW_COLOR,IDS_GLOW_COLOR_TIP,0xFFFFFF,CSetting::FLAG_WARM|(4<<24),L"#Glow",L"Glow"},
|
||||
{L"MaxGlow",CSetting::TYPE_BOOL,IDS_MAXGLOW,IDS_MAXGLOW_TIP,0,CSetting::FLAG_WARM,L"ShowCaption"},
|
||||
{L"MaxGlowColor",CSetting::TYPE_COLOR,IDS_MAXGLOW_COLOR,IDS_MAXGLOW_COLOR_TIP,0xFFFFFF,CSetting::FLAG_WARM|(5<<24),L"#MaxGlow",L"MaxGlow"},
|
||||
|
||||
{L"StatusBar",CSetting::TYPE_GROUP,IDS_STATUS_SETTINGS},
|
||||
{L"ShowProgress",CSetting::TYPE_BOOL,IDS_SHOW_PROGRESS,IDS_SHOW_PROGRESS_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"ShowZone",CSetting::TYPE_BOOL,IDS_SHOW_ZONE,IDS_SHOW_ZONE_TIP,1,CSetting::FLAG_WARM|CSetting::FLAG_BASIC},
|
||||
{L"ShowProtected",CSetting::TYPE_BOOL,IDS_SHOW_PROTECTED,IDS_SHOW_PROTECTED_TIP,1,CSetting::FLAG_WARM,L"ShowZone",L"ShowZone"},
|
||||
|
||||
{L"Language",CSetting::TYPE_GROUP,IDS_LANGUAGE_SETTINGS,0,0,0,NULL,NULL,GetLanguageSettings(COMPONENT_IE)},
|
||||
{L"Language",CSetting::TYPE_STRING,0,0,L"",CSetting::FLAG_SHARED},
|
||||
|
||||
{NULL}
|
||||
};
|
||||
|
||||
void UpgradeSettings( bool bShared )
|
||||
{
|
||||
}
|
||||
|
||||
void UpdateSettings( void )
|
||||
{
|
||||
bool bWin8=(GetWinVersion()>=WIN_VER_WIN8);
|
||||
|
||||
BOOL bComposition=0;
|
||||
if (FAILED(DwmIsCompositionEnabled(&bComposition)))
|
||||
bComposition=FALSE;
|
||||
|
||||
if (bComposition && bWin8)
|
||||
{
|
||||
// check for High Contrast theme on Win8
|
||||
HIGHCONTRAST contrast={sizeof(contrast)};
|
||||
if (SystemParametersInfo(SPI_GETHIGHCONTRAST,sizeof(contrast),&contrast,0) && (contrast.dwFlags&HCF_HIGHCONTRASTON))
|
||||
bComposition=FALSE;
|
||||
else
|
||||
{
|
||||
// check for Basic theme
|
||||
DWORD color;
|
||||
BOOL opaque;
|
||||
if (SUCCEEDED(DwmGetColorizationColor(&color,&opaque)) && opaque)
|
||||
bComposition=FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
UpdateSetting(L"Glow",CComVariant(bComposition?1:0),false);
|
||||
UpdateSetting(L"MaxGlow",CComVariant(bComposition?1:0),false);
|
||||
UpdateSetting(L"CenterCaption",CComVariant((bWin8 && GetWinVersion()<WIN_VER_WIN10)?1:0),false);
|
||||
|
||||
// create a dummy window to get a theme
|
||||
HWND hwnd=CreateWindow(L"#32770",L"",WS_OVERLAPPEDWINDOW,0,0,0,0,NULL,NULL,NULL,0);
|
||||
HTHEME theme=OpenThemeData(hwnd,L"Window");
|
||||
if (theme)
|
||||
{
|
||||
HDC hdc=GetDC(NULL);
|
||||
int dpi=GetDeviceCaps(hdc,LOGPIXELSY);
|
||||
ReleaseDC(NULL,hdc);
|
||||
|
||||
LOGFONT font;
|
||||
GetThemeSysFont(theme,TMT_CAPTIONFONT,&font);
|
||||
wchar_t text[256];
|
||||
const wchar_t *type=font.lfItalic?L"italic":L"normal";
|
||||
if (font.lfWeight>=FW_BOLD)
|
||||
type=font.lfItalic?L"bold_italic":L"bold";
|
||||
Sprintf(text,_countof(text),L"%s, %s, %d",font.lfFaceName,type,(-font.lfHeight*72+dpi/2)/dpi);
|
||||
UpdateSetting(L"CaptionFont",CComVariant(text),false);
|
||||
|
||||
int color=GetThemeSysColor(theme,COLOR_CAPTIONTEXT);
|
||||
UpdateSetting(L"TextColor",CComVariant(color),false);
|
||||
UpdateSetting(L"MaxColor",CComVariant(color),false);
|
||||
if (bWin8)
|
||||
color=GetThemeSysColor(theme,COLOR_INACTIVECAPTIONTEXT);
|
||||
UpdateSetting(L"InactiveColor",CComVariant(color),false);
|
||||
UpdateSetting(L"InactiveMaxColor",CComVariant(color),false);
|
||||
|
||||
CloseThemeData(theme);
|
||||
}
|
||||
else
|
||||
{
|
||||
int color=GetSysColor(COLOR_CAPTIONTEXT);
|
||||
UpdateSetting(L"TextColor",CComVariant(color),false);
|
||||
UpdateSetting(L"MaxColor",CComVariant(color),false);
|
||||
color=GetSysColor(COLOR_INACTIVECAPTIONTEXT);
|
||||
UpdateSetting(L"InactiveColor",CComVariant(color),false);
|
||||
UpdateSetting(L"InactiveMaxColor",CComVariant(color),false);
|
||||
}
|
||||
DestroyWindow(hwnd);
|
||||
|
||||
CRegKey regKey;
|
||||
wchar_t language[100]=L"";
|
||||
if (regKey.Open(HKEY_LOCAL_MACHINE,L"Software\\OpenShell\\OpenShell",KEY_READ|KEY_WOW64_64KEY)==ERROR_SUCCESS)
|
||||
{
|
||||
ULONG size=_countof(language);
|
||||
if (regKey.QueryStringValue(L"DefaultLanguage",language,&size)!=ERROR_SUCCESS)
|
||||
language[0]=0;
|
||||
}
|
||||
UpdateSetting(L"Language",language,false);
|
||||
}
|
||||
|
||||
void InitSettings( void )
|
||||
{
|
||||
InitSettings(g_Settings,COMPONENT_IE,NULL);
|
||||
}
|
||||
|
||||
void ClosingSettings( HWND hWnd, int flags, int command )
|
||||
{
|
||||
if (command==IDOK)
|
||||
{
|
||||
if (flags&CSetting::FLAG_WARM)
|
||||
{
|
||||
if (FindWindow(L"IEFrame",NULL))
|
||||
MessageBox(hWnd,LoadStringEx(IDS_NEW_SETTINGS),LoadStringEx(IDS_APP_TITLE),MB_OK|MB_ICONINFORMATION);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void SettingChangedCallback( const CSetting *pSetting )
|
||||
{
|
||||
}
|
||||
|
||||
CSIEAPI void ShowIESettings( void )
|
||||
{
|
||||
if (!GetSettingBool(L"EnableSettings"))
|
||||
return;
|
||||
wchar_t title[100];
|
||||
DWORD ver=GetVersionEx(g_Instance);
|
||||
if (ver)
|
||||
Sprintf(title,_countof(title),LoadStringEx(IDS_SETTINGS_TITLE_VER),ver>>24,(ver>>16)&0xFF,ver&0xFFFF);
|
||||
else
|
||||
Sprintf(title,_countof(title),LoadStringEx(IDS_SETTINGS_TITLE));
|
||||
EditSettings(title,true,0);
|
||||
}
|
||||
|
||||
CSIEAPI DWORD GetIESettings( void )
|
||||
{
|
||||
DWORD res=0;
|
||||
if (GetSettingBool(L"ShowCaption")) res|=IE_SETTING_CAPTION;
|
||||
if (GetSettingBool(L"ShowProgress")) res|=IE_SETTING_PROGRESS;
|
||||
if (GetSettingBool(L"ShowZone")) res|=IE_SETTING_ZONE;
|
||||
if (GetSettingBool(L"ShowProtected")) res|=IE_SETTING_PROTECTED;
|
||||
return res;
|
||||
}
|
||||
7
Src/ClassicIE/ClassicIEDLL/SettingsUI.h
Normal file
@@ -0,0 +1,7 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
void InitSettings( void );
|
||||
156
Src/ClassicIE/ClassicIEDLL/dllmain.cpp
Normal file
@@ -0,0 +1,156 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "resource.h"
|
||||
#include "..\..\Lib\resource.h"
|
||||
#include "Settings.h"
|
||||
#include "SettingsUI.h"
|
||||
#include "SettingsUIHelper.h"
|
||||
#include "DownloadHelper.h"
|
||||
#include "Translations.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "dllmain.h"
|
||||
#include "ClassicIEDLL.h"
|
||||
|
||||
#pragma comment(linker, \
|
||||
"\"/manifestdependency:type='Win32' "\
|
||||
"name='Microsoft.Windows.Common-Controls' "\
|
||||
"version='6.0.0.0' "\
|
||||
"processorArchitecture='*' "\
|
||||
"publicKeyToken='6595b64144ccf1df' "\
|
||||
"language='*'\"")
|
||||
|
||||
CClassicIEDLLModule _AtlModule;
|
||||
|
||||
static int g_LoadDialogs[]=
|
||||
{
|
||||
IDD_SETTINGS,0x04000000,
|
||||
IDD_SETTINGSTREE,0x04000000,
|
||||
IDD_LANGUAGE,0x04000000,
|
||||
IDD_PROGRESS,0x04000004,
|
||||
0
|
||||
};
|
||||
|
||||
static void NewVersionCallback( VersionData &data )
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(g_Instance,path,_countof(path));
|
||||
PathRemoveFileSpec(path);
|
||||
PathAppend(path,L"Update.exe");
|
||||
wchar_t cmdLine[1024];
|
||||
Sprintf(cmdLine,_countof(cmdLine),L"\"%s\" -popup",path);
|
||||
STARTUPINFO startupInfo={sizeof(startupInfo)};
|
||||
PROCESS_INFORMATION processInfo;
|
||||
memset(&processInfo,0,sizeof(processInfo));
|
||||
if (CreateProcess(path,cmdLine,NULL,NULL,TRUE,0,NULL,NULL,&startupInfo,&processInfo))
|
||||
{
|
||||
CloseHandle(processInfo.hThread);
|
||||
CloseHandle(processInfo.hProcess);
|
||||
}
|
||||
}
|
||||
|
||||
CSIEAPI void CheckForNewVersionIE( void )
|
||||
{
|
||||
CheckForNewVersion(NULL,COMPONENT_IE,CHECK_AUTO_WAIT,NewVersionCallback);
|
||||
}
|
||||
|
||||
static HANDLE g_DllInitThread;
|
||||
|
||||
static DWORD CALLBACK DllInitThread( void* )
|
||||
{
|
||||
InitSettings();
|
||||
CString language=GetSettingString(L"Language");
|
||||
ParseTranslations(NULL,language);
|
||||
|
||||
HINSTANCE resInstance=LoadTranslationDll(language);
|
||||
|
||||
LoadTranslationResources(resInstance,g_LoadDialogs);
|
||||
|
||||
if (resInstance)
|
||||
FreeLibrary(resInstance);
|
||||
InitClassicIE(g_Instance);
|
||||
return 0;
|
||||
}
|
||||
|
||||
CSIEAPI void WaitDllInitThread( void )
|
||||
{
|
||||
ATLASSERT(g_DllInitThread);
|
||||
WaitForSingleObject(g_DllInitThread,INFINITE);
|
||||
}
|
||||
|
||||
CSIEAPI void DllLogToFile( const wchar_t *location, const wchar_t *message, ... )
|
||||
{
|
||||
va_list args;
|
||||
va_start(args,message);
|
||||
VLogToFile(location,message,args);
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
#ifndef _WIN64
|
||||
CSIEAPI bool DllSaveAdmx( const char *admxFile, const char *admlFile, const char *docFile, const wchar_t *language )
|
||||
{
|
||||
WaitDllInitThread();
|
||||
HMODULE dll=NULL;
|
||||
if (language[0])
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetCurrentDirectory(_countof(path),path);
|
||||
PathAppend(path,language);
|
||||
PathAddExtension(path,L".dll");
|
||||
dll=LoadLibraryEx(path,NULL,LOAD_LIBRARY_AS_DATAFILE|LOAD_LIBRARY_AS_IMAGE_RESOURCE);
|
||||
}
|
||||
LoadTranslationResources(dll,NULL);
|
||||
return SaveAdmx(COMPONENT_IE,admxFile,admlFile,docFile);
|
||||
}
|
||||
#endif
|
||||
|
||||
CSIEAPI bool DllImportSettingsXml( const wchar_t *fname )
|
||||
{
|
||||
return ImportSettingsXml(fname);
|
||||
}
|
||||
|
||||
CSIEAPI bool DllExportSettingsXml( const wchar_t *fname )
|
||||
{
|
||||
return ExportSettingsXml(fname);
|
||||
}
|
||||
|
||||
// DLL Entry Point
|
||||
extern "C" BOOL WINAPI DllMain( HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved )
|
||||
{
|
||||
if (dwReason==DLL_PROCESS_ATTACH)
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
GetModuleFileName(NULL,path,_countof(path));
|
||||
const wchar_t *exe=PathFindFileName(path);
|
||||
if (_wcsicmp(exe,L"explorer.exe")==0) return FALSE;
|
||||
if (_wcsicmp(exe,L"iexplore.exe")==0)
|
||||
{
|
||||
DWORD version=GetVersionEx(GetModuleHandle(NULL));
|
||||
if (version<0x09000000) return FALSE;
|
||||
|
||||
CRegKey regSettings, regSettingsUser, regPolicy, regPolicyUser;
|
||||
bool bUpgrade=OpenSettingsKeys(COMPONENT_EXPLORER,regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
|
||||
CSetting settings[]={
|
||||
{L"ShowCaption",CSetting::TYPE_BOOL,0,0,1},
|
||||
{L"ShowProgress",CSetting::TYPE_BOOL,0,0,1},
|
||||
{L"ShowZone",CSetting::TYPE_BOOL,0,0,1},
|
||||
{NULL}
|
||||
};
|
||||
|
||||
settings[0].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
settings[1].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
settings[2].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
|
||||
if (!GetSettingBool(settings[0]) && !GetSettingBool(settings[1]) && !GetSettingBool(settings[2])) return FALSE;
|
||||
}
|
||||
|
||||
g_Instance=hInstance;
|
||||
|
||||
g_DllInitThread=CreateThread(NULL,0,DllInitThread,NULL,0,NULL);
|
||||
}
|
||||
|
||||
return _AtlModule.DllMain(dwReason, lpReserved);
|
||||
}
|
||||
16
Src/ClassicIE/ClassicIEDLL/dllmain.h
Normal file
@@ -0,0 +1,16 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "ClassicIEDLL_h.h"
|
||||
|
||||
class CClassicIEDLLModule : public CAtlDllModuleT< CClassicIEDLLModule >
|
||||
{
|
||||
public :
|
||||
DECLARE_LIBID(LIBID_ClassicIEDLLLib)
|
||||
DECLARE_REGISTRY_APPID_RESOURCEID(IDR_CLASSICIEDLL, "{DF3255F4-FF55-44FA-A728-E77B83E9E403}")
|
||||
};
|
||||
|
||||
extern class CClassicIEDLLModule _AtlModule;
|
||||
BIN
Src/ClassicIE/ClassicIEDLL/glow.bmp
Normal file
|
After Width: | Height: | Size: 2.3 KiB |
57
Src/ClassicIE/ClassicIEDLL/resource.h
Normal file
@@ -0,0 +1,57 @@
|
||||
//{{NO_DEPENDENCIES}}
|
||||
// Microsoft Visual C++ generated include file.
|
||||
// Used by ClassicIEDLL.rc
|
||||
//
|
||||
#define IDI_APPICON 1
|
||||
#define IDR_CLASSICIEDLL 101
|
||||
#define IDR_CLASSICIEBHO 102
|
||||
#define IDB_BITMAP1 201
|
||||
#define IDB_GLOW 201
|
||||
#define IDS_APP_TITLE 5000
|
||||
#define IDS_SETTINGS_TITLE 5001
|
||||
#define IDS_SETTINGS_TITLE_VER 5002
|
||||
#define IDS_NEW_SETTINGS 5003
|
||||
#define IDS_TITLE_SETTINGS 5004
|
||||
#define IDS_SHOW_CAPTION 5005
|
||||
#define IDS_SHOW_CAPTION_TIP 5006
|
||||
#define IDS_CENTER_CAPTION 5007
|
||||
#define IDS_CENTER_CAPTION_TIP 5008
|
||||
#define IDS_LANGUAGE_SETTINGS 5009
|
||||
#define IDS_CAPTION_FONT 5010
|
||||
#define IDS_CAPTION_FONT_TIP 5011
|
||||
#define IDS_TEXT_COLOR 5012
|
||||
#define IDS_TEXT_COLOR_TIP 5013
|
||||
#define IDS_MAXTEXT_COLOR 5014
|
||||
#define IDS_MAXTEXT_COLOR_TIP 5015
|
||||
#define IDS_INTEXT_COLOR 5016
|
||||
#define IDS_INTEXT_COLOR_TIP 5017
|
||||
#define IDS_MAXINTEXT_COLOR 5018
|
||||
#define IDS_MAXINTEXT_COLOR_TIP 5019
|
||||
#define IDS_GLOW 5020
|
||||
#define IDS_GLOW_TIP 5021
|
||||
#define IDS_GLOW_COLOR 5022
|
||||
#define IDS_GLOW_COLOR_TIP 5023
|
||||
#define IDS_MAXGLOW 5024
|
||||
#define IDS_MAXGLOW_TIP 5025
|
||||
#define IDS_MAXGLOW_COLOR 5026
|
||||
#define IDS_MAXGLOW_COLOR_TIP 5027
|
||||
#define IDS_STATUS_SETTINGS 5028
|
||||
#define IDS_SHOW_PROGRESS 5029
|
||||
#define IDS_SHOW_PROGRESS_TIP 5030
|
||||
#define IDS_SHOW_ZONE 5031
|
||||
#define IDS_SHOW_ZONE_TIP 5032
|
||||
#define IDS_SHOW_PROTECTED 5033
|
||||
#define IDS_SHOW_PROTECTED_TIP 5034
|
||||
#define IDS_SHOW_ICON 5035
|
||||
#define IDS_SHOW_ICON_TIP 5036
|
||||
|
||||
// Next default values for new objects
|
||||
//
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
#ifndef APSTUDIO_READONLY_SYMBOLS
|
||||
#define _APS_NEXT_RESOURCE_VALUE 202
|
||||
#define _APS_NEXT_COMMAND_VALUE 32768
|
||||
#define _APS_NEXT_CONTROL_VALUE 201
|
||||
#define _APS_NEXT_SYMED_VALUE 103
|
||||
#endif
|
||||
#endif
|
||||
5
Src/ClassicIE/ClassicIEDLL/stdafx.cpp
Normal file
@@ -0,0 +1,5 @@
|
||||
// stdafx.cpp : source file that includes just the standard includes
|
||||
// ClassicIEDLL.pch will be the pre-compiled header
|
||||
// stdafx.obj will contain the pre-compiled type information
|
||||
|
||||
#include "stdafx.h"
|
||||
27
Src/ClassicIE/ClassicIEDLL/stdafx.h
Normal file
@@ -0,0 +1,27 @@
|
||||
// stdafx.h : include file for standard system include files,
|
||||
// or project specific include files that are used frequently,
|
||||
// but are changed infrequently
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifndef STRICT
|
||||
#define STRICT
|
||||
#endif
|
||||
|
||||
#include "targetver.h"
|
||||
|
||||
#define ISOLATION_AWARE_ENABLED 1
|
||||
#define _ATL_APARTMENT_THREADED
|
||||
#define _ATL_NO_AUTOMATIC_NAMESPACE
|
||||
#define _ATL_MODULES // compatibility with /permissive-
|
||||
#define _ATL_CSTRING_EXPLICIT_CONSTRUCTORS // some CString constructors will be explicit
|
||||
|
||||
#include "resource.h"
|
||||
#include <atlbase.h>
|
||||
#include <atlcom.h>
|
||||
#include <atlctl.h>
|
||||
#include <atlstr.h>
|
||||
|
||||
using namespace ATL;
|
||||
|
||||
#include "StringUtils.h"
|
||||
24
Src/ClassicIE/ClassicIEDLL/targetver.h
Normal file
@@ -0,0 +1,24 @@
|
||||
#pragma once
|
||||
|
||||
// The following macros define the minimum required platform. The minimum required platform
|
||||
// is the earliest version of Windows, Internet Explorer etc. that has the necessary features to run
|
||||
// your application. The macros work by enabling all features available on platform versions up to and
|
||||
// including the version specified.
|
||||
|
||||
// Modify the following defines if you have to target a platform prior to the ones specified below.
|
||||
// Refer to MSDN for the latest info on corresponding values for different platforms.
|
||||
#ifndef WINVER // Specifies that the minimum required platform is Windows 7.
|
||||
#define WINVER 0x0602 // Change this to the appropriate value to target other versions of Windows.
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32_WINNT // Specifies that the minimum required platform is Windows 7.
|
||||
#define _WIN32_WINNT 0x0602 // Change this to the appropriate value to target other versions of Windows.
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32_WINDOWS // Specifies that the minimum required platform is Windows 98.
|
||||
#define _WIN32_WINDOWS 0x0410 // Change this to the appropriate value to target Windows Me or later.
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32_IE // Specifies that the minimum required platform is Internet Explorer 7.0.
|
||||
#define _WIN32_IE 0x0700 // Change this to the appropriate value to target other versions of IE.
|
||||
#endif
|
||||
21
Src/ClassicIE/Resource.h
Normal file
@@ -0,0 +1,21 @@
|
||||
//{{NO_DEPENDENCIES}}
|
||||
// Microsoft Visual C++ generated include file.
|
||||
// Used by ClassicIE.rc
|
||||
//
|
||||
#define IDC_MYICON 2
|
||||
#define IDD_CLASSICIE_DIALOG 102
|
||||
#define IDR_MAINFRAME 128
|
||||
#define IDI_ICON1 129
|
||||
#define IDC_STATIC -1
|
||||
|
||||
// Next default values for new objects
|
||||
//
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
#ifndef APSTUDIO_READONLY_SYMBOLS
|
||||
#define _APS_NO_MFC 1
|
||||
#define _APS_NEXT_RESOURCE_VALUE 130
|
||||
#define _APS_NEXT_COMMAND_VALUE 32771
|
||||
#define _APS_NEXT_CONTROL_VALUE 1000
|
||||
#define _APS_NEXT_SYMED_VALUE 110
|
||||
#endif
|
||||
#endif
|
||||
91
Src/Common.props
Normal file
@@ -0,0 +1,91 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ImportGroup Label="PropertySheets" />
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup>
|
||||
<!-- Default product version to use if CS_VERSION environment variable is not defined -->
|
||||
<CS_VERSION Condition="'$(CS_VERSION)'==''">4.4.1000</CS_VERSION>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- Output paths -->
|
||||
<PropertyGroup Condition="'$(Platform)'=='Win32'">
|
||||
<OutDir>$(MSBuildThisFileDirectory)..\build\bin\$(Configuration)\</OutDir>
|
||||
<IntDir>$(MSBuildThisFileDirectory)..\build\obj\$(ProjectName)\$(Configuration)\</IntDir>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Platform)'=='x64'">
|
||||
<OutDir>$(MSBuildThisFileDirectory)..\build\bin\$(Configuration)64\</OutDir>
|
||||
<IntDir>$(MSBuildThisFileDirectory)..\build\obj\$(ProjectName)\$(Configuration)64\</IntDir>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- Common settings for all configurations -->
|
||||
<ItemDefinitionGroup>
|
||||
<ClCompile>
|
||||
<AdditionalIncludeDirectories Condition="'$(ConfigurationType)'!='StaticLibrary'">$(MSBuildThisFileDirectory)Lib;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<PreprocessorDefinitions>WIN32;_WINDOWS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<PrecompiledHeader>Use</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<LanguageStandard>stdcpp17</LanguageStandard>
|
||||
</ClCompile>
|
||||
<Midl>
|
||||
<MkTypLibCompatible>false</MkTypLibCompatible>
|
||||
<GenerateStublessProxies>true</GenerateStublessProxies>
|
||||
<ValidateAllParameters>true</ValidateAllParameters>
|
||||
</Midl>
|
||||
<Link>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
</Link>
|
||||
<ResourceCompile>
|
||||
<AdditionalIncludeDirectories>$(MSBuildThisFileDirectory)Lib;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<PreprocessorDefinitions>_PRODUCT_VERSION=$(CS_VERSION.Replace('.', ',')),0;_PRODUCT_VERSION_STR=\"$(CS_VERSION_ORIG)\";%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ResourceCompile>
|
||||
</ItemDefinitionGroup>
|
||||
|
||||
<!-- Debug settings -->
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)'=='Debug'">
|
||||
<ClCompile>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<PreprocessorDefinitions>_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
|
||||
<RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
|
||||
<DebugInformationFormat>EditAndContinue</DebugInformationFormat>
|
||||
</ClCompile>
|
||||
<Midl>
|
||||
<PreprocessorDefinitions>_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</Midl>
|
||||
<ResourceCompile>
|
||||
<PreprocessorDefinitions>_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ResourceCompile>
|
||||
</ItemDefinitionGroup>
|
||||
|
||||
<!-- Non-Debug settings -->
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)'!='Debug'">
|
||||
<ClCompile>
|
||||
<Optimization>MaxSpeed</Optimization>
|
||||
<PreprocessorDefinitions>NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
</ClCompile>
|
||||
<Midl>
|
||||
<PreprocessorDefinitions>NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</Midl>
|
||||
<ResourceCompile>
|
||||
<PreprocessorDefinitions>NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ResourceCompile>
|
||||
<Link>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)'=='Setup'">
|
||||
<ClCompile>
|
||||
<PreprocessorDefinitions>BUILD_SETUP;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ClCompile>
|
||||
</ItemDefinitionGroup>
|
||||
|
||||
<ItemGroup />
|
||||
</Project>
|
||||
43
Src/LICENSE.txt
Normal file
@@ -0,0 +1,43 @@
|
||||
=============================================================================
|
||||
License for the Open-Shell Source Code (MIT license)
|
||||
|
||||
Copyright (c) 2009-2017, Ivo Beltchev http://www.classicshell.net/
|
||||
Copyright (C) 2017-2018, The Open-Shell Team https://github.com/open-shell
|
||||
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
|
||||
=============================================================================
|
||||
License for the Open-Shell source assets
|
||||
|
||||
Copyright (c) 2009-2013, Ivo Beltchev http://www.classicshell.net/
|
||||
Copyright (C) 2017-2018, The Open-Shell Team https://github.com/open-shell
|
||||
|
||||
Assets like bitmaps, icons, skins, HTML documentation are copyrighted works.
|
||||
Using them in a commercial project is not allowed without the author's written
|
||||
consent. Email classicshell@ibeltchev.com for details.
|
||||
|
||||
You are allowed to use the assets in free projects. This exception is granted
|
||||
to allow people to create and distribute free modifications of the Classic
|
||||
Shell software, and to create custom builds for personal or internal use.
|
||||
|
||||
NOTE: The Open-Shell brand and the Open-Shell logo are trademarks and
|
||||
cannot be used in any public project, or to identify other products and
|
||||
services.
|
||||
29
Src/Lib/Assert.cpp
Normal file
@@ -0,0 +1,29 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include <stdafx.h>
|
||||
#include "StringUtils.h"
|
||||
|
||||
static DWORD _stdcall AssertThreadProc( void *param )
|
||||
{
|
||||
return MessageBoxA(NULL,(const char *)param,"Assertion Failed",MB_ABORTRETRYIGNORE|MB_TASKMODAL|MB_ICONERROR);
|
||||
}
|
||||
|
||||
// debug assert
|
||||
bool dbg_assert( const char *exp, const char *file, unsigned line )
|
||||
{
|
||||
char buf[2048];
|
||||
Sprintf(buf,_countof(buf),"Expression: %s\r\nFile: %s\r\nLine: %d\n",exp,file,line);
|
||||
HANDLE h=CreateThread(NULL,0,AssertThreadProc,buf,0,NULL);
|
||||
if (h)
|
||||
{
|
||||
WaitForSingleObject(h,INFINITE);
|
||||
DWORD res=IDRETRY;
|
||||
GetExitCodeThread(h,&res);
|
||||
if (res==IDABORT)
|
||||
TerminateProcess(GetCurrentProcess(),1);
|
||||
return (res==IDIGNORE); // true will continue, false will cause _CrtDbgBreak
|
||||
}
|
||||
return true;
|
||||
}
|
||||
16
Src/Lib/Assert.h
Normal file
@@ -0,0 +1,16 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifdef _DEBUG
|
||||
|
||||
bool dbg_assert( const char *exp, const char *file, unsigned line );
|
||||
#define Assert(exp) do { if (!(exp) && !dbg_assert(#exp,__FILE__,__LINE__)) _CrtDbgBreak(); } while (0)
|
||||
|
||||
#else
|
||||
|
||||
#define Assert(exp) ((void)0)
|
||||
|
||||
#endif
|
||||
46
Src/Lib/ComHelper.h
Normal file
@@ -0,0 +1,46 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <shlobj.h>
|
||||
#include "Assert.h"
|
||||
|
||||
class CAbsolutePidl
|
||||
{
|
||||
public:
|
||||
CAbsolutePidl( void ) { m_Pidl=NULL; }
|
||||
CAbsolutePidl( const CAbsolutePidl &pidl ) { m_Pidl=pidl?ILCloneFull(pidl):NULL; }
|
||||
~CAbsolutePidl( void ) { Clear(); }
|
||||
void operator=( const CAbsolutePidl &pidl ) { Clone(pidl); }
|
||||
void operator=( PCIDLIST_ABSOLUTE pidl ) { Clone(pidl); }
|
||||
|
||||
void Clear( void ) { if (m_Pidl) ILFree(m_Pidl); m_Pidl=NULL; }
|
||||
operator PIDLIST_ABSOLUTE( void ) const { return m_Pidl; }
|
||||
PIDLIST_ABSOLUTE* operator&( void ) { Assert(m_Pidl==NULL); return &m_Pidl; }
|
||||
void Swap( CAbsolutePidl &pidl ) { PIDLIST_ABSOLUTE q=pidl.m_Pidl; pidl.m_Pidl=m_Pidl; m_Pidl=q; }
|
||||
void Attach( PIDLIST_ABSOLUTE pidl ) { Clear(); m_Pidl=pidl; }
|
||||
PIDLIST_ABSOLUTE Detach( void ) { PIDLIST_ABSOLUTE pidl=m_Pidl; m_Pidl=NULL; return pidl; }
|
||||
void Clone( PCIDLIST_ABSOLUTE pidl ) { Clear(); m_Pidl=pidl?ILCloneFull(pidl):NULL; }
|
||||
|
||||
private:
|
||||
PIDLIST_ABSOLUTE m_Pidl;
|
||||
};
|
||||
|
||||
class CComString
|
||||
{
|
||||
public:
|
||||
CComString( void ) { m_String=NULL; }
|
||||
~CComString( void ) { Clear(); }
|
||||
|
||||
void Clear( void ) { if (m_String) CoTaskMemFree(m_String); m_String=NULL; }
|
||||
operator const wchar_t*( void ) const { return m_String; }
|
||||
wchar_t** operator&( void ) { Assert(m_String==NULL); return &m_String; }
|
||||
void MakeUpper( void ) { if (m_String) CharUpper(m_String); }
|
||||
|
||||
private:
|
||||
CComString( const CComString &str );
|
||||
void operator=( const CComString &str );
|
||||
wchar_t *m_String;
|
||||
};
|
||||
913
Src/Lib/DownloadHelper.cpp
Normal file
@@ -0,0 +1,913 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include <stdafx.h>
|
||||
#include "resource.h"
|
||||
#include "DownloadHelper.h"
|
||||
#include "Settings.h"
|
||||
#include "SettingsUIHelper.h"
|
||||
#include "LanguageSettingsHelper.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "ComHelper.h"
|
||||
#include "FNVHash.h"
|
||||
#include "StringUtils.h"
|
||||
#include "Translations.h"
|
||||
#include <nlohmann/json.hpp>
|
||||
#include <wininet.h>
|
||||
#include <softpub.h>
|
||||
|
||||
//#define UPDATE_LOG L"-|%LOCALAPPDATA%\\OpenShell\\UpdateLog.txt"
|
||||
|
||||
const __int64 TIME_DIVISOR=360000000; // divisor for FILETIME to get 0.01 hour precision
|
||||
const int TIME_PRECISION=100; // 0.01 hour precision
|
||||
|
||||
class CProgressDlg: public CResizeableDlg<CProgressDlg>
|
||||
{
|
||||
public:
|
||||
CProgressDlg( void );
|
||||
BEGIN_MSG_MAP( CProgressDlg )
|
||||
MESSAGE_HANDLER( WM_INITDIALOG, OnInitDialog )
|
||||
MESSAGE_HANDLER( WM_CLEAR, OnClear )
|
||||
COMMAND_HANDLER( IDCANCEL, BN_CLICKED, OnCancel )
|
||||
END_MSG_MAP()
|
||||
|
||||
BEGIN_RESIZE_MAP
|
||||
END_RESIZE_MAP
|
||||
|
||||
void Create( HWND owner, const wchar_t *title );
|
||||
void SetText( const wchar_t *text ); // may block if messages are not processed
|
||||
void SetProgress( int progress ); // -1 for undefined
|
||||
void EnableCancel( bool bEnabled );
|
||||
bool IsCanceled( void ) const { return m_bCanceled; }
|
||||
|
||||
protected:
|
||||
// Handler prototypes:
|
||||
// LRESULT MessageHandler(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled);
|
||||
// LRESULT CommandHandler(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled);
|
||||
// LRESULT NotifyHandler(int idCtrl, LPNMHDR pnmh, BOOL& bHandled);
|
||||
LRESULT OnInitDialog( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnClear( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnCancel( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled );
|
||||
|
||||
private:
|
||||
bool m_bCanceled;
|
||||
bool m_bMarquee;
|
||||
CWindow m_Progress;
|
||||
|
||||
enum
|
||||
{
|
||||
COMMAND_SET_PROGRESS,
|
||||
COMMAND_ENABLE_CANCEL,
|
||||
};
|
||||
};
|
||||
|
||||
CProgressDlg::CProgressDlg( void )
|
||||
{
|
||||
m_bCanceled=m_bMarquee=false;
|
||||
}
|
||||
|
||||
LRESULT CProgressDlg::OnInitDialog( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled )
|
||||
{
|
||||
InitResize(MOVE_HORIZONTAL|MOVE_VERTICAL);
|
||||
m_Progress=GetDlgItem(IDC_PROGRESS);
|
||||
m_Progress.SendMessage(PBM_SETRANGE,0,MAKELPARAM(0,100));
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
void CProgressDlg::Create( HWND owner, const wchar_t *title )
|
||||
{
|
||||
DLGTEMPLATE *pTemplate=LoadDialogEx(IDD_PROGRESS);
|
||||
CResizeableDlg<CProgressDlg>::Create(owner,pTemplate);
|
||||
SetWindowText(title);
|
||||
ShowWindow(SW_SHOW);
|
||||
SetDlgItemText(IDC_MESSAGE,L"");
|
||||
}
|
||||
|
||||
void CProgressDlg::SetText( const wchar_t *text )
|
||||
{
|
||||
SetDlgItemText(IDC_MESSAGE,text);
|
||||
}
|
||||
|
||||
void CProgressDlg::SetProgress( int progress )
|
||||
{
|
||||
PostMessage(WM_CLEAR,COMMAND_SET_PROGRESS,progress);
|
||||
}
|
||||
|
||||
void CProgressDlg::EnableCancel( bool bEnabled )
|
||||
{
|
||||
PostMessage(WM_CLEAR,COMMAND_ENABLE_CANCEL,bEnabled?1:0);
|
||||
}
|
||||
|
||||
LRESULT CProgressDlg::OnClear( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled )
|
||||
{
|
||||
if (wParam==COMMAND_SET_PROGRESS)
|
||||
{
|
||||
int progress=(int)lParam;
|
||||
if (progress>=0)
|
||||
{
|
||||
if (m_bMarquee)
|
||||
{
|
||||
m_Progress.SendMessage(PBM_SETMARQUEE,FALSE);
|
||||
m_bMarquee=false;
|
||||
}
|
||||
m_Progress.SendMessage(PBM_SETPOS,progress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!m_bMarquee)
|
||||
{
|
||||
m_Progress.SendMessage(PBM_SETMARQUEE,TRUE,50);
|
||||
m_Progress.SetWindowLong(GWL_STYLE,m_Progress.GetWindowLong(GWL_STYLE)|PBS_MARQUEE);
|
||||
m_bMarquee=true;
|
||||
}
|
||||
m_Progress.SendMessage(PBM_STEPIT);
|
||||
}
|
||||
}
|
||||
else if (wParam==COMMAND_ENABLE_CANCEL)
|
||||
{
|
||||
GetDlgItem(IDCANCEL).EnableWindow(lParam!=0);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CProgressDlg::OnCancel( WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled )
|
||||
{
|
||||
m_bCanceled=true;
|
||||
return 0;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static bool g_bCheckingVersion;
|
||||
|
||||
enum TDownloadResult
|
||||
{
|
||||
DOWNLOAD_OK,
|
||||
DOWNLOAD_CANCEL,
|
||||
|
||||
// errors
|
||||
DOWNLOAD_FIRST_ERROR,
|
||||
DOWNLOAD_INTERNET=DOWNLOAD_FIRST_ERROR,
|
||||
DOWNLOAD_START,
|
||||
DOWNLOAD_FAIL,
|
||||
};
|
||||
|
||||
// Downloads a file
|
||||
// filename - returns the name of the downloaded file
|
||||
static TDownloadResult DownloadFile( const wchar_t *url, std::vector<char> &buf, CString *pFilename, bool bAcceptCached, CProgressDlg *pProgress, TSettingsComponent component )
|
||||
{
|
||||
const wchar_t *compName=L"Open-Shell";
|
||||
switch (component)
|
||||
{
|
||||
case COMPONENT_EXPLORER: compName=L"Classic Explorer"; break;
|
||||
case COMPONENT_MENU: compName=L"Open-Shell Menu"; break;
|
||||
case COMPONENT_IE: compName=L"Classic IE"; break;
|
||||
case COMPONENT_UPDATE: compName=L"Open-Shell Update"; break;
|
||||
}
|
||||
|
||||
DWORD compVersion=GetVersionEx(g_Instance);
|
||||
|
||||
wchar_t agent[100];
|
||||
Sprintf(agent,_countof(agent),L"%s %d.%d.%d (Win %x)",compName,compVersion>>24,(compVersion>>16)&0xFF,compVersion&0xFFFF,GetWinVersion());
|
||||
|
||||
TDownloadResult res=DOWNLOAD_OK;
|
||||
HINTERNET hInternet=InternetOpen(agent,INTERNET_OPEN_TYPE_PRECONFIG,NULL,NULL,0);
|
||||
if (!hInternet)
|
||||
return DOWNLOAD_INTERNET;
|
||||
if (pProgress && pProgress->IsCanceled())
|
||||
res=DOWNLOAD_CANCEL;
|
||||
|
||||
wchar_t host[256];
|
||||
wchar_t file[256];
|
||||
URL_COMPONENTS components={sizeof(components)};
|
||||
components.lpszHostName=host;
|
||||
components.dwHostNameLength=_countof(host);
|
||||
components.lpszUrlPath=file;
|
||||
components.dwUrlPathLength=_countof(file);
|
||||
InternetCrackUrl(url,0,0,&components);
|
||||
int time=GetTickCount();
|
||||
if (pProgress)
|
||||
pProgress->SetText(LoadStringEx(IDS_PROGRESS_CONNECT));
|
||||
HINTERNET hConnect=InternetConnect(hInternet,host,components.nPort,L"",L"",INTERNET_SERVICE_HTTP,0,0);
|
||||
if (hConnect)
|
||||
{
|
||||
if (pProgress && pProgress->IsCanceled())
|
||||
res=DOWNLOAD_CANCEL;
|
||||
|
||||
if (res==DOWNLOAD_OK)
|
||||
{
|
||||
const wchar_t* accept[] = { L"*/*",NULL };
|
||||
HINTERNET hRequest=HttpOpenRequest(hConnect,L"GET",file,NULL,NULL,accept,((components.nScheme==INTERNET_SCHEME_HTTPS)?INTERNET_FLAG_SECURE:0)|(bAcceptCached?0:INTERNET_FLAG_RELOAD),0);
|
||||
if (hRequest)
|
||||
{
|
||||
if (pProgress && pProgress->IsCanceled())
|
||||
res=DOWNLOAD_CANCEL;
|
||||
// get size (may be missing)
|
||||
DWORD fileSize;
|
||||
if (res==DOWNLOAD_OK)
|
||||
{
|
||||
if (HttpSendRequest(hRequest,NULL,0,NULL,0))
|
||||
{
|
||||
DWORD len=sizeof(fileSize);
|
||||
DWORD index=0;
|
||||
if (!HttpQueryInfo(hRequest,HTTP_QUERY_CONTENT_LENGTH|HTTP_QUERY_FLAG_NUMBER,&fileSize,&len,&index))
|
||||
fileSize=0;
|
||||
}
|
||||
else
|
||||
res=DOWNLOAD_START;
|
||||
}
|
||||
|
||||
// get file name (must be after HttpSendRequest to resolve any redirections)
|
||||
if (res==DOWNLOAD_OK && pFilename)
|
||||
{
|
||||
wchar_t buf[1024];
|
||||
DWORD len=sizeof(buf);
|
||||
if (InternetQueryOption(hRequest,INTERNET_OPTION_URL,buf,&len))
|
||||
{
|
||||
const wchar_t *name=wcsrchr(buf,'/');
|
||||
if (name && name[1])
|
||||
*pFilename=name+1;
|
||||
else
|
||||
res=DOWNLOAD_START;
|
||||
}
|
||||
else
|
||||
res=DOWNLOAD_START;
|
||||
}
|
||||
|
||||
if (res==DOWNLOAD_OK)
|
||||
{
|
||||
if (pProgress)
|
||||
{
|
||||
pProgress->SetText(LoadStringEx(IDS_PROGRESS_DOWNLOAD));
|
||||
if (fileSize==0)
|
||||
pProgress->SetProgress(-1);
|
||||
}
|
||||
int CHUNK_SIZE=32768;
|
||||
DWORD size=0;
|
||||
buf.reserve(fileSize+CHUNK_SIZE);
|
||||
while (1)
|
||||
{
|
||||
if (pProgress && pProgress->IsCanceled())
|
||||
{
|
||||
res=DOWNLOAD_CANCEL;
|
||||
break;
|
||||
}
|
||||
DWORD dwSize;
|
||||
buf.resize(size+CHUNK_SIZE);
|
||||
if (!InternetReadFile(hRequest,&buf[size],CHUNK_SIZE,&dwSize))
|
||||
{
|
||||
res=DOWNLOAD_FAIL;
|
||||
break;
|
||||
}
|
||||
if (dwSize==0)
|
||||
break;
|
||||
size+=dwSize;
|
||||
if (pProgress && fileSize)
|
||||
pProgress->SetProgress(size*100/fileSize);
|
||||
}
|
||||
buf.resize(size);
|
||||
}
|
||||
InternetCloseHandle(hRequest);
|
||||
}
|
||||
else
|
||||
res=DOWNLOAD_START;
|
||||
}
|
||||
InternetCloseHandle(hConnect);
|
||||
}
|
||||
else
|
||||
res=DOWNLOAD_START;
|
||||
|
||||
InternetCloseHandle(hInternet);
|
||||
return res;
|
||||
}
|
||||
|
||||
static int SaveFile( const wchar_t *fname, const std::vector<char> &buf )
|
||||
{
|
||||
HANDLE h=CreateFile(fname,GENERIC_WRITE,0,NULL,CREATE_ALWAYS,FILE_ATTRIBUTE_NORMAL,NULL);
|
||||
int err=0;
|
||||
if (h!=INVALID_HANDLE_VALUE)
|
||||
{
|
||||
DWORD size=(DWORD)buf.size();
|
||||
DWORD q;
|
||||
if (WriteFile(h,&buf[0],size,&q,NULL) && q==size)
|
||||
CloseHandle(h);
|
||||
else
|
||||
{
|
||||
err=GetLastError();
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"Failed to write file '%s': 0x%08X",fname,err);
|
||||
#endif
|
||||
CloseHandle(h);
|
||||
DeleteFile(fname);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
err=GetLastError();
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"Failed to save file '%s': 0x%08X",fname,err);
|
||||
#endif
|
||||
}
|
||||
return err;
|
||||
}
|
||||
|
||||
struct VersionCheckParams
|
||||
{
|
||||
TVersionCheck check;
|
||||
TSettingsComponent component;
|
||||
tNewVersionCallback callback;
|
||||
CProgressDlg *progress;
|
||||
bool nightly = false;
|
||||
};
|
||||
|
||||
// 0 - fail, 1 - success, 2 - cancel
|
||||
static DWORD WINAPI ThreadVersionCheck( void *param )
|
||||
{
|
||||
VersionCheckParams params=*(VersionCheckParams*)param;
|
||||
delete param;
|
||||
param=NULL;
|
||||
ULONGLONG curTimeL;
|
||||
GetSystemTimeAsFileTime((FILETIME*)&curTimeL);
|
||||
DWORD curTime=(DWORD)(curTimeL/TIME_DIVISOR); // in 0.01 hours
|
||||
|
||||
CRegKey regKey;
|
||||
if (regKey.Open(HKEY_CURRENT_USER,L"Software\\OpenShell\\OpenShell")!=ERROR_SUCCESS)
|
||||
{
|
||||
g_bCheckingVersion=false;
|
||||
return 0;
|
||||
}
|
||||
DWORD curVersion=GetVersionEx(g_Instance);
|
||||
|
||||
bool res = false;
|
||||
VersionData data;
|
||||
|
||||
{
|
||||
auto load = data.Load(!params.nightly);
|
||||
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG, L"Load result: %d", load);
|
||||
#endif
|
||||
res = (load == VersionData::LOAD_OK);
|
||||
}
|
||||
|
||||
curTime+=(rand()*TIME_PRECISION)/(RAND_MAX+1)-(TIME_PRECISION/2); // add between -30 and 30 minutes to randomize access
|
||||
if (!res)
|
||||
{
|
||||
g_bCheckingVersion=false;
|
||||
// if the check failed pretend we checked 5 days ago (so we check again in 48 hours)
|
||||
if (curTime>24*5*TIME_PRECISION)
|
||||
regKey.SetDWORDValue(L"LastUpdateTime",curTime-24*5*TIME_PRECISION);
|
||||
return 0;
|
||||
}
|
||||
|
||||
regKey.SetDWORDValue(L"LastUpdateTime",curTime);
|
||||
|
||||
{
|
||||
DWORD remindedVersion;
|
||||
if (regKey.QueryDWORDValue(L"RemindedVersion",remindedVersion)!=ERROR_SUCCESS)
|
||||
remindedVersion=0;
|
||||
data.bNewVersion=(data.newVersion>curVersion);
|
||||
data.bIgnoreVersion=(data.bNewVersion && data.newVersion<=remindedVersion);
|
||||
}
|
||||
|
||||
data.bValid=true;
|
||||
if (params.check==CHECK_UPDATE)
|
||||
{
|
||||
params.callback(data);
|
||||
g_bCheckingVersion=false;
|
||||
return 1;
|
||||
}
|
||||
if (data.bNewVersion && !data.bIgnoreVersion)
|
||||
params.callback(data);
|
||||
g_bCheckingVersion=false;
|
||||
return 0;
|
||||
}
|
||||
|
||||
DWORD CheckForNewVersion( HWND owner, TSettingsComponent component, TVersionCheck check, tNewVersionCallback callback )
|
||||
{
|
||||
if (g_bCheckingVersion) return 0;
|
||||
|
||||
if (check==CHECK_UPDATE)
|
||||
{
|
||||
g_bCheckingVersion=true;
|
||||
VersionCheckParams *params=new VersionCheckParams;
|
||||
params->check=check;
|
||||
params->component=component;
|
||||
params->callback=callback;
|
||||
params->progress=NULL;
|
||||
|
||||
// check the Update setting (uses the current value in the registry, not the one from memory
|
||||
{
|
||||
CRegKey regSettings, regSettingsUser, regPolicy, regPolicyUser;
|
||||
bool bUpgrade = OpenSettingsKeys(COMPONENT_SHARED, regSettings, regSettingsUser, regPolicy, regPolicyUser);
|
||||
|
||||
CSetting settings[] = {
|
||||
{L"Nightly",CSetting::TYPE_BOOL,0,0,0},
|
||||
{NULL}
|
||||
};
|
||||
|
||||
settings[0].LoadValue(regSettings, regSettingsUser, regPolicy, regPolicyUser);
|
||||
|
||||
params->nightly = GetSettingBool(settings[0]);
|
||||
}
|
||||
|
||||
if (!owner)
|
||||
return ThreadVersionCheck(params);
|
||||
|
||||
CProgressDlg progress;
|
||||
params->progress=&progress;
|
||||
progress.Create(owner,LoadStringEx(IDS_PROGRESS_TITLE_CHECK));
|
||||
|
||||
HANDLE hThread=CreateThread(NULL,0,ThreadVersionCheck,params,0,NULL);
|
||||
|
||||
while (1)
|
||||
{
|
||||
DWORD wait=MsgWaitForMultipleObjects(1,&hThread,FALSE,INFINITE,QS_ALLINPUT);
|
||||
if (wait!=WAIT_OBJECT_0+1)
|
||||
break;
|
||||
MSG msg;
|
||||
while (PeekMessage(&msg,0,0,0,PM_REMOVE))
|
||||
{
|
||||
TranslateMessage(&msg);
|
||||
DispatchMessage(&msg);
|
||||
}
|
||||
}
|
||||
progress.DestroyWindow();
|
||||
DWORD exit;
|
||||
if (!GetExitCodeThread(hThread,&exit))
|
||||
exit=0;
|
||||
CloseHandle(hThread);
|
||||
return exit;
|
||||
}
|
||||
else
|
||||
{
|
||||
ULONGLONG curTimeL;
|
||||
GetSystemTimeAsFileTime((FILETIME*)&curTimeL);
|
||||
DWORD curTime=(DWORD)(curTimeL/TIME_DIVISOR); // in 0.01 hours
|
||||
|
||||
CRegKey regKey;
|
||||
if (regKey.Open(HKEY_CURRENT_USER,L"Software\\OpenShell\\OpenShell")!=ERROR_SUCCESS)
|
||||
regKey.Create(HKEY_CURRENT_USER,L"Software\\OpenShell\\OpenShell");
|
||||
|
||||
DWORD lastTime;
|
||||
if (regKey.QueryDWORDValue(L"LastUpdateTime",lastTime)!=ERROR_SUCCESS)
|
||||
lastTime=0;
|
||||
if ((int)(curTime-lastTime)<168*TIME_PRECISION)
|
||||
return 0; // check weekly
|
||||
|
||||
// check the Update setting (uses the current value in the registry, not the one from memory
|
||||
bool nightly = false;
|
||||
{
|
||||
CRegKey regSettings, regSettingsUser, regPolicy, regPolicyUser;
|
||||
bool bUpgrade=OpenSettingsKeys(COMPONENT_SHARED,regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
|
||||
CSetting settings[]={
|
||||
{L"Update",CSetting::TYPE_BOOL,0,0,1},
|
||||
{L"Nightly",CSetting::TYPE_BOOL,0,0,0},
|
||||
{NULL}
|
||||
};
|
||||
|
||||
settings[0].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
settings[1].LoadValue(regSettings,regSettingsUser,regPolicy,regPolicyUser);
|
||||
|
||||
if (!GetSettingBool(settings[0]))
|
||||
return 0;
|
||||
nightly = GetSettingBool(settings[1]);
|
||||
}
|
||||
|
||||
VersionCheckParams *params=new VersionCheckParams;
|
||||
params->check=check;
|
||||
params->component=component;
|
||||
params->callback=callback;
|
||||
params->progress=NULL;
|
||||
params->nightly=nightly;
|
||||
|
||||
g_bCheckingVersion=true;
|
||||
if (check==CHECK_AUTO_WAIT)
|
||||
return ThreadVersionCheck(params);
|
||||
HANDLE hThread=CreateThread(NULL,0,ThreadVersionCheck,params,0,NULL);
|
||||
CloseHandle(hThread);
|
||||
return hThread!=NULL?1:0;
|
||||
}
|
||||
}
|
||||
|
||||
static CString LoadStringEx( HMODULE hModule, int stringId, int langId )
|
||||
{
|
||||
CString res;
|
||||
|
||||
HRSRC hrsrc=FindResourceEx(hModule,RT_STRING,MAKEINTRESOURCE((stringId>>4)+1),(WORD)langId);
|
||||
if (!hrsrc) return res;
|
||||
HGLOBAL hglb=LoadResource(hModule,hrsrc);
|
||||
if (!hglb) return res;
|
||||
WORD *data=(WORD*)LockResource(hglb);
|
||||
if (!data) return res;
|
||||
|
||||
stringId&=15;
|
||||
for (int i=0;i<stringId;i++)
|
||||
data+=*data+1;
|
||||
int len=*data;
|
||||
data++;
|
||||
|
||||
if (len)
|
||||
{
|
||||
wchar_t *buf=res.GetBuffer(len);
|
||||
memcpy(buf,data,len*2);
|
||||
buf[len]=0;
|
||||
res.ReleaseBufferSetLength(len);
|
||||
}
|
||||
|
||||
UnlockResource(hglb);
|
||||
return res;
|
||||
}
|
||||
|
||||
static bool VerifyDigitalCertificate( const wchar_t *fname, const wchar_t *signer )
|
||||
{
|
||||
// verify the certificate
|
||||
WINTRUST_FILE_INFO fileData={sizeof(fileData),fname};
|
||||
|
||||
WINTRUST_DATA winTrustData={sizeof(winTrustData)};
|
||||
winTrustData.dwUIChoice=WTD_UI_NONE;
|
||||
winTrustData.fdwRevocationChecks=WTD_REVOKE_NONE;
|
||||
winTrustData.dwUnionChoice=WTD_CHOICE_FILE;
|
||||
winTrustData.dwStateAction=WTD_STATEACTION_VERIFY;
|
||||
winTrustData.pFile=&fileData;
|
||||
|
||||
GUID policyGUID=WINTRUST_ACTION_GENERIC_VERIFY_V2;
|
||||
LONG lStatus=WinVerifyTrust((HWND)INVALID_HANDLE_VALUE,&policyGUID,&winTrustData);
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"Verify Trust Result: 0x%08X",lStatus);
|
||||
#endif
|
||||
|
||||
winTrustData.dwStateAction=WTD_STATEACTION_CLOSE;
|
||||
WinVerifyTrust((HWND)INVALID_HANDLE_VALUE,&policyGUID,&winTrustData);
|
||||
if (lStatus!=ERROR_SUCCESS && lStatus!=CERT_E_EXPIRED)
|
||||
return false;
|
||||
|
||||
// verify the signer name
|
||||
CString signerName;
|
||||
|
||||
HCERTSTORE hStore;
|
||||
HCRYPTMSG hMsg;
|
||||
if (CryptQueryObject(CERT_QUERY_OBJECT_FILE,fname,CERT_QUERY_CONTENT_FLAG_ALL,CERT_QUERY_FORMAT_FLAG_ALL,0,NULL,NULL,NULL,&hStore,&hMsg,NULL) && hStore && hMsg)
|
||||
{
|
||||
DWORD len;
|
||||
if (CryptMsgGetParam(hMsg,CMSG_SIGNER_INFO_PARAM,0,NULL,&len) && len>0)
|
||||
{
|
||||
std::vector<char> signerInfo(len);
|
||||
CMSG_SIGNER_INFO *pSignerInfo=(CMSG_SIGNER_INFO*)&signerInfo[0];
|
||||
if (CryptMsgGetParam(hMsg,CMSG_SIGNER_INFO_PARAM,0,pSignerInfo,&len))
|
||||
{
|
||||
CERT_INFO certInfo;
|
||||
certInfo.Issuer=pSignerInfo->Issuer;
|
||||
certInfo.SerialNumber=pSignerInfo->SerialNumber;
|
||||
PCCERT_CONTEXT pCertContext=CertFindCertificateInStore(hStore,X509_ASN_ENCODING|PKCS_7_ASN_ENCODING,0,CERT_FIND_SUBJECT_CERT,&certInfo,NULL);
|
||||
if (pCertContext)
|
||||
{
|
||||
len=CertGetNameString(pCertContext,CERT_NAME_SIMPLE_DISPLAY_TYPE,0,NULL,NULL,0);
|
||||
if (len>1)
|
||||
{
|
||||
wchar_t *buf=signerName.GetBuffer(len-1);
|
||||
if (buf)
|
||||
{
|
||||
DWORD res=CertGetNameString(pCertContext,CERT_NAME_SIMPLE_DISPLAY_TYPE,0,NULL,buf,len);
|
||||
signerName.ReleaseBufferSetLength(len-1);
|
||||
if (!res) signerName.Empty();
|
||||
}
|
||||
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"Signer: '%s', '%s'",signer,signerName);
|
||||
#endif
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"CertGetNameString failed");
|
||||
#endif
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"CertFindCertificateInStore failed");
|
||||
#endif
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"CryptMsgGetParam2 failed");
|
||||
#endif
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"CryptMsgGetParam1 failed");
|
||||
#endif
|
||||
}
|
||||
if (hStore) CertCloseStore(hStore,0);
|
||||
if (hMsg) CryptMsgClose(hMsg);
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG,L"CryptQueryObject failed");
|
||||
#endif
|
||||
}
|
||||
|
||||
return (signerName==signer);
|
||||
}
|
||||
|
||||
void VersionData::Clear( void )
|
||||
{
|
||||
bValid=false;
|
||||
newVersion=0;
|
||||
downloadUrl.Empty();
|
||||
downloadSigner.Empty();
|
||||
news.Empty();
|
||||
updateLink="https://github.com/Open-Shell/Open-Shell-Menu/releases";
|
||||
bNewVersion=bIgnoreVersion=false;
|
||||
}
|
||||
|
||||
void VersionData::Swap( VersionData &data )
|
||||
{
|
||||
std::swap(bValid,data.bValid);
|
||||
std::swap(newVersion,data.newVersion);
|
||||
std::swap(downloadUrl,data.downloadUrl);
|
||||
std::swap(downloadSigner,data.downloadSigner);
|
||||
std::swap(news,data.news);
|
||||
std::swap(updateLink,data.updateLink);
|
||||
std::swap(bNewVersion,data.bNewVersion);
|
||||
std::swap(bIgnoreVersion,data.bIgnoreVersion);
|
||||
}
|
||||
|
||||
std::vector<char> DownloadUrl(const wchar_t* url)
|
||||
{
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG, L"URL: %s", url);
|
||||
#endif
|
||||
|
||||
std::vector<char> buffer;
|
||||
TDownloadResult download = DownloadFile(url, buffer, nullptr, false, nullptr, COMPONENT_UPDATE);
|
||||
|
||||
#ifdef UPDATE_LOG
|
||||
LogToFile(UPDATE_LOG, L"Download result: %d", download);
|
||||
#endif
|
||||
|
||||
if (download != DOWNLOAD_OK)
|
||||
buffer.clear();
|
||||
|
||||
return buffer;
|
||||
}
|
||||
|
||||
using namespace nlohmann;
|
||||
|
||||
VersionData::TLoadResult VersionData::Load(bool official)
|
||||
{
|
||||
Clear();
|
||||
|
||||
std::wstring baseUrl = L"https://api.github.com/repos/Open-Shell/Open-Shell-Menu/releases";
|
||||
if (official)
|
||||
baseUrl += L"/latest";
|
||||
|
||||
auto buf = DownloadUrl(baseUrl.c_str());
|
||||
if (buf.empty())
|
||||
return LOAD_ERROR;
|
||||
|
||||
try
|
||||
{
|
||||
auto jsonData = json::parse(buf.begin(), buf.end());
|
||||
auto& data = jsonData;
|
||||
|
||||
if (official)
|
||||
{
|
||||
// skip prerelease versions (just in case)
|
||||
if (data["prerelease"].get<bool>())
|
||||
return LOAD_BAD_VERSION;
|
||||
}
|
||||
else
|
||||
{
|
||||
// we've got list of versions (release and pre-release)
|
||||
// lets pick first one (that should be the latest one)
|
||||
data = jsonData[0];
|
||||
}
|
||||
|
||||
// make sure we didn't get draft release (for whatever reason)
|
||||
if (data["draft"].get<bool>())
|
||||
return LOAD_BAD_VERSION;
|
||||
|
||||
// get version from tag name
|
||||
auto tag = data["tag_name"].get<std::string>();
|
||||
if (tag.empty())
|
||||
return LOAD_BAD_FILE;
|
||||
|
||||
int v1, v2, v3;
|
||||
if (sscanf_s(tag.c_str(), "v%d.%d.%d", &v1, &v2, &v3) != 3)
|
||||
return LOAD_BAD_FILE;
|
||||
|
||||
newVersion = (v1 << 24) | (v2 << 16) | v3;
|
||||
|
||||
// installer url
|
||||
std::string url;
|
||||
for (const auto& asset : data["assets"])
|
||||
{
|
||||
if (asset["name"].get<std::string>().find("OpenShellSetup") == 0)
|
||||
{
|
||||
url = asset["browser_download_url"].get<std::string>();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (url.empty())
|
||||
return LOAD_BAD_FILE;
|
||||
|
||||
downloadUrl.Append(CA2T(url.c_str()));
|
||||
|
||||
// changelog
|
||||
auto body = data["body"].get<std::string>();
|
||||
if (!body.empty())
|
||||
{
|
||||
auto name = data["name"].get<std::string>();
|
||||
if (!name.empty())
|
||||
{
|
||||
news.Append(CA2T(name.c_str()));
|
||||
news.Append(L"\r\n\r\n");
|
||||
}
|
||||
|
||||
news.Append(CA2T(body.c_str()));
|
||||
news.Replace(L"\\n", L"\n");
|
||||
news.Replace(L"\\r", L"\r");
|
||||
}
|
||||
|
||||
return LOAD_OK;
|
||||
}
|
||||
catch (...)
|
||||
{
|
||||
return LOAD_BAD_FILE;
|
||||
}
|
||||
}
|
||||
|
||||
struct DownloadFileParams
|
||||
{
|
||||
// input
|
||||
const wchar_t *url;
|
||||
const wchar_t *signer;
|
||||
DWORD hash;
|
||||
const wchar_t *path;
|
||||
CString fname; // file name on input, full path on output
|
||||
CProgressDlg *progress;
|
||||
bool bAcceptCached;
|
||||
TSettingsComponent component;
|
||||
|
||||
// output
|
||||
TDownloadResult downloadRes;
|
||||
int saveRes;
|
||||
bool valid;
|
||||
};
|
||||
|
||||
static DWORD WINAPI ThreadDownloadFile( void *param )
|
||||
{
|
||||
DownloadFileParams ¶ms=*(DownloadFileParams*)param;
|
||||
param=NULL;
|
||||
params.valid=false;
|
||||
params.saveRes=0;
|
||||
|
||||
std::vector<char> buf;
|
||||
params.downloadRes=DownloadFile(params.url,buf,params.fname.IsEmpty()?¶ms.fname:NULL,params.bAcceptCached,params.progress,params.component);
|
||||
if (params.downloadRes==DOWNLOAD_CANCEL || params.downloadRes>=DOWNLOAD_FIRST_ERROR)
|
||||
return 0;
|
||||
|
||||
params.valid=!buf.empty();
|
||||
if (!params.valid)
|
||||
return 0;
|
||||
|
||||
// validate hash
|
||||
if (params.hash)
|
||||
{
|
||||
if (params.progress)
|
||||
params.progress->SetText(LoadStringEx(IDS_PROGRESS_VERIFY));
|
||||
|
||||
params.valid=(CalcFNVHash(&buf[0],(int)buf.size(),FNV_HASH0)==params.hash);
|
||||
if (!params.valid)
|
||||
return 0;
|
||||
}
|
||||
|
||||
// save
|
||||
if (params.progress)
|
||||
{
|
||||
params.progress->SetText(LoadStringEx(IDS_PROGRESS_SAVE));
|
||||
params.progress->EnableCancel(false);
|
||||
params.progress->SetProgress(-1);
|
||||
}
|
||||
wchar_t fname[_MAX_PATH];
|
||||
Sprintf(fname,_countof(fname),L"%s\\%s",params.path,params.fname);
|
||||
params.fname=fname;
|
||||
params.saveRes=SaveFile(fname,buf);
|
||||
if (params.saveRes)
|
||||
return 0;
|
||||
|
||||
// validate signer
|
||||
/*
|
||||
if (params.signer)
|
||||
{
|
||||
if (params.progress)
|
||||
params.progress->SetText(LoadStringEx(IDS_PROGRESS_VERIFY));
|
||||
params.valid=VerifyDigitalCertificate(fname,params.signer);
|
||||
if (!params.valid)
|
||||
{
|
||||
DeleteFile(fname);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
*/
|
||||
return 0;
|
||||
}
|
||||
|
||||
DWORD DownloadNewVersion( HWND owner, TSettingsComponent component, const wchar_t *url, const wchar_t *signer, CString &fname, CString &error )
|
||||
{
|
||||
CComString pPath;
|
||||
if (FAILED(SHGetKnownFolderPath(FOLDERID_Downloads,0,NULL,&pPath)) || !pPath)
|
||||
{
|
||||
if (FAILED(SHGetKnownFolderPath(FOLDERID_Documents,0,NULL,&pPath)) || !pPath)
|
||||
{
|
||||
if (FAILED(SHGetKnownFolderPath(FOLDERID_Desktop,0,NULL,&pPath)) || !pPath)
|
||||
{
|
||||
error=LoadStringEx(IDS_INST_DOWNLOAD_FAIL);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
CProgressDlg progress;
|
||||
progress.Create(owner,LoadStringEx(IDS_PROGRESS_TITLE_DOWNLOAD));
|
||||
|
||||
DownloadFileParams params;
|
||||
params.url=url;
|
||||
params.signer=signer;
|
||||
params.hash=0;
|
||||
params.path=pPath;
|
||||
params.progress=&progress;
|
||||
params.bAcceptCached=true;
|
||||
params.component=component;
|
||||
|
||||
{
|
||||
const wchar_t* name = wcsrchr(url, '/');
|
||||
if (name && name[1])
|
||||
params.fname.Append(name+1);
|
||||
}
|
||||
|
||||
HANDLE hThread=CreateThread(NULL,0,ThreadDownloadFile,¶ms,0,NULL);
|
||||
|
||||
while (1)
|
||||
{
|
||||
DWORD wait=MsgWaitForMultipleObjects(1,&hThread,FALSE,INFINITE,QS_ALLINPUT);
|
||||
if (wait!=WAIT_OBJECT_0+1)
|
||||
break;
|
||||
MSG msg;
|
||||
while (PeekMessage(&msg,0,0,0,PM_REMOVE))
|
||||
{
|
||||
TranslateMessage(&msg);
|
||||
DispatchMessage(&msg);
|
||||
}
|
||||
}
|
||||
progress.DestroyWindow();
|
||||
CloseHandle(hThread);
|
||||
|
||||
if (params.downloadRes==DOWNLOAD_CANCEL)
|
||||
return 2;
|
||||
if (params.downloadRes==DOWNLOAD_INTERNET)
|
||||
{
|
||||
error=LoadStringEx(IDS_INTERNET_FAIL);
|
||||
return 0;
|
||||
}
|
||||
else if (params.downloadRes==DOWNLOAD_START)
|
||||
{
|
||||
error=LoadStringEx(IDS_INITIATE_FAIL);
|
||||
return 0;
|
||||
}
|
||||
else if (params.downloadRes==DOWNLOAD_FAIL)
|
||||
{
|
||||
error=LoadStringEx(IDS_INST_DOWNLOAD_FAIL);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (params.saveRes)
|
||||
{
|
||||
wchar_t msg[256];
|
||||
FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM|FORMAT_MESSAGE_IGNORE_INSERTS,NULL,params.saveRes,0,msg,_countof(msg),NULL);
|
||||
error.Format(LoadStringEx(IDS_INST_SAVE_FAIL),params.fname);
|
||||
error+="\r\n";
|
||||
error+=msg;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!params.valid)
|
||||
{
|
||||
error=LoadStringEx(IDS_INST_DOWNLOAD_FAIL);
|
||||
return 0;
|
||||
}
|
||||
|
||||
fname=params.fname;
|
||||
return 1;
|
||||
}
|
||||
50
Src/Lib/DownloadHelper.h
Normal file
@@ -0,0 +1,50 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
|
||||
enum TVersionCheck
|
||||
{
|
||||
CHECK_AUTO,
|
||||
CHECK_AUTO_WAIT,
|
||||
CHECK_UPDATE,
|
||||
};
|
||||
|
||||
enum TSettingsComponent;
|
||||
|
||||
struct VersionData
|
||||
{
|
||||
bool bValid = false;
|
||||
DWORD newVersion = 0;
|
||||
CString downloadUrl;
|
||||
CString downloadSigner;
|
||||
CString news;
|
||||
CString updateLink;
|
||||
bool bNewVersion = false;
|
||||
bool bIgnoreVersion = false;
|
||||
|
||||
~VersionData( void ) { Clear(); }
|
||||
void Clear( void );
|
||||
void Swap( VersionData &data );
|
||||
|
||||
enum TLoadResult
|
||||
{
|
||||
LOAD_OK,
|
||||
LOAD_ERROR, // the file is missing some data
|
||||
LOAD_BAD_VERSION, // the version is wrong
|
||||
LOAD_BAD_FILE, // the file is corrupted
|
||||
};
|
||||
|
||||
TLoadResult Load(bool official);
|
||||
private:
|
||||
void operator=( const VersionData& );
|
||||
};
|
||||
|
||||
typedef void (*tNewVersionCallback)( VersionData &data );
|
||||
|
||||
// 0 - fail, 1 - success, 2 - cancel
|
||||
DWORD CheckForNewVersion( HWND owner, TSettingsComponent component, TVersionCheck check, tNewVersionCallback callback );
|
||||
DWORD DownloadNewVersion( HWND owner, TSettingsComponent component, const wchar_t *url, const wchar_t *signer, CString &fname, CString &error );
|
||||
29
Src/Lib/FNVHash.cpp
Normal file
@@ -0,0 +1,29 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include <stdafx.h>
|
||||
#include "FNVHash.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
// FNV hash algorithm as described here: http://www.isthe.com/chongo/tech/comp/fnv/index.html
|
||||
|
||||
// Calculate FNV hash for a memory buffer
|
||||
unsigned int CalcFNVHash( const void *buf, int len, unsigned int hash )
|
||||
{
|
||||
for (int i=0;i<len;i++)
|
||||
hash=(hash^((const unsigned char*)buf)[i])*16777619;
|
||||
return hash;
|
||||
}
|
||||
|
||||
// Calculate FNV hash for a string
|
||||
unsigned int CalcFNVHash( const char *text, unsigned int hash )
|
||||
{
|
||||
return CalcFNVHash(text,Strlen(text),hash);
|
||||
}
|
||||
|
||||
// Calculate FNV hash for a wide string
|
||||
unsigned int CalcFNVHash( const wchar_t *text, unsigned int hash )
|
||||
{
|
||||
return CalcFNVHash(text,Strlen(text)*2,hash);
|
||||
}
|
||||
16
Src/Lib/FNVHash.h
Normal file
@@ -0,0 +1,16 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
const unsigned int FNV_HASH0=2166136261;
|
||||
|
||||
// Calculate FNV hash for a memory buffer
|
||||
unsigned int CalcFNVHash( const void *buf, int len, unsigned int hash=FNV_HASH0 );
|
||||
|
||||
// Calculate FNV hash for a string
|
||||
unsigned int CalcFNVHash( const char *text, unsigned int hash=FNV_HASH0 );
|
||||
|
||||
// Calculate FNV hash for a wide string
|
||||
unsigned int CalcFNVHash( const wchar_t *text, unsigned int hash=FNV_HASH0 );
|
||||
76
Src/Lib/FileHelper.cpp
Normal file
@@ -0,0 +1,76 @@
|
||||
#include "stdafx.h"
|
||||
#include "StringUtils.h"
|
||||
|
||||
bool CreateFakeFolder( const wchar_t *source, const wchar_t *fname )
|
||||
{
|
||||
// create directory
|
||||
CreateDirectory(fname,NULL);
|
||||
if (!SetFileAttributes(fname,FILE_ATTRIBUTE_READONLY))
|
||||
return false;
|
||||
|
||||
// create shortcut
|
||||
wchar_t path[_MAX_PATH];
|
||||
Sprintf(path,_countof(path),L"%s\\target.lnk",fname);
|
||||
{
|
||||
CComPtr<IShellLink> pLink;
|
||||
HRESULT hr=pLink.CoCreateInstance(CLSID_ShellLink);
|
||||
if (FAILED(hr)) return false;
|
||||
pLink->SetPath(source);
|
||||
CComQIPtr<IPersistFile> pFile(pLink);
|
||||
if (!pFile) return false;
|
||||
hr=pFile->Save(path,TRUE);
|
||||
if (FAILED(hr)) return false;
|
||||
}
|
||||
|
||||
// create desktop.ini
|
||||
Sprintf(path,_countof(path),L"%s\\desktop.ini",fname);
|
||||
HANDLE f=CreateFile(path,GENERIC_WRITE,0,NULL,CREATE_ALWAYS,FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM,NULL);
|
||||
if (f==INVALID_HANDLE_VALUE) return false;
|
||||
const char *desktopIni="[.ShellClassInfo]\r\nCLSID2={0AFACED1-E828-11D1-9187-B532F1E9575D}\r\nFlags=2\r\n";
|
||||
DWORD q;
|
||||
WriteFile(f,desktopIni,Strlen(desktopIni),&q,NULL);
|
||||
CloseHandle(f);
|
||||
return true;
|
||||
}
|
||||
|
||||
void DeleteFakeFolder( const wchar_t *fname )
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
Sprintf(path,_countof(path),L"%s\\target.lnk",fname);
|
||||
BOOL res;
|
||||
res=SetFileAttributes(path,GetFileAttributes(path)&~FILE_ATTRIBUTE_READONLY);
|
||||
res=DeleteFile(path);
|
||||
Sprintf(path,_countof(path),L"%s\\desktop.ini",fname);
|
||||
res=SetFileAttributes(path,GetFileAttributes(path)&~FILE_ATTRIBUTE_READONLY);
|
||||
res=DeleteFile(path);
|
||||
res=SetFileAttributes(fname,GetFileAttributes(fname)&~FILE_ATTRIBUTE_READONLY);
|
||||
res=RemoveDirectory(fname);
|
||||
}
|
||||
|
||||
bool IsFakeFolder( const wchar_t *fname )
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
Sprintf(path,_countof(path),L"%s\\target.lnk",fname);
|
||||
if (GetFileAttributes(path)!=INVALID_FILE_ATTRIBUTES)
|
||||
{
|
||||
Sprintf(path,_countof(path),L"%s\\desktop.ini",fname);
|
||||
DWORD attrib=GetFileAttributes(path);
|
||||
if (attrib!=INVALID_FILE_ATTRIBUTES && (attrib&FILE_ATTRIBUTE_SYSTEM))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool GetFakeFolder( wchar_t *dst, int len, const wchar_t *src )
|
||||
{
|
||||
Sprintf(dst,len,L"%s\\target.lnk",src);
|
||||
if (GetFileAttributes(dst)!=INVALID_FILE_ATTRIBUTES)
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
Sprintf(path,_countof(path),L"%s\\desktop.ini",src);
|
||||
DWORD attrib=GetFileAttributes(path);
|
||||
if (attrib!=INVALID_FILE_ATTRIBUTES && (attrib&FILE_ATTRIBUTE_SYSTEM))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
10
Src/Lib/FileHelper.h
Normal file
@@ -0,0 +1,10 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
bool CreateFakeFolder( const wchar_t *source, const wchar_t *fname );
|
||||
void DeleteFakeFolder( const wchar_t *fname );
|
||||
bool IsFakeFolder( const wchar_t *fname );
|
||||
bool GetFakeFolder( wchar_t *dst, int len, const wchar_t *src );
|
||||
144
Src/Lib/IatHookHelper.cpp
Normal file
@@ -0,0 +1,144 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include <stdafx.h>
|
||||
#include "IatHookHelper.h"
|
||||
#include "Assert.h"
|
||||
|
||||
struct ImgDelayDescr
|
||||
{
|
||||
DWORD grAttrs; // attributes
|
||||
DWORD rvaDLLName; // RVA to dll name
|
||||
DWORD rvaHmod; // RVA of module handle
|
||||
DWORD rvaIAT; // RVA of the IAT
|
||||
DWORD rvaINT; // RVA of the INT
|
||||
DWORD rvaBoundIAT; // RVA of the optional bound IAT
|
||||
DWORD rvaUnloadIAT; // RVA of optional copy of original IAT
|
||||
DWORD dwTimeStamp; // 0 if not bound, O.W. date/time stamp of DLL bound to (Old BIND)
|
||||
};
|
||||
|
||||
static void *PtrFromRva( IMAGE_DOS_HEADER *dosHeader, size_t offset )
|
||||
{
|
||||
return (BYTE*)dosHeader+offset;
|
||||
}
|
||||
|
||||
static IatHookData *g_IatHooks;
|
||||
static int g_IatHookCount;
|
||||
|
||||
const int MAX_IAT_HOOKS=4096/sizeof(IatHookData);
|
||||
|
||||
void InitializeIatHooks( void )
|
||||
{
|
||||
Assert(!g_IatHooks);
|
||||
g_IatHooks=(IatHookData*)VirtualAlloc(NULL,4096,MEM_COMMIT,PAGE_EXECUTE_READWRITE);
|
||||
g_IatHookCount=0;
|
||||
}
|
||||
|
||||
void ClearIatHooks( void )
|
||||
{
|
||||
if (!g_IatHooks) return;
|
||||
for (int i=0;i<g_IatHookCount;i++)
|
||||
{
|
||||
if (g_IatHooks[i].jump[0])
|
||||
return; // still used
|
||||
}
|
||||
VirtualFree(g_IatHooks,0,MEM_RELEASE);
|
||||
g_IatHooks=NULL;
|
||||
g_IatHookCount=0;
|
||||
}
|
||||
|
||||
IatHookData *SetIatHook( IMAGE_DOS_HEADER *dosHeader, DWORD iatOffset, DWORD intOfset, const char *targetProc, void *newProc )
|
||||
{
|
||||
IMAGE_THUNK_DATA *thunk=(IMAGE_THUNK_DATA*)PtrFromRva(dosHeader,iatOffset);
|
||||
IMAGE_THUNK_DATA *origThunk=(IMAGE_THUNK_DATA*)PtrFromRva(dosHeader,intOfset);
|
||||
for (;origThunk->u1.Function;origThunk++,thunk++)
|
||||
{
|
||||
if (origThunk->u1.Ordinal&IMAGE_ORDINAL_FLAG)
|
||||
{
|
||||
if (IS_INTRESOURCE(targetProc) && IMAGE_ORDINAL(origThunk->u1.Ordinal)==(uintptr_t)targetProc)
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
IMAGE_IMPORT_BY_NAME *import=(IMAGE_IMPORT_BY_NAME*)PtrFromRva(dosHeader,origThunk->u1.AddressOfData);
|
||||
if (!IS_INTRESOURCE(targetProc) && strcmp(targetProc,(char*)import->Name)==0)
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (origThunk->u1.Function)
|
||||
{
|
||||
IatHookData *hook=g_IatHooks+g_IatHookCount;
|
||||
g_IatHookCount++;
|
||||
hook->jump[0]=hook->jump[1]=0x90; // NOP
|
||||
hook->jump[2]=0xFF; hook->jump[3]=0x25; // JUMP
|
||||
#ifdef _WIN64
|
||||
hook->jumpOffs=0;
|
||||
#else
|
||||
hook->jumpOffs=(DWORD)(hook)+8;
|
||||
#endif
|
||||
hook->newProc=newProc;
|
||||
hook->oldProc=(void*)thunk->u1.Function;
|
||||
hook->thunk=thunk;
|
||||
DWORD oldProtect;
|
||||
VirtualProtect(&thunk->u1.Function,sizeof(void*),PAGE_READWRITE,&oldProtect);
|
||||
thunk->u1.Function=(DWORD_PTR)hook;
|
||||
VirtualProtect(&thunk->u1.Function,sizeof(void*),oldProtect,&oldProtect);
|
||||
return hook;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
IatHookData *SetIatHook( HMODULE hPatchedModule, const char *targetModule, const char *targetProc, void *newProc )
|
||||
{
|
||||
ATLASSERT(g_IatHooks);
|
||||
if (g_IatHookCount>=MAX_IAT_HOOKS) return NULL;
|
||||
IMAGE_DOS_HEADER *dosHeader=(IMAGE_DOS_HEADER*)hPatchedModule;
|
||||
IMAGE_NT_HEADERS *ntHeader=(IMAGE_NT_HEADERS*)PtrFromRva(dosHeader,dosHeader->e_lfanew);
|
||||
if (ntHeader->Signature!=IMAGE_NT_SIGNATURE) return NULL;
|
||||
|
||||
IMAGE_IMPORT_DESCRIPTOR *importDescriptor=(IMAGE_IMPORT_DESCRIPTOR*)PtrFromRva(dosHeader,ntHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress);
|
||||
|
||||
for (;importDescriptor->Characteristics!=0;importDescriptor++)
|
||||
{
|
||||
const char *dllName=(char*)PtrFromRva(dosHeader,importDescriptor->Name);
|
||||
if (_stricmp(dllName,targetModule)!=0) continue;
|
||||
|
||||
if (!importDescriptor->FirstThunk || !importDescriptor->OriginalFirstThunk) break;
|
||||
|
||||
return SetIatHook(dosHeader,importDescriptor->FirstThunk,importDescriptor->OriginalFirstThunk,targetProc,newProc);
|
||||
}
|
||||
|
||||
ImgDelayDescr *delayDescriptor=(ImgDelayDescr*)PtrFromRva(dosHeader,ntHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT].VirtualAddress);
|
||||
|
||||
for (;delayDescriptor->rvaDLLName!=0;delayDescriptor++)
|
||||
{
|
||||
const char *dllName=(char*)PtrFromRva(dosHeader,delayDescriptor->rvaDLLName);
|
||||
if (_stricmp(dllName,targetModule)!=0) continue;
|
||||
|
||||
if (!delayDescriptor->rvaIAT || !delayDescriptor->rvaINT) break;
|
||||
|
||||
return SetIatHook(dosHeader,delayDescriptor->rvaIAT,delayDescriptor->rvaINT,targetProc,newProc);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void ClearIatHook( IatHookData *hook )
|
||||
{
|
||||
if (!hook || !hook->jump[0]) return;
|
||||
if (hook->thunk->u1.Function==(DWORD_PTR)hook)
|
||||
{
|
||||
// the hook was untouched by anybody else
|
||||
DWORD oldProtect;
|
||||
VirtualProtect(&hook->thunk->u1.Function,sizeof(void*),PAGE_READWRITE,&oldProtect);
|
||||
void *cex=InterlockedCompareExchangePointer((void**)&hook->thunk->u1.Function,hook->oldProc,hook);
|
||||
VirtualProtect(&hook->thunk->u1.Function,sizeof(void*),oldProtect,&oldProtect);
|
||||
if (cex==hook)
|
||||
{
|
||||
hook->jump[0]=0;
|
||||
return; // successfully replaced the original function
|
||||
}
|
||||
}
|
||||
// failed to replace the original function, leave behind the thunk
|
||||
hook->newProc=hook->oldProc;
|
||||
}
|
||||
19
Src/Lib/IatHookHelper.h
Normal file
@@ -0,0 +1,19 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
struct IatHookData
|
||||
{
|
||||
unsigned char jump[4]; // jump instruction 0x90, 0x90, 0xFF, 0x25
|
||||
DWORD jumpOffs; // jump instruction offset
|
||||
void *newProc; // the address of the new proc
|
||||
void *oldProc; // the address of the old proc
|
||||
IMAGE_THUNK_DATA *thunk; // the IAT thunk
|
||||
};
|
||||
|
||||
void InitializeIatHooks( void );
|
||||
IatHookData *SetIatHook( HMODULE hPatchedModule, const char *targetModule, const char *targetProc, void *newProc );
|
||||
void ClearIatHook( IatHookData *hook );
|
||||
void ClearIatHooks( void );
|
||||
7
Src/Lib/Instance.cpp
Normal file
@@ -0,0 +1,7 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include <stdafx.h>
|
||||
|
||||
HINSTANCE g_Instance;
|
||||
431
Src/Lib/LanguageSettingsHelper.cpp
Normal file
@@ -0,0 +1,431 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include <stdafx.h>
|
||||
#include "resource.h"
|
||||
#include "Settings.h"
|
||||
#include "SettingsUIHelper.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "ComHelper.h"
|
||||
#include "FNVHash.h"
|
||||
#include "StringUtils.h"
|
||||
#include "Translations.h"
|
||||
#include "DownloadHelper.h"
|
||||
#include <uxtheme.h>
|
||||
#include <map>
|
||||
#include <algorithm>
|
||||
|
||||
int g_LanguageIDs[]={
|
||||
0x0401,
|
||||
0x0402,
|
||||
0x0403,
|
||||
0x0405,
|
||||
0x0406,
|
||||
0x0407,
|
||||
0x0408,
|
||||
0x0409,
|
||||
0x0C0A,
|
||||
0x0425,
|
||||
0x0429,
|
||||
0x040B,
|
||||
0x040C,
|
||||
0x0491,
|
||||
0x040D,
|
||||
0x041A,
|
||||
0x040E,
|
||||
0x040F,
|
||||
0x0410,
|
||||
0x0411,
|
||||
0x0412,
|
||||
0x0427,
|
||||
0x0426,
|
||||
0x0414,
|
||||
0x0413,
|
||||
0x0415,
|
||||
0x0416,
|
||||
0x0816,
|
||||
0x0418,
|
||||
0x0419,
|
||||
0x041B,
|
||||
0x0424,
|
||||
0x081A,
|
||||
0x041D,
|
||||
0x041E,
|
||||
0x041F,
|
||||
0x0422,
|
||||
0x0804,
|
||||
0x0C04,
|
||||
0x0404,
|
||||
};
|
||||
|
||||
int g_LanguageIDCount=_countof(g_LanguageIDs);
|
||||
|
||||
class CLanguageSettingsDlg: public CResizeableDlg<CLanguageSettingsDlg>
|
||||
{
|
||||
public:
|
||||
BEGIN_MSG_MAP( CLanguageSettingsDlg )
|
||||
MESSAGE_HANDLER( WM_INITDIALOG, OnInitDialog )
|
||||
MESSAGE_HANDLER( WM_DESTROY, OnDestroy )
|
||||
MESSAGE_HANDLER( WM_SIZE, OnSize )
|
||||
NOTIFY_HANDLER( IDC_LISTLANGUAGE, LVN_ITEMCHANGED, OnSelChange )
|
||||
NOTIFY_HANDLER( IDC_LISTLANGUAGE, LVN_ITEMCHANGING, OnSelChanging )
|
||||
NOTIFY_HANDLER( IDC_LISTLANGUAGE, NM_CUSTOMDRAW, OnCustomDraw )
|
||||
END_MSG_MAP()
|
||||
|
||||
BEGIN_RESIZE_MAP
|
||||
RESIZE_CONTROL(IDC_LISTLANGUAGE,MOVE_SIZE_X|MOVE_SIZE_Y)
|
||||
END_RESIZE_MAP
|
||||
|
||||
void SetGroup( CSetting *pGroup );
|
||||
void SetComponent( TSettingsComponent component ) { m_Component=component; }
|
||||
|
||||
protected:
|
||||
// Handler prototypes:
|
||||
// LRESULT MessageHandler(UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled);
|
||||
// LRESULT CommandHandler(WORD wNotifyCode, WORD wID, HWND hWndCtl, BOOL& bHandled);
|
||||
// LRESULT NotifyHandler(int idCtrl, LPNMHDR pnmh, BOOL& bHandled);
|
||||
LRESULT OnInitDialog( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnDestroy( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnSize( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled );
|
||||
LRESULT OnSelChange( int idCtrl, LPNMHDR pnmh, BOOL& bHandled );
|
||||
LRESULT OnSelChanging( int idCtrl, LPNMHDR pnmh, BOOL& bHandled );
|
||||
LRESULT OnCustomDraw( int idCtrl, LPNMHDR pnmh, BOOL& bHandled );
|
||||
|
||||
private:
|
||||
CSetting *m_pSetting;
|
||||
TSettingsComponent m_Component;
|
||||
CWindow m_Tooltip;
|
||||
HIMAGELIST m_ImageList;
|
||||
bool m_bLargeFlags;
|
||||
bool m_bLocked;
|
||||
|
||||
struct LangInfo
|
||||
{
|
||||
CString name;
|
||||
int id;
|
||||
int image;
|
||||
bool operator<( const LangInfo &info ) { return _wcsicmp(name,info.name)<0; }
|
||||
};
|
||||
std::vector<LangInfo> m_LanguageIDs; // the order matches the items in the listbox
|
||||
|
||||
void UpdateFlags( void );
|
||||
|
||||
void AddFlag( const wchar_t *langName, int langId, HBITMAP bmp );
|
||||
};
|
||||
|
||||
void CLanguageSettingsDlg::AddFlag( const wchar_t *langName, int langId, HBITMAP bmp )
|
||||
{
|
||||
int idx=1;
|
||||
for (;idx<(int)m_LanguageIDs.size();idx++)
|
||||
{
|
||||
if (_wcsicmp(langName,m_LanguageIDs[idx].name)<=0)
|
||||
break;
|
||||
}
|
||||
if (idx==(int)m_LanguageIDs.size() || _wcsicmp(langName,m_LanguageIDs[idx].name)<0)
|
||||
{
|
||||
LangInfo info;
|
||||
info.id=langId;
|
||||
info.image=ImageList_AddMasked(m_ImageList,bmp,0xFF00FF);
|
||||
info.name=langName;
|
||||
m_LanguageIDs.insert(m_LanguageIDs.begin()+idx,info);
|
||||
|
||||
CWindow list=GetDlgItem(IDC_LISTLANGUAGE);
|
||||
wchar_t name[256];
|
||||
GetLocaleInfo(info.id,LOCALE_SLANGUAGE,name,_countof(name));
|
||||
wchar_t text[256];
|
||||
Sprintf(text,_countof(text),L"%s - %s",info.name,name);
|
||||
LVITEM item={LVIF_IMAGE|LVIF_TEXT};
|
||||
item.iItem=idx;
|
||||
item.iImage=info.image;
|
||||
item.pszText=text;
|
||||
ListView_InsertItem(list,&item);
|
||||
}
|
||||
}
|
||||
|
||||
void CLanguageSettingsDlg::UpdateFlags( void )
|
||||
{
|
||||
// add flags from dlls
|
||||
for (int pass=0;pass<2;pass++)
|
||||
{
|
||||
wchar_t path[_MAX_PATH];
|
||||
if (pass==0)
|
||||
{
|
||||
GetModuleFileName(g_Instance,path,_countof(path));
|
||||
*PathFindFileName(path)=0;
|
||||
}
|
||||
else
|
||||
{
|
||||
Strcpy(path,_countof(path),L"%ALLUSERSPROFILE%\\OpenShell\\Languages");
|
||||
DoEnvironmentSubst(path,_countof(path));
|
||||
}
|
||||
|
||||
wchar_t find[_MAX_PATH];
|
||||
Sprintf(find,_countof(find),L"%s\\*.dll",path);
|
||||
WIN32_FIND_DATA data;
|
||||
HANDLE h=FindFirstFile(find,&data);
|
||||
while (h!=INVALID_HANDLE_VALUE)
|
||||
{
|
||||
if (!(data.dwFileAttributes&FILE_ATTRIBUTE_DIRECTORY) && wcschr(data.cFileName,'-'))
|
||||
{
|
||||
wchar_t fname[_MAX_PATH];
|
||||
Sprintf(fname,_countof(fname),L"%s\\%s",path,data.cFileName);
|
||||
wchar_t language[_MAX_PATH];
|
||||
Strcpy(language,_countof(language),data.cFileName);
|
||||
PathRemoveExtension(language);
|
||||
|
||||
bool bFound=false;
|
||||
for (std::vector<LangInfo>::const_iterator it=m_LanguageIDs.begin();it!=m_LanguageIDs.end();++it)
|
||||
{
|
||||
if (_wcsicmp(it->name,language)==0)
|
||||
{
|
||||
bFound=true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
int langId=0;
|
||||
if (!bFound && GetLocaleInfoEx(language,LOCALE_ILANGUAGE|LOCALE_RETURN_NUMBER,(LPWSTR)&langId,4))
|
||||
{
|
||||
HINSTANCE hModule=LoadLibraryEx(fname,NULL,LOAD_LIBRARY_AS_DATAFILE|LOAD_LIBRARY_AS_IMAGE_RESOURCE);
|
||||
if (hModule)
|
||||
{
|
||||
HBITMAP bmp;
|
||||
if (m_bLargeFlags)
|
||||
bmp=(HBITMAP)LoadImage(hModule,MAKEINTRESOURCE(1),IMAGE_BITMAP,32,16,LR_CREATEDIBSECTION);
|
||||
else
|
||||
bmp=(HBITMAP)LoadImage(hModule,MAKEINTRESOURCE(2),IMAGE_BITMAP,24,11,LR_CREATEDIBSECTION);
|
||||
if (bmp)
|
||||
{
|
||||
AddFlag(language,langId,bmp);
|
||||
DeleteObject(bmp);
|
||||
}
|
||||
FreeLibrary(hModule);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!FindNextFile(h,&data))
|
||||
{
|
||||
FindClose(h);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
LRESULT CLanguageSettingsDlg::OnInitDialog( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled )
|
||||
{
|
||||
m_bLocked=false;
|
||||
InitResize();
|
||||
EnableThemeDialogTexture(m_hWnd,ETDT_ENABLETAB);
|
||||
|
||||
CWindow list=GetDlgItem(IDC_LISTLANGUAGE);
|
||||
if (IsAppThemed())
|
||||
SetWindowTheme(list,L"Explorer",NULL);
|
||||
HBITMAP bmp;
|
||||
HDC hdc=::GetDC(NULL);
|
||||
int dpi=GetDeviceCaps(hdc,LOGPIXELSY);
|
||||
::ReleaseDC(NULL,hdc);
|
||||
m_bLargeFlags=dpi>=144;
|
||||
if (m_bLargeFlags)
|
||||
{
|
||||
m_ImageList=ImageList_Create(32,16,ILC_COLOR24|ILC_MASK|(IsLanguageRTL()?ILC_MIRROR:0),0,0);
|
||||
bmp=(HBITMAP)LoadImage(_AtlBaseModule.GetResourceInstance(),MAKEINTRESOURCE(IDB_FLAGS24),IMAGE_BITMAP,0,0,LR_CREATEDIBSECTION);
|
||||
}
|
||||
else
|
||||
{
|
||||
m_ImageList=ImageList_Create(24,11,ILC_COLOR24|ILC_MASK|(IsLanguageRTL()?ILC_MIRROR:0),0,0);
|
||||
bmp=(HBITMAP)LoadImage(_AtlBaseModule.GetResourceInstance(),MAKEINTRESOURCE(IDB_FLAGS),IMAGE_BITMAP,0,0,LR_CREATEDIBSECTION);
|
||||
}
|
||||
ImageList_AddMasked(m_ImageList,bmp,0xFF00FF);
|
||||
DeleteObject(bmp);
|
||||
ListView_SetImageList(list,m_ImageList,LVSIL_SMALL);
|
||||
RECT rc;
|
||||
list.GetWindowRect(&rc);
|
||||
ListView_SetExtendedListViewStyleEx(list,LVS_EX_DOUBLEBUFFER,LVS_EX_DOUBLEBUFFER);
|
||||
LVCOLUMN column={LVCF_WIDTH,0,rc.right-rc.left};
|
||||
ListView_InsertColumn(list,0,&column);
|
||||
|
||||
m_LanguageIDs.resize(_countof(g_LanguageIDs)+1);
|
||||
{
|
||||
wchar_t languages[100]={0};
|
||||
ULONG size=0;
|
||||
ULONG len=_countof(languages);
|
||||
GetUserPreferredUILanguages(MUI_LANGUAGE_ID,&size,languages,&len);
|
||||
wchar_t *end;
|
||||
m_LanguageIDs[0].id=wcstol(languages,&end,16);
|
||||
m_LanguageIDs[0].image=I_IMAGENONE;
|
||||
}
|
||||
|
||||
for (int i=0;i<=(int)_countof(g_LanguageIDs);i++)
|
||||
{
|
||||
if (i>0)
|
||||
{
|
||||
m_LanguageIDs[i].id=g_LanguageIDs[i-1];
|
||||
m_LanguageIDs[i].image=i-1;
|
||||
}
|
||||
wchar_t name[256];
|
||||
GetLocaleInfo(m_LanguageIDs[i].id,LOCALE_SNAME,name,_countof(name));
|
||||
m_LanguageIDs[i].name=name;
|
||||
}
|
||||
|
||||
std::sort(m_LanguageIDs.begin()+1,m_LanguageIDs.end());
|
||||
|
||||
LVITEM item={LVIF_IMAGE|LVIF_TEXT};
|
||||
for (int i=0;i<(int)m_LanguageIDs.size();i++)
|
||||
{
|
||||
wchar_t name[256];
|
||||
GetLocaleInfo(m_LanguageIDs[i].id,LOCALE_SLANGUAGE,name,_countof(name));
|
||||
wchar_t text[256];
|
||||
if (i==0)
|
||||
Sprintf(text,_countof(text),L"%s (%s)",LoadStringEx(IDS_OS_LANGUAGE),m_LanguageIDs[i].name);
|
||||
else
|
||||
Sprintf(text,_countof(text),L"%s - %s",m_LanguageIDs[i].name,name);
|
||||
item.iItem=i;
|
||||
item.iImage=m_LanguageIDs[i].image;
|
||||
item.pszText=text;
|
||||
ListView_InsertItem(list,&item);
|
||||
}
|
||||
|
||||
UpdateFlags();
|
||||
|
||||
m_Tooltip.Create(TOOLTIPS_CLASS,m_hWnd,NULL,NULL,WS_POPUP|TTS_NOPREFIX);
|
||||
TOOLINFO tool={sizeof(tool),TTF_SUBCLASS|TTF_IDISHWND,m_hWnd,'CLSH'};
|
||||
tool.uId=(UINT_PTR)list.m_hWnd;
|
||||
tool.lpszText=(LPWSTR)L"";
|
||||
m_Tooltip.SendMessage(TTM_ADDTOOL,0,(LPARAM)&tool);
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
LRESULT CLanguageSettingsDlg::OnDestroy( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled )
|
||||
{
|
||||
m_Tooltip.Detach();
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CLanguageSettingsDlg::OnSize( UINT uMsg, WPARAM wParam, LPARAM lParam, BOOL& bHandled )
|
||||
{
|
||||
CResizeableDlg<CLanguageSettingsDlg>::OnSize();
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CLanguageSettingsDlg::OnSelChange( int idCtrl, LPNMHDR pnmh, BOOL& bHandled )
|
||||
{
|
||||
// set setting
|
||||
CWindow list=GetDlgItem(IDC_LISTLANGUAGE);
|
||||
int idx=ListView_GetNextItem(list,-1,LVNI_SELECTED);
|
||||
if (idx<0) return 0;
|
||||
|
||||
const wchar_t *name=idx>0?m_LanguageIDs[idx].name.GetString():L"";
|
||||
CSettingsLockWrite lock;
|
||||
CComVariant val(name);
|
||||
if (m_pSetting->value!=val)
|
||||
SetSettingsDirty();
|
||||
m_pSetting->value=std::move(val);
|
||||
|
||||
if (_wcsicmp(m_pSetting->value.bstrVal,m_pSetting->defValue.bstrVal)==0)
|
||||
m_pSetting->flags|=CSetting::FLAG_DEFAULT;
|
||||
else
|
||||
m_pSetting->flags&=~CSetting::FLAG_DEFAULT;
|
||||
return 0;
|
||||
}
|
||||
|
||||
LRESULT CLanguageSettingsDlg::OnSelChanging( int idCtrl, LPNMHDR pnmh, BOOL& bHandled )
|
||||
{
|
||||
return m_bLocked?TRUE:FALSE;
|
||||
}
|
||||
|
||||
LRESULT CLanguageSettingsDlg::OnCustomDraw( int idCtrl, LPNMHDR pnmh, BOOL& bHandled )
|
||||
{
|
||||
NMLVCUSTOMDRAW *pDraw=(NMLVCUSTOMDRAW*)pnmh;
|
||||
if (!m_bLocked)
|
||||
{
|
||||
bHandled=FALSE;
|
||||
return 0;
|
||||
}
|
||||
if (pDraw->nmcd.dwDrawStage==CDDS_PREPAINT)
|
||||
return CDRF_NOTIFYITEMDRAW;
|
||||
if (pDraw->nmcd.dwDrawStage!=CDDS_ITEMPREPAINT)
|
||||
{
|
||||
bHandled=FALSE;
|
||||
return 0;
|
||||
}
|
||||
pDraw->clrTextBk=GetSysColor(COLOR_BTNFACE);
|
||||
return CDRF_DODEFAULT;
|
||||
}
|
||||
|
||||
static HRESULT CALLBACK TaskDialogCallbackProc( HWND hwnd, UINT uNotification, WPARAM wParam, LPARAM lParam, LONG_PTR dwRefData )
|
||||
{
|
||||
if (uNotification==TDN_HYPERLINK_CLICKED)
|
||||
{
|
||||
ShellExecute(hwnd,L"open",(const wchar_t*)lParam,NULL,NULL,SW_SHOWNORMAL);
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
void CLanguageSettingsDlg::SetGroup( CSetting *pGroup )
|
||||
{
|
||||
m_bLocked=false;
|
||||
m_pSetting=pGroup+1;
|
||||
|
||||
const wchar_t *language=L"";
|
||||
if (m_pSetting->value.vt==VT_BSTR && m_pSetting->value.bstrVal)
|
||||
language=m_pSetting->value.bstrVal;
|
||||
int len=Strlen(language);
|
||||
|
||||
CWindow list=GetDlgItem(IDC_LISTLANGUAGE);
|
||||
for (int idx=0;idx<(int)m_LanguageIDs.size();idx++)
|
||||
{
|
||||
const wchar_t *name=idx>0?m_LanguageIDs[idx].name.GetString():L"";
|
||||
if (_wcsicmp(language,name)==0)
|
||||
{
|
||||
ListView_SetItemState(list,idx,LVIS_SELECTED|LVIS_FOCUSED,LVIS_SELECTED|LVIS_FOCUSED);
|
||||
ListView_EnsureVisible(list,idx,FALSE);
|
||||
break;
|
||||
}
|
||||
}
|
||||
m_bLocked=m_pSetting->IsLocked();
|
||||
|
||||
TOOLINFO tool={sizeof(tool),0,m_hWnd,'CLSH'};
|
||||
tool.uId=(UINT_PTR)list.m_hWnd;
|
||||
CString str;
|
||||
if (m_bLocked)
|
||||
str=LoadStringEx(IDS_SETTING_LOCKED);
|
||||
tool.lpszText=(LPWSTR)(LPCWSTR)str;
|
||||
m_Tooltip.SendMessage(TTM_UPDATETIPTEXT,0,(LPARAM)&tool);
|
||||
ListView_SetBkColor(list,GetSysColor(m_bLocked?COLOR_BTNFACE:COLOR_WINDOW));
|
||||
}
|
||||
|
||||
class CLanguageSettingsPanel: public ISettingsPanel
|
||||
{
|
||||
public:
|
||||
CLanguageSettingsPanel( TSettingsComponent component ) { s_Dialog.SetComponent(component); }
|
||||
virtual HWND Create( HWND parent );
|
||||
virtual HWND Activate( CSetting *pGroup, const RECT &rect, bool bReset );
|
||||
virtual bool Validate( HWND parent ) { return true; }
|
||||
|
||||
private:
|
||||
static CLanguageSettingsDlg s_Dialog;
|
||||
};
|
||||
|
||||
CLanguageSettingsDlg CLanguageSettingsPanel::s_Dialog;
|
||||
|
||||
ISettingsPanel *GetLanguageSettings( TSettingsComponent component )
|
||||
{
|
||||
static CLanguageSettingsPanel panel(component);
|
||||
return &panel;
|
||||
}
|
||||
|
||||
HWND CLanguageSettingsPanel::Create( HWND parent )
|
||||
{
|
||||
if (!s_Dialog.m_hWnd)
|
||||
s_Dialog.Create(parent,LoadDialogEx(IDD_LANGUAGE));
|
||||
return s_Dialog.m_hWnd;
|
||||
}
|
||||
|
||||
HWND CLanguageSettingsPanel::Activate( CSetting *pGroup, const RECT &rect, bool bReset )
|
||||
{
|
||||
s_Dialog.SetGroup(pGroup);
|
||||
s_Dialog.SetWindowPos(HWND_TOP,&rect,SWP_SHOWWINDOW);
|
||||
return s_Dialog.m_hWnd;
|
||||
}
|
||||
12
Src/Lib/LanguageSettingsHelper.h
Normal file
@@ -0,0 +1,12 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
class ISettingsPanel;
|
||||
|
||||
extern int g_LanguageIDs[];
|
||||
extern int g_LanguageIDCount;
|
||||
|
||||
ISettingsPanel *GetLanguageSettings( TSettingsComponent component );
|
||||
315
Src/Lib/Lib.rc
Normal file
@@ -0,0 +1,315 @@
|
||||
// Microsoft Visual C++ generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
#define APSTUDIO_READONLY_SYMBOLS
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#include "winres.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
|
||||
#ifdef _WIN32
|
||||
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
|
||||
#pragma code_page(1252)
|
||||
#endif //_WIN32
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#include ""afxres.h""\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Dialog
|
||||
//
|
||||
|
||||
IDD_SETTINGSTREE DIALOGEX 0, 0, 350, 160
|
||||
STYLE DS_SETFONT | DS_CONTROL | WS_CHILD | WS_SYSMENU
|
||||
FONT 9, "Segoe UI", 400, 0, 0x0
|
||||
BEGIN
|
||||
CONTROL "",IDC_SETTINGS,"SysTreeView32",TVS_DISABLEDRAGDROP | TVS_INFOTIP | WS_BORDER | WS_HSCROLL | WS_TABSTOP,7,7,336,126
|
||||
LTEXT "The settings that are modified from the default will show in bold\r\nRight-click on a setting for more functions",IDC_STATICTIP,7,135,336,18
|
||||
END
|
||||
|
||||
IDD_SETTINGS DIALOGEX 0, 0, 381, 213
|
||||
STYLE DS_SETFONT | DS_SETFOREGROUND | DS_CENTER | WS_MINIMIZEBOX | WS_MAXIMIZEBOX | WS_POPUP | WS_CLIPCHILDREN | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME
|
||||
EXSTYLE WS_EX_CONTROLPARENT
|
||||
CAPTION "Settings"
|
||||
FONT 9, "Segoe UI", 400, 0, 0x0
|
||||
BEGIN
|
||||
ICON "",IDC_ICONSEARCH,7,9,20,20
|
||||
EDITTEXT IDC_EDITSEARCH,22,7,120,12,ES_AUTOHSCROLL
|
||||
CONTROL "Show all settings",IDC_CHECKALL,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,154,7,79,12
|
||||
CONTROL "<a>Help...</a>",IDC_LINKHELP,"SysLink",WS_TABSTOP,348,9,26,10,WS_EX_TRANSPARENT
|
||||
CONTROL "",IDC_TABSETTINGS,"SysTabControl32",TCS_MULTILINE | TCS_FOCUSNEVER,7,20,367,169
|
||||
CONTROL "<a>Open-Shell Homepage</a>",IDC_LINKWEB,"SysLink",WS_TABSTOP,7,195,75,10,WS_EX_TRANSPARENT
|
||||
CONTROL "Name of translator goes <a href=""http://www.yoursite.com"">here</a>",IDC_SYSLINKLOC,
|
||||
"SysLink",NOT WS_VISIBLE | WS_TABSTOP,80,195,111,10
|
||||
PUSHBUTTON "&Backup",IDC_BUTTONBACKUP,200,192,60,14,WS_GROUP
|
||||
DEFPUSHBUTTON "OK",IDOK,267,192,50,14
|
||||
PUSHBUTTON "Cancel",IDCANCEL,324,192,50,14
|
||||
END
|
||||
|
||||
IDD_BROWSEFORICON DIALOGEX 0, 0, 317, 183
|
||||
STYLE DS_SETFONT | WS_POPUP | WS_CLIPCHILDREN | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME
|
||||
CAPTION "Select Icon"
|
||||
FONT 9, "Segoe UI", 400, 0, 0x0
|
||||
BEGIN
|
||||
LTEXT "File:",IDC_STATICFILE,7,7,19,14,SS_CENTERIMAGE
|
||||
EDITTEXT IDC_EDITFILE,33,7,260,14,ES_AUTOHSCROLL
|
||||
PUSHBUTTON "...",IDC_BUTTONBROWSE,294,7,16,14
|
||||
CONTROL "",IDC_LISTICONS,"SysListView32",LVS_SINGLESEL | LVS_SHOWSELALWAYS | LVS_AUTOARRANGE | LVS_ALIGNLEFT | WS_BORDER | WS_TABSTOP,7,26,303,132
|
||||
DEFPUSHBUTTON "OK",IDOK,205,162,50,14
|
||||
PUSHBUTTON "Cancel",IDCANCEL,260,162,50,14
|
||||
END
|
||||
|
||||
IDD_LANGUAGE DIALOGEX 0, 0, 316, 144
|
||||
STYLE DS_SETFONT | DS_CONTROL | WS_CHILD | WS_CLIPCHILDREN | WS_SYSMENU
|
||||
FONT 9, "Segoe UI", 400, 0, 0x0
|
||||
BEGIN
|
||||
CONTROL "",IDC_LISTLANGUAGE,"SysListView32",LVS_REPORT | LVS_SINGLESEL | LVS_SHOWSELALWAYS | LVS_ALIGNLEFT | LVS_NOCOLUMNHEADER | LVS_NOSORTHEADER | WS_BORDER | WS_TABSTOP,7,18,302,99
|
||||
LTEXT "Select a language for the user interface:",IDC_STATICHINT,7,7,131,8
|
||||
END
|
||||
|
||||
IDD_CUSTOMTREE DIALOGEX 0, 0, 365, 183
|
||||
STYLE DS_SETFONT | DS_CONTROL | WS_CHILD | WS_CLIPCHILDREN | WS_SYSMENU
|
||||
FONT 9, "Segoe UI", 400, 0, 0x0
|
||||
BEGIN
|
||||
LTEXT "Current toolbar items:",IDC_STATICLEFT,7,7,167,8
|
||||
CONTROL "",IDC_TREEITEMS,"SysTreeView32",TVS_HASBUTTONS | TVS_HASLINES | TVS_LINESATROOT | TVS_EDITLABELS | TVS_SHOWSELALWAYS | TVS_INFOTIP | WS_BORDER | WS_HSCROLL | WS_TABSTOP,7,16,167,139
|
||||
LTEXT "Available commands:",IDC_STATICRIGHT,193,7,100,8
|
||||
CONTROL "",IDC_TREECOMMANDS,"SysTreeView32",TVS_SHOWSELALWAYS | TVS_INFOTIP | WS_BORDER | WS_HSCROLL | WS_TABSTOP,191,16,167,139
|
||||
LTEXT "<<",IDC_STATICMIDDLE,177,77,11,8
|
||||
LTEXT "Drag items from the right column to the left. Double-click to edit. Right-click for more functions",IDC_STATICHINT,7,159,351,17
|
||||
END
|
||||
|
||||
IDD_PROGRESS DIALOGEX 0, 0, 209, 63
|
||||
STYLE DS_SETFONT | DS_MODALFRAME | DS_CENTER | WS_POPUP | WS_CAPTION
|
||||
CAPTION "Dialog"
|
||||
FONT 9, "Segoe UI", 400, 0, 0x0
|
||||
BEGIN
|
||||
PUSHBUTTON "Cancel",IDCANCEL,152,42,50,14
|
||||
CONTROL "",IDC_PROGRESS,"msctls_progress32",WS_BORDER,7,20,195,14
|
||||
LTEXT "Static",IDC_MESSAGE,7,7,195,12
|
||||
END
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// DESIGNINFO
|
||||
//
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
GUIDELINES DESIGNINFO
|
||||
BEGIN
|
||||
IDD_SETTINGSTREE, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 343
|
||||
TOPMARGIN, 7
|
||||
BOTTOMMARGIN, 153
|
||||
END
|
||||
|
||||
IDD_SETTINGS, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 374
|
||||
TOPMARGIN, 7
|
||||
BOTTOMMARGIN, 206
|
||||
END
|
||||
|
||||
IDD_BROWSEFORICON, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 310
|
||||
TOPMARGIN, 7
|
||||
BOTTOMMARGIN, 176
|
||||
END
|
||||
|
||||
IDD_LANGUAGE, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 309
|
||||
TOPMARGIN, 7
|
||||
BOTTOMMARGIN, 137
|
||||
END
|
||||
|
||||
IDD_CUSTOMTREE, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 358
|
||||
TOPMARGIN, 7
|
||||
BOTTOMMARGIN, 176
|
||||
END
|
||||
|
||||
IDD_PROGRESS, DIALOG
|
||||
BEGIN
|
||||
LEFTMARGIN, 7
|
||||
RIGHTMARGIN, 202
|
||||
TOPMARGIN, 7
|
||||
BOTTOMMARGIN, 56
|
||||
END
|
||||
END
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Icon
|
||||
//
|
||||
|
||||
// Icon with lowest ID value placed first to ensure application icon
|
||||
// remains consistent on all systems.
|
||||
IDI_ICONLOCK ICON "padlock.ico"
|
||||
IDI_ICONPLAY ICON "play.ico"
|
||||
IDI_ICONWARNING ICON "warning.ico"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Bitmap
|
||||
//
|
||||
|
||||
IDB_FLAGS BITMAP "flags.bmp"
|
||||
IDB_FLAGS24 BITMAP "flags24.bmp"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// String Table
|
||||
//
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_TOGGLE_SETTING "Toggle Setting\tSpace"
|
||||
IDS_SELECT_SETTING "Select Setting\tSpace"
|
||||
IDS_DEFAULT_SETTING "Set Default\tCtrl+Space"
|
||||
IDS_PLAY_SETTING "Play Sound\tCtrl+P"
|
||||
IDS_ICON_FILTERS "Icon files (*.ico, *.dll, *.exe)|*.ico;*.dll;*.exe|ICO files (*.ico)|*.ico|DLL files (*.dll)|*.dll|EXE files (*.exe)|*.exe|All Files (*.*)|*.*|"
|
||||
IDS_ICON_TITLE "Select Source File"
|
||||
IDS_WAV_FILTERS "WAV files (*.wav)|*.wav|"
|
||||
IDS_WAV_TITLE "Select Sound File"
|
||||
IDS_SETTING_LOCKED "This setting has been locked by the administrator"
|
||||
IDS_SETTING_LOCKED_GP "This setting has been locked by a group policy"
|
||||
IDS_BASIC_SETTINGS "Basic Settings"
|
||||
IDS_ALWAYS_ON_TOP "&Always on Top"
|
||||
IDS_MENU_EDIT "Edit Item"
|
||||
IDS_MENU_DELETE "Delete Item"
|
||||
IDS_MENU_RENAME "Rename Item"
|
||||
IDS_PICK_LINK_TITLE "Select a file or a folder"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_PICK_LINK_FILE "Select File"
|
||||
IDS_PICK_LINK_FOLDER "Select Folder"
|
||||
IDS_DUPLICATE_ITEM "Item named '%s' already exists."
|
||||
IDS_ERROR_TITLE "Error"
|
||||
IDS_ERROR_SEPARATOR "The item name cannot be '%s'."
|
||||
IDS_ERROR_ASCII "This is an internal name of the item and must contain only English letters and numbers. Use the Text and Tip properties to enter the visible text."
|
||||
IDS_ERROR_EMPTY "The item name cannot be empty."
|
||||
IDS_RESET_TOOLBAR "Reset Toolbar"
|
||||
IDS_RESET_TOOLBAR_WARN "Are you sure you want to reset all toolbar buttons?"
|
||||
IDS_RESET_MENU "Reset Start Menu"
|
||||
IDS_RESET_MENU_WARN "Are you sure you want to reset the whole start menu?"
|
||||
IDS_ADD_TOOLBAR "Add to Toolbar"
|
||||
IDS_ADD_MENU "Add to Menu"
|
||||
IDS_INSERT_MENU "Create sub-menu"
|
||||
IDS_EMPTY_MENU "<empty menu>"
|
||||
IDS_TREE_TOOLBAR "Current toolbar buttons:"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_TREE_MENU "Current menu items:"
|
||||
IDS_XML_FILTERS "XML files (*.xml)|*.xml|"
|
||||
IDS_XML_TITLE_LOAD "Load XML File"
|
||||
IDS_XML_TITLE_SAVE "Save XML File"
|
||||
IDS_RESET_CONFIRM "Are you sure you want to reset all settings?"
|
||||
IDS_RESET_TITLE "Reset All Settings"
|
||||
IDS_TOOLBAR_LOCKED "The toolbar is locked by the administrator"
|
||||
IDS_MENU_LOCKED "The start menu is locked by the administrator"
|
||||
IDS_BACKUP_SAVE "Save to XML File..."
|
||||
IDS_BACKUP_LOAD "Load from XML File..."
|
||||
IDS_BACKUP_RESET "Reset all settings"
|
||||
IDS_ERROR_LOADING_XML "Error loading XML file '%s'."
|
||||
IDS_ERROR_SAVING_XML "Error saving XML file '%s'."
|
||||
IDS_DRAG_DROP_EXP_TIP "Drag buttons from the right column to the left. You can drop on top of a button to create a sub-menu.\nDouble-click in the left column to edit the button. Right-click for more functions."
|
||||
IDS_DRAG_DROP_SM_TIP "Drag menu items from the right column to the left. You can drop on top of a menu item to create a sub-menu.\nDouble-click in the left column to edit the item. Right-click for more functions."
|
||||
IDS_COMMAND_EXP_TIP "Drag the command or double-click on it to add it to the toolbar"
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_COMMAND_SM_TIP "Drag the command or double-click on it to add it to the start menu"
|
||||
IDS_COMMAND_FILTERS "Programs (*.exe, *.com, *.pif, *.bat, *.cmd)|*.exe;*.com;*.pif;*.bat;*.cmd|All files (*.*)|*.*|"
|
||||
IDS_OS_LANGUAGE "Current OS language"
|
||||
IDS_BMP_FILTERS "Image files (*.bmp,*.png)|*.bmp;*.png|"
|
||||
IDS_BMP_TITLE "Select Image File"
|
||||
IDS_SEARCH_PROMPT "Search Settings"
|
||||
IDS_SETTING_SEARCH "Search Results"
|
||||
IDS_WEBSITE_TIP "Visit Open-Shell on the web - https://open-shell.github.io/Open-Shell-Menu"
|
||||
IDS_LOCATE_SETTING "Locate setting"
|
||||
IDS_INTERNET_FAIL "Failed to connect to the Internet."
|
||||
END
|
||||
|
||||
STRINGTABLE
|
||||
BEGIN
|
||||
IDS_INITIATE_FAIL "Failed to initiate the download."
|
||||
IDS_UPDATE_TITLE "Open-Shell Update"
|
||||
IDS_INST_DOWNLOAD_FAIL "Failed to download the new version."
|
||||
IDS_INST_SAVE_FAIL "Failed to save file '%s'."
|
||||
IDS_PROGRESS_CONNECT "Connecting..."
|
||||
IDS_PROGRESS_DOWNLOAD "Downloading..."
|
||||
IDS_PROGRESS_VERIFY "Verifying..."
|
||||
IDS_PROGRESS_SAVE "Saving..."
|
||||
IDS_PROGRESS_TITLE_CHECK "Checking for updates"
|
||||
IDS_PROGRESS_TITLE_DOWNLOAD "Downloading update"
|
||||
IDS_DOWNLOAD_TIP "You can try getting the file directly from the website:"
|
||||
IDS_BMP_FILTERS2 "Image files (*.bmp,*.png,*.jpg)|*.bmp;*.png;*.jpg|"
|
||||
IDS_UNSAVED_CHANGES "Do you want to save your changes to the settings?"
|
||||
IDS_UNSAVED_TITLE "Unsaved changes"
|
||||
END
|
||||
|
||||
#endif // English (U.S.) resources
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
#ifndef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 3 resource.
|
||||
//
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#endif // not APSTUDIO_INVOKED
|
||||
|
||||
117
Src/Lib/Lib.vcxproj
Normal file
@@ -0,0 +1,117 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|x64">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|x64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<ProjectGuid>{D42FE717-485B-492D-884A-1999F6D51154}</ProjectGuid>
|
||||
<RootNamespace>Lib</RootNamespace>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Label="Configuration">
|
||||
<ConfigurationType>StaticLibrary</ConfigurationType>
|
||||
<PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>
|
||||
<UseOfAtl>Static</UseOfAtl>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<WholeProgramOptimization Condition="'$(Configuration)'!='Debug'">true</WholeProgramOptimization>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets">
|
||||
<Import Project="..\Common.props" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup>
|
||||
<OutDir>$(IntDir)</OutDir>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup>
|
||||
<ClCompile>
|
||||
<PreprocessorDefinitions>_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ClCompile>
|
||||
<Lib>
|
||||
<TargetMachine Condition="'$(Platform)'=='Win32'">MachineX86</TargetMachine>
|
||||
</Lib>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<Image Include="..\Setup\OpenShell.ico" />
|
||||
<Image Include="flags.bmp" />
|
||||
<Image Include="flags24.bmp" />
|
||||
<Image Include="padlock.ico" />
|
||||
<Image Include="play.ico" />
|
||||
<Image Include="warning.ico" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="Lib.rc" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="Assert.h" />
|
||||
<ClInclude Include="ComHelper.h" />
|
||||
<ClInclude Include="DownloadHelper.h" />
|
||||
<ClInclude Include="FileHelper.h" />
|
||||
<ClInclude Include="FNVHash.h" />
|
||||
<ClInclude Include="IatHookHelper.h" />
|
||||
<ClInclude Include="LanguageSettingsHelper.h" />
|
||||
<ClInclude Include="resource.h" />
|
||||
<ClInclude Include="ResourceHelper.h" />
|
||||
<ClInclude Include="Settings.h" />
|
||||
<ClInclude Include="SettingsParser.h" />
|
||||
<ClInclude Include="SettingsUIHelper.h" />
|
||||
<ClInclude Include="stdafx.h" />
|
||||
<ClInclude Include="StringSet.h" />
|
||||
<ClInclude Include="StringUtils.h" />
|
||||
<ClInclude Include="targetver.h" />
|
||||
<ClInclude Include="TrackResources.h" />
|
||||
<ClInclude Include="Translations.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="Assert.cpp" />
|
||||
<ClCompile Include="DownloadHelper.cpp" />
|
||||
<ClCompile Include="FileHelper.cpp" />
|
||||
<ClCompile Include="FNVHash.cpp" />
|
||||
<ClCompile Include="IatHookHelper.cpp" />
|
||||
<ClCompile Include="Instance.cpp" />
|
||||
<ClCompile Include="LanguageSettingsHelper.cpp" />
|
||||
<ClCompile Include="ResourceHelper.cpp" />
|
||||
<ClCompile Include="Settings.cpp" />
|
||||
<ClCompile Include="SettingsParser.cpp" />
|
||||
<ClCompile Include="SettingsUIHelper.cpp" />
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<PrecompiledHeader>Create</PrecompiledHeader>
|
||||
</ClCompile>
|
||||
<ClCompile Include="StringSet.cpp" />
|
||||
<ClCompile Include="StringUtils.cpp" />
|
||||
<ClCompile Include="TrackResources.cpp" />
|
||||
<ClCompile Include="Translations.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="packages.config" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
<Import Project="..\packages\nlohmann.json.3.11.2\build\native\nlohmann.json.targets" Condition="Exists('..\packages\nlohmann.json.3.11.2\build\native\nlohmann.json.targets')" />
|
||||
</ImportGroup>
|
||||
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
|
||||
<PropertyGroup>
|
||||
<ErrorText>This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
|
||||
</PropertyGroup>
|
||||
<Error Condition="!Exists('..\packages\nlohmann.json.3.11.2\build\native\nlohmann.json.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\nlohmann.json.3.11.2\build\native\nlohmann.json.targets'))" />
|
||||
</Target>
|
||||
</Project>
|
||||
155
Src/Lib/Lib.vcxproj.filters
Normal file
@@ -0,0 +1,155 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="Resource Files">
|
||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Strings">
|
||||
<UniqueIdentifier>{2dafcc43-3a9f-4c0e-8d8a-b43c78f07e35}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Resources">
|
||||
<UniqueIdentifier>{48a0589e-ec5e-4ded-b507-ca72c33429c7}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Settings">
|
||||
<UniqueIdentifier>{402c170e-bb90-4637-85b7-98857963160f}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Lib">
|
||||
<UniqueIdentifier>{40e914e4-1c35-4b97-a4f6-15dce5ff5b20}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Image Include="..\Setup\OpenShell.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="flags.bmp">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="flags24.bmp">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="padlock.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="play.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
<Image Include="warning.ico">
|
||||
<Filter>Resource Files</Filter>
|
||||
</Image>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="Lib.rc">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ResourceCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="resource.h">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Assert.h">
|
||||
<Filter>Strings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="FNVHash.h">
|
||||
<Filter>Strings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="StringSet.h">
|
||||
<Filter>Strings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="StringUtils.h">
|
||||
<Filter>Strings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ComHelper.h">
|
||||
<Filter>Resources</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="FileHelper.h">
|
||||
<Filter>Resources</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="IatHookHelper.h">
|
||||
<Filter>Resources</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="ResourceHelper.h">
|
||||
<Filter>Resources</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="TrackResources.h">
|
||||
<Filter>Resources</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="DownloadHelper.h">
|
||||
<Filter>Settings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="LanguageSettingsHelper.h">
|
||||
<Filter>Settings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Settings.h">
|
||||
<Filter>Settings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="SettingsParser.h">
|
||||
<Filter>Settings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="SettingsUIHelper.h">
|
||||
<Filter>Settings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="Translations.h">
|
||||
<Filter>Settings</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="stdafx.h">
|
||||
<Filter>Lib</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="targetver.h">
|
||||
<Filter>Lib</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="Assert.cpp">
|
||||
<Filter>Strings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="FNVHash.cpp">
|
||||
<Filter>Strings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="StringSet.cpp">
|
||||
<Filter>Strings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="StringUtils.cpp">
|
||||
<Filter>Strings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="FileHelper.cpp">
|
||||
<Filter>Resources</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="IatHookHelper.cpp">
|
||||
<Filter>Resources</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Instance.cpp">
|
||||
<Filter>Resources</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="ResourceHelper.cpp">
|
||||
<Filter>Resources</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="TrackResources.cpp">
|
||||
<Filter>Resources</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="DownloadHelper.cpp">
|
||||
<Filter>Settings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="LanguageSettingsHelper.cpp">
|
||||
<Filter>Settings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Settings.cpp">
|
||||
<Filter>Settings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="SettingsParser.cpp">
|
||||
<Filter>Settings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="SettingsUIHelper.cpp">
|
||||
<Filter>Settings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="Translations.cpp">
|
||||
<Filter>Settings</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<Filter>Lib</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="packages.config" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
952
Src/Lib/ResourceHelper.cpp
Normal file
@@ -0,0 +1,952 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "StringSet.h"
|
||||
#include "StringUtils.h"
|
||||
#include "Settings.h"
|
||||
#include "Translations.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "Assert.h"
|
||||
#include <vector>
|
||||
#include <wincodec.h>
|
||||
#include "TrackResources.h"
|
||||
|
||||
static CStringSet g_ResStrings;
|
||||
static std::map<int,std::vector<char> > g_ResDialogs;
|
||||
|
||||
// Loads all strings and dialogs from hLngInstance
|
||||
// pDialogs is a NULL-terminated list of dialog IDs. They are loaded from hLngInstance if possible, otherwise from g_Instance
|
||||
void LoadTranslationResources( HINSTANCE hLngInstance, int *pDialogs )
|
||||
{
|
||||
Assert(g_Instance);
|
||||
DWORD lngVersion=0;
|
||||
if (hLngInstance)
|
||||
{
|
||||
LoadTranslationOverrides(hLngInstance);
|
||||
g_ResStrings.Init(hLngInstance);
|
||||
lngVersion=GetVersionEx(hLngInstance);
|
||||
}
|
||||
if (!pDialogs)
|
||||
return;
|
||||
for (int i=0;pDialogs[i];i+=2)
|
||||
{
|
||||
int dlgId=pDialogs[i];
|
||||
DWORD dlgVersion=pDialogs[i+1];
|
||||
HINSTANCE hInst=hLngInstance;
|
||||
HRSRC hrsrc=NULL;
|
||||
if (hLngInstance && lngVersion>=dlgVersion)
|
||||
hrsrc=FindResource(hInst,MAKEINTRESOURCE(dlgId),RT_DIALOG);
|
||||
if (!hrsrc)
|
||||
{
|
||||
hInst=g_Instance;
|
||||
hrsrc=FindResource(hInst,MAKEINTRESOURCE(dlgId),RT_DIALOG);
|
||||
}
|
||||
if (hrsrc)
|
||||
{
|
||||
HGLOBAL hglb=LoadResource(hInst,hrsrc);
|
||||
if (hglb)
|
||||
{
|
||||
// finally lock the resource
|
||||
LPVOID res=LockResource(hglb);
|
||||
std::vector<char> &dlg=g_ResDialogs[dlgId];
|
||||
dlg.resize(SizeofResource(hInst,hrsrc));
|
||||
if (!dlg.empty())
|
||||
memcpy(&dlg[0],res,dlg.size());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Loads the best DLL for the current language
|
||||
HINSTANCE LoadTranslationDll( const wchar_t *langSetting )
|
||||
{
|
||||
Assert(g_Instance);
|
||||
CString language=langSetting;
|
||||
wchar_t languages[100]={0};
|
||||
if (!language.IsEmpty())
|
||||
{
|
||||
Strcpy(languages,_countof(languages)-1,language);
|
||||
}
|
||||
else
|
||||
{
|
||||
ULONG size=0;
|
||||
ULONG len=_countof(languages);
|
||||
GetUserPreferredUILanguages(MUI_LANGUAGE_NAME,&size,languages,&len);
|
||||
}
|
||||
|
||||
wchar_t path1[_MAX_PATH];
|
||||
GetModuleFileName(g_Instance,path1,_countof(path1));
|
||||
*PathFindFileName(path1)=0;
|
||||
|
||||
wchar_t path2[_MAX_PATH]=L"%ALLUSERSPROFILE%\\OpenShell\\Languages\\";
|
||||
DoEnvironmentSubst(path2,_countof(path2));
|
||||
|
||||
DWORD curVersion=GetVersionEx(g_Instance);
|
||||
HINSTANCE resInstance=NULL;
|
||||
for (const wchar_t *lang=languages;*lang;lang+=Strlen(lang)+1)
|
||||
{
|
||||
if (_wcsicmp(lang,L"en")==0 || _wcsnicmp(lang,L"en-",3)==0)
|
||||
break; // English
|
||||
wchar_t fname[_MAX_PATH];
|
||||
DWORD ver1=0, ver2=0, build1=0, build2=0;
|
||||
Sprintf(fname,_countof(fname),L"%s%s.dll",path1,lang);
|
||||
HINSTANCE resInstance1=LoadLibraryEx(fname,NULL,LOAD_LIBRARY_AS_DATAFILE|LOAD_LIBRARY_AS_IMAGE_RESOURCE);
|
||||
if (resInstance1)
|
||||
{
|
||||
ver1=GetVersionEx(resInstance1,&build1);
|
||||
if (ver1<MIN_LANGUAGE_VERSION || ver1>curVersion)
|
||||
{
|
||||
ver1=0;
|
||||
FreeLibrary(resInstance1);
|
||||
resInstance1=NULL;
|
||||
}
|
||||
}
|
||||
Sprintf(fname,_countof(fname),L"%s%s.dll",path2,lang);
|
||||
HINSTANCE resInstance2=LoadLibraryEx(fname,NULL,LOAD_LIBRARY_AS_DATAFILE|LOAD_LIBRARY_AS_IMAGE_RESOURCE);
|
||||
if (resInstance2)
|
||||
{
|
||||
ver2=GetVersionEx(resInstance2,&build2);
|
||||
if (ver2<MIN_LANGUAGE_VERSION || ver2>curVersion)
|
||||
{
|
||||
ver2=0;
|
||||
FreeLibrary(resInstance2);
|
||||
resInstance2=NULL;
|
||||
}
|
||||
}
|
||||
if (ver1 || ver2)
|
||||
{
|
||||
if (ver1>ver2 || (ver1==ver2 && build1>build2))
|
||||
{
|
||||
resInstance=resInstance1;
|
||||
if (resInstance2) FreeLibrary(resInstance2);
|
||||
}
|
||||
else
|
||||
{
|
||||
resInstance=resInstance2;
|
||||
if (resInstance1) FreeLibrary(resInstance1);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
return resInstance;
|
||||
}
|
||||
|
||||
// Returns a localized string
|
||||
CString LoadStringEx( int stringID )
|
||||
{
|
||||
CString str=g_ResStrings.GetString(stringID);
|
||||
if (str.IsEmpty())
|
||||
str.LoadString(g_Instance,stringID);
|
||||
return str;
|
||||
}
|
||||
|
||||
CString LoadStringEnglish( int stringID )
|
||||
{
|
||||
CString str;
|
||||
str.LoadString(g_Instance,stringID);
|
||||
return str;
|
||||
}
|
||||
|
||||
// Returns a localized dialog template
|
||||
DLGTEMPLATE *LoadDialogEx( int dlgID )
|
||||
{
|
||||
std::map<int,std::vector<char> >::iterator it=g_ResDialogs.find(dlgID);
|
||||
if (it==g_ResDialogs.end())
|
||||
return NULL;
|
||||
if (it->second.empty())
|
||||
return NULL;
|
||||
return (DLGTEMPLATE*)&it->second[0];
|
||||
}
|
||||
|
||||
// Loads an icon. path can be a path to .ico file, or in the format "module.dll, number"
|
||||
HICON LoadIcon( int iconSize, const wchar_t *path, std::vector<HMODULE> &modules )
|
||||
{
|
||||
wchar_t text[1024];
|
||||
Strcpy(text,_countof(text),path);
|
||||
DoEnvironmentSubst(text,_countof(text));
|
||||
wchar_t *c=wcsrchr(text,',');
|
||||
if (c)
|
||||
{
|
||||
// resource file
|
||||
*c=0;
|
||||
const wchar_t *res=c+1;
|
||||
int idx=_wtol(res);
|
||||
if (idx>0) res=MAKEINTRESOURCE(idx);
|
||||
if (!text[0])
|
||||
return (HICON)LoadImage(_AtlBaseModule.GetResourceInstance(),res,IMAGE_ICON,iconSize,iconSize,LR_DEFAULTCOLOR);
|
||||
HMODULE hMod=GetModuleHandle(PathFindFileName(text));
|
||||
if (!hMod)
|
||||
{
|
||||
hMod=LoadLibraryEx(text,NULL,LOAD_LIBRARY_AS_DATAFILE|LOAD_LIBRARY_AS_IMAGE_RESOURCE);
|
||||
if (!hMod) return NULL;
|
||||
modules.push_back(hMod);
|
||||
}
|
||||
return (HICON)LoadImage(hMod,res,IMAGE_ICON,iconSize,iconSize,LR_DEFAULTCOLOR);
|
||||
}
|
||||
else
|
||||
{
|
||||
return (HICON)LoadImage(NULL,text,IMAGE_ICON,iconSize,iconSize,LR_DEFAULTCOLOR|LR_LOADFROMFILE);
|
||||
}
|
||||
}
|
||||
|
||||
HICON LoadIcon( int iconSize, PIDLIST_ABSOLUTE pidl )
|
||||
{
|
||||
HICON hIcon=NULL;
|
||||
CComPtr<IShellFolder> pFolder;
|
||||
PCITEMID_CHILD child;
|
||||
if (SUCCEEDED(SHBindToParent(pidl,IID_IShellFolder,(void**)&pFolder,&child)))
|
||||
{
|
||||
bool bLarge=(iconSize>GetSystemMetrics(SM_CXSMICON));
|
||||
LONG lSize;
|
||||
if (bLarge)
|
||||
lSize=MAKELONG(iconSize,GetSystemMetrics(SM_CXSMICON));
|
||||
else
|
||||
lSize=MAKELONG(GetSystemMetrics(SM_CXICON),iconSize);
|
||||
CComPtr<IExtractIcon> pExtract;
|
||||
if (SUCCEEDED(pFolder->GetUIObjectOf(NULL,1,&child,IID_IExtractIcon,NULL,(void**)&pExtract)))
|
||||
{
|
||||
// get the icon location
|
||||
wchar_t location[_MAX_PATH];
|
||||
int index=0;
|
||||
UINT flags=0;
|
||||
if (pExtract->GetIconLocation(0,location,_countof(location),&index,&flags)==S_OK)
|
||||
{
|
||||
if (flags&GIL_NOTFILENAME)
|
||||
{
|
||||
// extract the icon
|
||||
HICON hIcon2=NULL;
|
||||
HRESULT hr=pExtract->Extract(location,index,bLarge?&hIcon:&hIcon2,bLarge?&hIcon2:&hIcon,lSize);
|
||||
if (FAILED(hr))
|
||||
hIcon=hIcon2=NULL;
|
||||
if (hr==S_FALSE)
|
||||
flags=0;
|
||||
if (hIcon2) DestroyIcon(hIcon2); // HACK!!! Even though Extract should support NULL, not all implementations do. For example shfusion.dll crashes
|
||||
}
|
||||
if (!(flags&GIL_NOTFILENAME))
|
||||
{
|
||||
if (ExtractIconEx(location,index==-1?0:index,bLarge?&hIcon:NULL,bLarge?NULL:&hIcon,1)!=1)
|
||||
hIcon=NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// try again using the ANSI version
|
||||
CComPtr<IExtractIconA> pExtractA;
|
||||
if (SUCCEEDED(pFolder->GetUIObjectOf(NULL,1,&child,IID_IExtractIconA,NULL,(void**)&pExtractA)))
|
||||
{
|
||||
// get the icon location
|
||||
char location[_MAX_PATH];
|
||||
int index=0;
|
||||
UINT flags=0;
|
||||
if (pExtractA->GetIconLocation(0,location,_countof(location),&index,&flags)==S_OK)
|
||||
{
|
||||
if (flags&GIL_NOTFILENAME)
|
||||
{
|
||||
// extract the icon
|
||||
HICON hIcon2=NULL;
|
||||
HRESULT hr=pExtractA->Extract(location,index,bLarge?&hIcon:&hIcon2,bLarge?&hIcon2:&hIcon,lSize);
|
||||
if (FAILED(hr))
|
||||
hIcon=hIcon2=NULL;
|
||||
if (hr==S_FALSE)
|
||||
flags=0;
|
||||
if (hIcon2) DestroyIcon(hIcon2); // HACK!!! Even though Extract should support NULL, not all implementations do. For example shfusion.dll crashes
|
||||
}
|
||||
if (!(flags&GIL_NOTFILENAME))
|
||||
{
|
||||
if (ExtractIconExA(location,index==-1?0:index,bLarge?&hIcon:NULL,bLarge?NULL:&hIcon,1)!=1)
|
||||
hIcon=NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return hIcon;
|
||||
}
|
||||
|
||||
HICON ShExtractIcon( const wchar_t *path, int index, int iconSize )
|
||||
{
|
||||
HICON hIcon;
|
||||
|
||||
typedef UINT (WINAPI *FSHExtractIconsW)( LPCWSTR pszFileName, int nIconIndex, int cxIcon, int cyIcon, HICON *phIcon, UINT *pIconId, UINT nIcons, UINT flags );
|
||||
static FSHExtractIconsW s_SHExtractIconsW;
|
||||
|
||||
if (!s_SHExtractIconsW)
|
||||
{
|
||||
HMODULE hShell32=GetModuleHandle(L"Shell32.dll");
|
||||
if (hShell32)
|
||||
s_SHExtractIconsW=(FSHExtractIconsW)GetProcAddress(hShell32,"SHExtractIconsW");
|
||||
}
|
||||
|
||||
if (s_SHExtractIconsW)
|
||||
{
|
||||
UINT id;
|
||||
if (!s_SHExtractIconsW(path,index,iconSize,iconSize,&hIcon,&id,1,LR_DEFAULTCOLOR))
|
||||
hIcon=NULL;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ExtractIconEx(path,index,&hIcon,NULL,1)!=1)
|
||||
return NULL;
|
||||
}
|
||||
if (hIcon)
|
||||
{
|
||||
AddTrackedIcon(hIcon);
|
||||
}
|
||||
return hIcon;
|
||||
}
|
||||
|
||||
HICON ShExtractIcon( const char *path, int index, int iconSize )
|
||||
{
|
||||
wchar_t pathW[_MAX_PATH];
|
||||
MbsToWcs(pathW,_countof(pathW),path);
|
||||
return ShExtractIcon(pathW,index,iconSize);
|
||||
}
|
||||
|
||||
// Converts an icon to a bitmap. pBits may be NULL. If bDestroyIcon is true, hIcon will be destroyed
|
||||
HBITMAP BitmapFromIcon( HICON hIcon, int iconSize, unsigned int **pBits, bool bDestroyIcon )
|
||||
{
|
||||
BITMAPINFO bi={0};
|
||||
bi.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
|
||||
bi.bmiHeader.biWidth=bi.bmiHeader.biHeight=iconSize;
|
||||
bi.bmiHeader.biPlanes=1;
|
||||
bi.bmiHeader.biBitCount=32;
|
||||
RECT rc={0,0,iconSize,iconSize};
|
||||
|
||||
HDC hdc=CreateCompatibleDC(NULL);
|
||||
unsigned int *bits;
|
||||
HBITMAP bmp=CreateDIBSection(hdc,&bi,DIB_RGB_COLORS,(void**)&bits,NULL,0);
|
||||
HGDIOBJ bmp0=SelectObject(hdc,bmp);
|
||||
FillRect(hdc,&rc,(HBRUSH)GetStockObject(BLACK_BRUSH));
|
||||
DrawIconEx(hdc,0,0,hIcon,iconSize,iconSize,0,NULL,DI_NORMAL);
|
||||
SelectObject(hdc,bmp0);
|
||||
DeleteDC(hdc);
|
||||
if (bDestroyIcon) DestroyIcon(hIcon);
|
||||
if (pBits) *pBits=bits;
|
||||
return bmp;
|
||||
}
|
||||
|
||||
// Premultiplies a DIB section by the alpha channel and a given color
|
||||
void PremultiplyBitmap( HBITMAP hBitmap, COLORREF rgb )
|
||||
{
|
||||
if (hBitmap == NULL) return;
|
||||
BITMAP info;
|
||||
GetObject(hBitmap,sizeof(info),&info);
|
||||
int n=info.bmWidth*info.bmHeight;
|
||||
int mr=(rgb)&255;
|
||||
int mg=(rgb>>8)&255;
|
||||
int mb=(rgb>>16)&255;
|
||||
// pre-multiply the alpha
|
||||
for (int i=0;i<n;i++)
|
||||
{
|
||||
unsigned int &pixel=((unsigned int*)info.bmBits)[i];
|
||||
int a=(pixel>>24);
|
||||
int r=(pixel>>16)&255;
|
||||
int g=(pixel>>8)&255;
|
||||
int b=(pixel)&255;
|
||||
r=(r*a*mr)/(255*255);
|
||||
g=(g*a*mg)/(255*255);
|
||||
b=(b*a*mb)/(255*255);
|
||||
pixel=(a<<24)|(r<<16)|(g<<8)|b;
|
||||
}
|
||||
}
|
||||
|
||||
// Creates a grayscale version of an icon
|
||||
HICON CreateDisabledIcon( HICON hIcon, int iconSize )
|
||||
{
|
||||
// convert normal icon to grayscale
|
||||
ICONINFO info;
|
||||
GetIconInfo(hIcon,&info);
|
||||
|
||||
unsigned int *bits;
|
||||
HBITMAP bmp=BitmapFromIcon(hIcon,iconSize,&bits,false);
|
||||
|
||||
int n=iconSize*iconSize;
|
||||
for (int i=0;i<n;i++)
|
||||
{
|
||||
unsigned int &pixel=bits[i];
|
||||
int r=(pixel&255);
|
||||
int g=((pixel>>8)&255);
|
||||
int b=((pixel>>16)&255);
|
||||
int l=(77*r+151*g+28*b)/256;
|
||||
pixel=(pixel&0xFF000000)|(l*0x010101);
|
||||
}
|
||||
|
||||
if (info.hbmColor) DeleteObject(info.hbmColor);
|
||||
info.hbmColor=bmp;
|
||||
hIcon=CreateIconIndirect(&info);
|
||||
DeleteObject(bmp);
|
||||
if (info.hbmMask) DeleteObject(info.hbmMask);
|
||||
return hIcon;
|
||||
}
|
||||
|
||||
// Loads an image file into a bitmap and optionally resizes it
|
||||
HBITMAP LoadImageFile( const wchar_t *path, const SIZE *pSize, bool bUseAlpha, bool bPremultiply, std::vector<unsigned int> *pButtonAnim )
|
||||
{
|
||||
HBITMAP srcBmp=NULL;
|
||||
if (_wcsicmp(PathFindExtension(path),L".bmp")==0)
|
||||
{
|
||||
srcBmp=(HBITMAP)LoadImage(NULL,path,IMAGE_BITMAP,0,0,LR_CREATEDIBSECTION|LR_LOADFROMFILE);
|
||||
}
|
||||
if (srcBmp && !pSize)
|
||||
return srcBmp;
|
||||
CComPtr<IWICImagingFactory> pFactory;
|
||||
if (FAILED(pFactory.CoCreateInstance(CLSID_WICImagingFactory)))
|
||||
{
|
||||
if (FAILED(pFactory.CoCreateInstance(CLSID_WICImagingFactory1)))
|
||||
{
|
||||
if (srcBmp) DeleteObject(srcBmp);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
CComPtr<IWICBitmapSource> pBitmap;
|
||||
if (srcBmp)
|
||||
{
|
||||
CComPtr<IWICBitmap> pBitmap2;
|
||||
if (FAILED(pFactory->CreateBitmapFromHBITMAP(srcBmp,NULL,bUseAlpha?WICBitmapUseAlpha:WICBitmapIgnoreAlpha,&pBitmap2)))
|
||||
{
|
||||
DeleteObject(srcBmp);
|
||||
return NULL;
|
||||
}
|
||||
pBitmap=pBitmap2;
|
||||
DeleteObject(srcBmp);
|
||||
}
|
||||
else
|
||||
{
|
||||
CComPtr<IWICBitmapDecoder> pDecoder;
|
||||
if (FAILED(pFactory->CreateDecoderFromFilename(path,NULL,GENERIC_READ,WICDecodeMetadataCacheOnLoad,&pDecoder)))
|
||||
return NULL;
|
||||
|
||||
CComPtr<IWICBitmapFrameDecode> pFrame;
|
||||
if (FAILED(pDecoder->GetFrame(0,&pFrame)))
|
||||
return NULL;
|
||||
pBitmap=pFrame;
|
||||
}
|
||||
|
||||
CComPtr<IWICFormatConverter> pConverter;
|
||||
if (FAILED(pFactory->CreateFormatConverter(&pConverter)))
|
||||
return NULL;
|
||||
pConverter->Initialize(pBitmap,bPremultiply?GUID_WICPixelFormat32bppPBGRA:GUID_WICPixelFormat32bppBGRA,WICBitmapDitherTypeNone,NULL,0,WICBitmapPaletteTypeMedianCut);
|
||||
pBitmap=pConverter;
|
||||
|
||||
int frameCount=1;
|
||||
int Yoffset=0;
|
||||
if (pButtonAnim)
|
||||
{
|
||||
frameCount=3;
|
||||
UINT width=0, height=0;
|
||||
pBitmap->GetSize(&width,&height);
|
||||
if (width>=3)
|
||||
{
|
||||
unsigned int data[3];
|
||||
WICRect rect={0,0,3,1};
|
||||
if (SUCCEEDED(pBitmap->CopyPixels(&rect,12,12,(BYTE*)data)) && (data[0]&0xFFFFFF)==ANIM_BUTTON_TAG1 && (data[1]&0xFFFFFF)==ANIM_BUTTON_TAG2)
|
||||
{
|
||||
Yoffset=(data[2]>>16)&255;
|
||||
if (Yoffset<(int)height)
|
||||
{
|
||||
frameCount=data[2]&255;
|
||||
if (frameCount<1) frameCount=1;
|
||||
if (frameCount>(int)(height-1)) frameCount=height-1;
|
||||
pButtonAnim->resize(Yoffset*width);
|
||||
rect.Width=width;
|
||||
rect.Height=Yoffset;
|
||||
pBitmap->CopyPixels(&rect,width*4,Yoffset*width*4,(BYTE*)&(*pButtonAnim)[0]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int frameWidthS, frameHeightS;
|
||||
int frameWidthD, frameHeightD;
|
||||
{
|
||||
UINT width=0, height=0;
|
||||
pBitmap->GetSize(&width,&height);
|
||||
frameWidthS=width;
|
||||
frameHeightS=(height-Yoffset)/frameCount;
|
||||
frameWidthD=frameWidthS;
|
||||
frameHeightD=frameHeightS;
|
||||
|
||||
// if cx>0, use as width
|
||||
// if cx<0, use -cx as width limit
|
||||
// if cy==0, scale proportionally
|
||||
if (pSize && pSize->cx && (pSize->cx>0 || -pSize->cx<frameWidthS))
|
||||
{
|
||||
frameWidthD=abs(pSize->cx);
|
||||
if (pSize->cy)
|
||||
frameHeightD=pSize->cy;
|
||||
else
|
||||
frameHeightD=frameWidthD*frameHeightS/frameWidthS;
|
||||
}
|
||||
}
|
||||
|
||||
BITMAPINFO bi={0};
|
||||
bi.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
|
||||
bi.bmiHeader.biWidth=frameWidthD;
|
||||
bi.bmiHeader.biHeight=-frameHeightD*frameCount;
|
||||
bi.bmiHeader.biPlanes=1;
|
||||
bi.bmiHeader.biBitCount=32;
|
||||
|
||||
HDC hdc=CreateCompatibleDC(NULL);
|
||||
BYTE *pBits;
|
||||
HBITMAP bmp=CreateDIBSection(hdc,&bi,DIB_RGB_COLORS,(void**)&pBits,NULL,0);
|
||||
DeleteDC(hdc);
|
||||
|
||||
for (int frame=0;frame<frameCount;frame++)
|
||||
{
|
||||
CComPtr<IWICBitmapSource> pFrame=pBitmap;
|
||||
if (frameCount>1)
|
||||
{
|
||||
CComPtr<IWICBitmapClipper> pClipper;
|
||||
if (FAILED(pFactory->CreateBitmapClipper(&pClipper)))
|
||||
{
|
||||
DeleteObject(bmp);
|
||||
bmp=NULL;
|
||||
break;
|
||||
}
|
||||
WICRect rect={0,frameHeightS*frame+Yoffset,frameWidthS,frameHeightS};
|
||||
pClipper->Initialize(pBitmap,&rect);
|
||||
pFrame=pClipper;
|
||||
}
|
||||
if (frameWidthS!=frameWidthD || frameHeightS!=frameHeightD)
|
||||
{
|
||||
CComPtr<IWICBitmapScaler> pScaler;
|
||||
if (FAILED(pFactory->CreateBitmapScaler(&pScaler)))
|
||||
{
|
||||
DeleteObject(bmp);
|
||||
bmp=NULL;
|
||||
break;
|
||||
}
|
||||
pScaler->Initialize(pFrame,frameWidthD,frameHeightD,WICBitmapInterpolationModeFant);
|
||||
pFrame=pScaler;
|
||||
}
|
||||
int stride=frameWidthD*4;
|
||||
int frameSize=frameHeightD*stride;
|
||||
pFrame->CopyPixels(NULL,stride,frameSize,pBits+frameSize*frame);
|
||||
}
|
||||
|
||||
return bmp;
|
||||
}
|
||||
|
||||
// Loads a bitmap from a IMAGE resource
|
||||
HBITMAP LoadImageResource( HMODULE hModule, const wchar_t *name, bool bTopDown, bool bPremultiply )
|
||||
{
|
||||
CComPtr<IWICImagingFactory> pFactory;
|
||||
if (FAILED(pFactory.CoCreateInstance(CLSID_WICImagingFactory)))
|
||||
{
|
||||
if (FAILED(pFactory.CoCreateInstance(CLSID_WICImagingFactory1)))
|
||||
return NULL;
|
||||
}
|
||||
|
||||
CComPtr<IWICBitmapSource> pBitmap;
|
||||
if (hModule)
|
||||
{
|
||||
HRSRC src=FindResource(hModule,name,L"IMAGE");
|
||||
if (!src) return NULL;
|
||||
HGLOBAL hGlobal=LoadResource(hModule,src);
|
||||
if (!hGlobal) return NULL;
|
||||
void *pngData=LockResource(hGlobal);
|
||||
if (!pngData) return NULL;
|
||||
DWORD size=SizeofResource(hModule,src);
|
||||
CComPtr<IStream> pStream;
|
||||
pStream.Attach(SHCreateMemStream((BYTE*)pngData,size));
|
||||
if (!pStream) return NULL;
|
||||
|
||||
CComPtr<IWICBitmapDecoder> pDecoder;
|
||||
if (FAILED(pFactory->CreateDecoderFromStream(pStream,NULL,WICDecodeMetadataCacheOnLoad,&pDecoder)))
|
||||
return NULL;
|
||||
CComPtr<IWICBitmapFrameDecode> pFrame;
|
||||
if (FAILED(pDecoder->GetFrame(0,&pFrame)))
|
||||
return NULL;
|
||||
pBitmap=pFrame;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (_wcsicmp(PathFindExtension(name),L".bmp")==0)
|
||||
{
|
||||
HBITMAP bmp=(HBITMAP)LoadImage(NULL,name,IMAGE_BITMAP,0,0,LR_CREATEDIBSECTION|LR_LOADFROMFILE);
|
||||
if (!bmp)
|
||||
return NULL;
|
||||
CComPtr<IWICBitmap> pBitmap2;
|
||||
if (FAILED(pFactory->CreateBitmapFromHBITMAP(bmp,NULL,WICBitmapUseAlpha,&pBitmap2)))
|
||||
pBitmap2=NULL;
|
||||
DeleteObject(bmp);
|
||||
if (!pBitmap2)
|
||||
return NULL;
|
||||
pBitmap=pBitmap2;
|
||||
}
|
||||
else
|
||||
{
|
||||
CComPtr<IWICBitmapDecoder> pDecoder;
|
||||
if (FAILED(pFactory->CreateDecoderFromFilename(name,NULL,GENERIC_READ,WICDecodeMetadataCacheOnLoad,&pDecoder)))
|
||||
return NULL;
|
||||
CComPtr<IWICBitmapFrameDecode> pFrame;
|
||||
if (FAILED(pDecoder->GetFrame(0,&pFrame)))
|
||||
return NULL;
|
||||
pBitmap=pFrame;
|
||||
}
|
||||
}
|
||||
|
||||
CComPtr<IWICFormatConverter> pConverter;
|
||||
if (FAILED(pFactory->CreateFormatConverter(&pConverter)))
|
||||
return NULL;
|
||||
pConverter->Initialize(pBitmap,bPremultiply?GUID_WICPixelFormat32bppPBGRA:GUID_WICPixelFormat32bppBGRA,WICBitmapDitherTypeNone,NULL,0,WICBitmapPaletteTypeMedianCut);
|
||||
|
||||
UINT width=0, height=0;
|
||||
pConverter->GetSize(&width,&height);
|
||||
|
||||
BITMAPINFO bi={0};
|
||||
bi.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
|
||||
bi.bmiHeader.biWidth=width;
|
||||
bi.bmiHeader.biHeight=bTopDown?-(int)height:(int)height;
|
||||
bi.bmiHeader.biPlanes=1;
|
||||
bi.bmiHeader.biBitCount=32;
|
||||
|
||||
HDC hdc=CreateCompatibleDC(NULL);
|
||||
BYTE *bits;
|
||||
HBITMAP bmp=CreateDIBSection(hdc,&bi,DIB_RGB_COLORS,(void**)&bits,NULL,0);
|
||||
DeleteDC(hdc);
|
||||
|
||||
if (bTopDown)
|
||||
{
|
||||
pConverter->CopyPixels(NULL,width*4,width*height*4,bits);
|
||||
}
|
||||
else
|
||||
{
|
||||
for (UINT y=0;y<height;y++)
|
||||
{
|
||||
WICRect rc={0,(INT)y,(INT)width,1};
|
||||
pConverter->CopyPixels(&rc,width*4,width*4,bits+(height-y-1)*width*4);
|
||||
}
|
||||
}
|
||||
|
||||
return bmp;
|
||||
}
|
||||
|
||||
// Returns the version of a given module
|
||||
DWORD GetVersionEx( HINSTANCE hInstance, DWORD *pBuild )
|
||||
{
|
||||
// get the DLL version. this is a bit hacky. the standard way is to use GetFileVersionInfo and such API.
|
||||
// but it takes a file name instead of module handle so it will probably load the DLL a second time.
|
||||
// the header of the version resource is a fixed size so we can count on VS_FIXEDFILEINFO to always
|
||||
// be at offset 40
|
||||
HRSRC hResInfo=FindResource(hInstance,MAKEINTRESOURCE(VS_VERSION_INFO),RT_VERSION);
|
||||
if (!hResInfo)
|
||||
return 0;
|
||||
HGLOBAL hRes=LoadResource(hInstance,hResInfo);
|
||||
void *pRes=LockResource(hRes);
|
||||
if (!pRes) return 0;
|
||||
|
||||
VS_FIXEDFILEINFO *pVer=(VS_FIXEDFILEINFO*)((char*)pRes+40);
|
||||
if (pBuild)
|
||||
*pBuild=LOWORD(pVer->dwProductVersionLS);
|
||||
return ((HIWORD(pVer->dwProductVersionMS)&255)<<24)|((LOWORD(pVer->dwProductVersionMS)&255)<<16)|HIWORD(pVer->dwProductVersionLS);
|
||||
}
|
||||
|
||||
// Returns the Windows version - 0x600, 0x601, ...
|
||||
WORD GetWinVersion( void )
|
||||
{
|
||||
static WORD version;
|
||||
if (!version)
|
||||
{
|
||||
#pragma warning(suppress:4996)
|
||||
DWORD ver=GetVersion();
|
||||
version=MAKEWORD(HIBYTE(ver),LOBYTE(ver));
|
||||
}
|
||||
return version;
|
||||
}
|
||||
|
||||
static bool IsWin81Update1Helper( void )
|
||||
{
|
||||
DWORD build;
|
||||
DWORD ver=GetVersionEx(GetModuleHandle(L"user32.dll"),&build);
|
||||
return HIWORD(ver)==WIN_VER_WIN81 && build>17000;
|
||||
}
|
||||
|
||||
// Returns true if the version is Win81 Update1 or later
|
||||
bool IsWin81Update1( void )
|
||||
{
|
||||
static bool bIsUpdate1=IsWin81Update1Helper();
|
||||
return bIsUpdate1;
|
||||
}
|
||||
|
||||
static bool IsWin10RS1Helper( void )
|
||||
{
|
||||
DWORD build;
|
||||
DWORD ver=GetVersionEx(GetModuleHandle(L"user32.dll"),&build);
|
||||
return ver>MAKELONG(14000,10<<8);
|
||||
}
|
||||
|
||||
// Returns true if the version is Windows10 RS1 or later
|
||||
bool IsWin10RS1( void )
|
||||
{
|
||||
static bool bIsRS1=IsWin10RS1Helper();
|
||||
return bIsRS1;
|
||||
}
|
||||
|
||||
typedef LONG NTSTATUS, *PNTSTATUS;
|
||||
#define STATUS_SUCCESS (0x00000000)
|
||||
typedef NTSTATUS (WINAPI* RtlGetVersionPtr)(PRTL_OSVERSIONINFOW);
|
||||
// *DO NOT USE DIRECTLY* : Call GetOSVersion() instead.
|
||||
//
|
||||
// The functions above return a windows version
|
||||
// that is rather not user-readable. This code should give
|
||||
// us a number we can reference with the "public" windows builds
|
||||
// such as what is returned by 'winver.exe'.
|
||||
RTL_OSVERSIONINFOW GetRealOSVersion() {
|
||||
HMODULE hMod = ::GetModuleHandleW(L"ntdll.dll");
|
||||
if (hMod) {
|
||||
RtlGetVersionPtr fxPtr = (RtlGetVersionPtr)::GetProcAddress(hMod, "RtlGetVersion");
|
||||
if (fxPtr != nullptr) {
|
||||
RTL_OSVERSIONINFOW rovi = { 0 };
|
||||
rovi.dwOSVersionInfoSize = sizeof(rovi);
|
||||
if ( STATUS_SUCCESS == fxPtr(&rovi) ) {
|
||||
return rovi;
|
||||
}
|
||||
}
|
||||
}
|
||||
RTL_OSVERSIONINFOW rovi = { 0 };
|
||||
return rovi;
|
||||
}
|
||||
|
||||
static RTL_OSVERSIONINFOW GetOSVersion()
|
||||
{
|
||||
// cache result to avoid calling the dll multiple times.
|
||||
static RTL_OSVERSIONINFOW ver = GetRealOSVersion();
|
||||
return ver;
|
||||
}
|
||||
|
||||
static bool IsWin10RS4Helper( void )
|
||||
{
|
||||
auto version = GetOSVersion();
|
||||
return version.dwMajorVersion > 8 && version.dwBuildNumber > 17131;
|
||||
}
|
||||
|
||||
// Returns true if the version is Windows10 RS4 (Spring Creator Update) or later
|
||||
bool IsWin10RS4( void )
|
||||
{
|
||||
static bool bIsRS4=IsWin10RS4Helper();
|
||||
return bIsRS4;
|
||||
}
|
||||
|
||||
static bool IsWin11Helper()
|
||||
{
|
||||
auto version = GetOSVersion();
|
||||
return version.dwMajorVersion >= 10 && version.dwBuildNumber >= 22000;
|
||||
}
|
||||
|
||||
// Returns true if the version is Windows11 or later
|
||||
bool IsWin11(void)
|
||||
{
|
||||
static bool bIsWin11 = IsWin11Helper();
|
||||
return bIsWin11;
|
||||
}
|
||||
|
||||
// Wrapper for IShellFolder::ParseDisplayName
|
||||
HRESULT ShParseDisplayName( const wchar_t *pszName, PIDLIST_ABSOLUTE *ppidl, SFGAOF sfgaoIn, SFGAOF *psfgaoOut )
|
||||
{
|
||||
static ITEMIDLIST ilRoot={0};
|
||||
static CComPtr<IShellFolder> pDesktop;
|
||||
if (_wcsicmp(pszName,L"::{Desktop}")==0)
|
||||
{
|
||||
*ppidl=ILCloneFull((PIDLIST_ABSOLUTE)&ilRoot);
|
||||
if (psfgaoOut)
|
||||
{
|
||||
*psfgaoOut=0;
|
||||
if (sfgaoIn&SFGAO_FOLDER)
|
||||
*psfgaoOut|=SFGAO_FOLDER;
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
else
|
||||
{
|
||||
*ppidl=NULL;
|
||||
if (!pDesktop)
|
||||
{
|
||||
HRESULT hr=SHGetDesktopFolder(&pDesktop);
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
}
|
||||
SFGAOF flags=sfgaoIn;
|
||||
HRESULT hr=pDesktop->ParseDisplayName(NULL,NULL,(wchar_t*)pszName,NULL,(PIDLIST_RELATIVE*)ppidl,psfgaoOut?&flags:NULL);
|
||||
if (FAILED(hr))
|
||||
return hr;
|
||||
if (psfgaoOut)
|
||||
*psfgaoOut=flags;
|
||||
return hr;
|
||||
}
|
||||
}
|
||||
|
||||
// Separates the arguments from the program
|
||||
// May return NULL if no arguments are found
|
||||
const wchar_t *SeparateArguments( const wchar_t *command, wchar_t *program )
|
||||
{
|
||||
if (command[0]=='"')
|
||||
{
|
||||
// quoted program - just GetToken will work
|
||||
return GetToken(command,program,_MAX_PATH,L" ");
|
||||
}
|
||||
|
||||
// skip leading spaces
|
||||
while (*command==' ')
|
||||
command++;
|
||||
const wchar_t *args=wcschr(command,' ');
|
||||
if (!args)
|
||||
{
|
||||
// no spaces - the whole thing is a program
|
||||
Strcpy(program,_MAX_PATH,command);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int len=(int)(args-command);
|
||||
if (len>_MAX_PATH-1) len=_MAX_PATH-1;
|
||||
memcpy(program,command,len*2);
|
||||
program[len]=0;
|
||||
|
||||
const wchar_t *space=command;
|
||||
while (*space)
|
||||
{
|
||||
space=wcschr(space+1,' ');
|
||||
if (!space)
|
||||
space=command+Strlen(command);
|
||||
len=(int)(space-command);
|
||||
if (len>=_MAX_PATH) break;
|
||||
wchar_t prog2[_MAX_PATH];
|
||||
memcpy(prog2,command,len*2);
|
||||
prog2[len]=0;
|
||||
if (len>0 && prog2[len-1]=='\\')
|
||||
prog2[len-1]=0;
|
||||
WIN32_FIND_DATA data;
|
||||
HANDLE h=FindFirstFile(prog2,&data);
|
||||
if (h!=INVALID_HANDLE_VALUE)
|
||||
{
|
||||
// found a valid file
|
||||
FindClose(h);
|
||||
memcpy(program,command,len*2);
|
||||
program[len]=0;
|
||||
if (*space)
|
||||
args=space+1;
|
||||
else
|
||||
args=NULL;
|
||||
}
|
||||
}
|
||||
|
||||
while (args && *args==' ')
|
||||
args++;
|
||||
return args;
|
||||
}
|
||||
struct CommonEnvVar
|
||||
{
|
||||
const wchar_t *name;
|
||||
wchar_t value[_MAX_PATH];
|
||||
int len;
|
||||
};
|
||||
|
||||
CommonEnvVar g_CommonEnvVars[]={
|
||||
{L"USERPROFILE"},
|
||||
{L"ALLUSERSPROFILE"},
|
||||
{L"SystemRoot"},
|
||||
{L"SystemDrive"},
|
||||
};
|
||||
|
||||
void UnExpandEnvStrings( const wchar_t *src, wchar_t *dst, int size )
|
||||
{
|
||||
static bool bInit=false;
|
||||
if (!bInit)
|
||||
{
|
||||
bInit=true;
|
||||
for (int i=0;i<_countof(g_CommonEnvVars);i++)
|
||||
{
|
||||
int len=GetEnvironmentVariable(g_CommonEnvVars[i].name,g_CommonEnvVars[i].value,_MAX_PATH);
|
||||
if (len<=_MAX_PATH)
|
||||
g_CommonEnvVars[i].len=len;
|
||||
}
|
||||
}
|
||||
|
||||
for (int i=0;i<_countof(g_CommonEnvVars);i++)
|
||||
{
|
||||
int len=g_CommonEnvVars[i].len;
|
||||
if (_wcsnicmp(src,g_CommonEnvVars[i].value,len)==0)
|
||||
{
|
||||
const wchar_t *name=g_CommonEnvVars[i].name;
|
||||
if (Strlen(src)-len+Strlen(name)+3>size)
|
||||
break; // not enough space
|
||||
Sprintf(dst,size,L"%%%s%%%s",name,src+len);
|
||||
return;
|
||||
}
|
||||
}
|
||||
Strcpy(dst,size,src);
|
||||
}
|
||||
|
||||
void StringUpper( CString &str )
|
||||
{
|
||||
int len=str.GetLength();
|
||||
wchar_t *buf=str.GetBuffer(len);
|
||||
CharUpper(buf);
|
||||
str.ReleaseBufferSetLength(len);
|
||||
}
|
||||
|
||||
// Create a font from the user settings
|
||||
HFONT CreateFontSetting( const wchar_t *fontStr, int dpi )
|
||||
{
|
||||
const wchar_t *str=fontStr;
|
||||
if (!*str) return NULL;
|
||||
|
||||
wchar_t name[256];
|
||||
while (*str==' ')
|
||||
str++;
|
||||
str=GetToken(str,name,_countof(name),L",");
|
||||
int len=Strlen(name);
|
||||
while (len>0 && name[len-1]==' ')
|
||||
name[--len]=0;
|
||||
while (*str==' ')
|
||||
str++;
|
||||
wchar_t token[256];
|
||||
str=GetToken(str,token,_countof(token),L",");
|
||||
len=Strlen(token);
|
||||
while (len>0 && token[len-1]==' ')
|
||||
token[--len]=0;
|
||||
int weight=FW_NORMAL;
|
||||
bool bItalic=false;
|
||||
if (_wcsicmp(token,L"bold")==0)
|
||||
weight=FW_BOLD;
|
||||
else if (_wcsicmp(token,L"italic")==0)
|
||||
bItalic=1;
|
||||
else if (_wcsicmp(token,L"bold_italic")==0)
|
||||
weight=FW_BOLD, bItalic=true;
|
||||
str=GetToken(str,token,_countof(token),L", \t");
|
||||
int size=-_wtol(token);
|
||||
return CreateFont(MulDiv(size,dpi,72),0,0,0,weight,bItalic?1:0,0,0,DEFAULT_CHARSET,OUT_DEFAULT_PRECIS,CLIP_DEFAULT_PRECIS,DEFAULT_QUALITY,DEFAULT_PITCH,name);
|
||||
}
|
||||
|
||||
static UINT WINAPI GetDpiForWindow(HWND hwnd)
|
||||
{
|
||||
static auto p = static_cast<decltype(&GetDpiForWindow)>((void*)GetProcAddress(GetModuleHandle(L"user32.dll"), "GetDpiForWindow"));
|
||||
if (p)
|
||||
return p(hwnd);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
UINT GetDpi(HWND hwnd)
|
||||
{
|
||||
UINT dpi = GetDpiForWindow(hwnd);
|
||||
if (!dpi)
|
||||
{
|
||||
// fall-back for older systems
|
||||
HDC hdc = GetDC(nullptr);
|
||||
dpi = GetDeviceCaps(hdc, LOGPIXELSY);
|
||||
ReleaseDC(nullptr, hdc);
|
||||
}
|
||||
|
||||
return dpi;
|
||||
}
|
||||
|
||||
int ScaleForDpi(HWND hwnd, int value)
|
||||
{
|
||||
return MulDiv(value, GetDpi(hwnd), USER_DEFAULT_SCREEN_DPI);
|
||||
}
|
||||
97
Src/Lib/ResourceHelper.h
Normal file
@@ -0,0 +1,97 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <shobjidl.h>
|
||||
#include <vector>
|
||||
|
||||
// Loads the best DLL for the given language
|
||||
HINSTANCE LoadTranslationDll( const wchar_t *langSetting );
|
||||
|
||||
// Loads all strings and dialogs from hLngInstance
|
||||
// pDialogs is a NULL-terminated list of dialog IDs. They are loaded from hLngInstance if possible, otherwise from g_Instance
|
||||
void LoadTranslationResources( HINSTANCE hLngInstance, int *pDialogs );
|
||||
|
||||
// Returns a localized string
|
||||
CString LoadStringEx( int stringID );
|
||||
CString LoadStringEnglish( int stringID );
|
||||
|
||||
// Returns a localized dialog template
|
||||
DLGTEMPLATE *LoadDialogEx( int dlgID );
|
||||
|
||||
// Loads an icon. path can be a path to .ico file, or in the format "module.dll, number"
|
||||
HICON LoadIcon( int iconSize, const wchar_t *path, std::vector<HMODULE> &modules );
|
||||
|
||||
// Loads the icon for the given pidl (file or folder)
|
||||
HICON LoadIcon( int iconSize, PIDLIST_ABSOLUTE pidl );
|
||||
|
||||
// Extracts icon of a given size from a specified location the way Shell does it
|
||||
HICON ShExtractIcon( const wchar_t *path, int index, int iconSize );
|
||||
HICON ShExtractIcon( const char *path, int index, int iconSize );
|
||||
|
||||
// Converts an icon to a bitmap. pBits may be NULL. If bDestroyIcon is true, hIcon will be destroyed
|
||||
HBITMAP BitmapFromIcon( HICON hIcon, int iconSize, unsigned int **pBits, bool bDestroyIcon );
|
||||
|
||||
// Loads an image file into a bitmap and optionally resizes it
|
||||
HBITMAP LoadImageFile( const wchar_t *path, const SIZE *pSize, bool bUseAlpha, bool bPremultiply, std::vector<unsigned int> *pButtonAnim );
|
||||
|
||||
// Loads a bitmap from a IMAGE resource
|
||||
HBITMAP LoadImageResource( HMODULE hModule, const wchar_t *name, bool bTopDown, bool bPremultiply );
|
||||
|
||||
// Premultiplies a DIB section by the alpha channel and a given color
|
||||
void PremultiplyBitmap( HBITMAP hBitmap, COLORREF rgb );
|
||||
|
||||
// Creates a grayscale version of an icon
|
||||
HICON CreateDisabledIcon( HICON hIcon, int iconSize );
|
||||
|
||||
// Returns the version of a given module
|
||||
DWORD GetVersionEx( HINSTANCE hInstance, DWORD *pBuild=NULL );
|
||||
|
||||
const int WIN_VER_VISTA=0x600;
|
||||
const int WIN_VER_WIN7 =0x601;
|
||||
const int WIN_VER_WIN8 =0x602;
|
||||
const int WIN_VER_WIN81=0x603;
|
||||
const int WIN_VER_WIN10=0xA00;
|
||||
|
||||
// Returns the Windows version - 0x600, 0x601, ...
|
||||
WORD GetWinVersion( void );
|
||||
|
||||
// Returns true if the version is Win81 Update1
|
||||
bool IsWin81Update1( void );
|
||||
|
||||
// Returns true if the version is Windows10 RS1 or later
|
||||
bool IsWin10RS1( void );
|
||||
|
||||
// Returns true if the version is Windows10 RS4 (Spring Creator Update) or later
|
||||
bool IsWin10RS4( void );
|
||||
|
||||
// Returns true if the version is Windows11 or later
|
||||
bool IsWin11();
|
||||
|
||||
// Wrapper for IShellFolder::ParseDisplayName
|
||||
HRESULT ShParseDisplayName( const wchar_t *pszName, PIDLIST_ABSOLUTE *ppidl, SFGAOF sfgaoIn, SFGAOF *psfgaoOut );
|
||||
|
||||
// Separates the arguments from the program
|
||||
// May return NULL if no arguments are found
|
||||
const wchar_t *SeparateArguments( const wchar_t *command, wchar_t *program );
|
||||
|
||||
// Replaces some common paths with environment variables
|
||||
void UnExpandEnvStrings( const wchar_t *src, wchar_t *dst, int size );
|
||||
|
||||
void StringUpper( CString &str );
|
||||
|
||||
// Create a font from the user settings
|
||||
HFONT CreateFontSetting( const wchar_t *fontStr, int dpi );
|
||||
|
||||
// Return DPI of given window (or system DPI on older systems)
|
||||
UINT GetDpi(HWND hwnd = nullptr);
|
||||
|
||||
// Scale given value according to DPI of window
|
||||
int ScaleForDpi(HWND hwnd, int value);
|
||||
|
||||
extern HINSTANCE g_Instance;
|
||||
|
||||
const int ANIM_BUTTON_TAG1='ANM';
|
||||
const int ANIM_BUTTON_TAG2='BTN';
|
||||
2852
Src/Lib/Settings.cpp
Normal file
197
Src/Lib/Settings.h
Normal file
@@ -0,0 +1,197 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#pragma once
|
||||
|
||||
class ISettingsPanel
|
||||
{
|
||||
public:
|
||||
virtual HWND Create( HWND parent )=0;
|
||||
virtual HWND Activate( struct CSetting *pGroup, const RECT &rect, bool bReset )=0;
|
||||
virtual bool Validate( HWND parent )=0;
|
||||
};
|
||||
|
||||
struct CSetting
|
||||
{
|
||||
enum Type
|
||||
{
|
||||
TYPE_GROUP=-2,
|
||||
TYPE_RADIO=-1,
|
||||
TYPE_BOOL=1,
|
||||
TYPE_INT,
|
||||
TYPE_HOTKEY,
|
||||
TYPE_HOTKEY_ANY,
|
||||
TYPE_COLOR, // requires the high 8 bits of the flags to contain an index into the color palette
|
||||
|
||||
// string types
|
||||
TYPE_STRING,
|
||||
TYPE_ICON,
|
||||
TYPE_BITMAP,
|
||||
TYPE_BITMAP_JPG,
|
||||
TYPE_SOUND,
|
||||
TYPE_FONT,
|
||||
TYPE_MULTISTRING,
|
||||
TYPE_DIRECTORY,
|
||||
};
|
||||
|
||||
enum
|
||||
{
|
||||
// initial settings
|
||||
FLAG_WARM= 0x00001,
|
||||
FLAG_COLD= 0x00002,
|
||||
FLAG_BASIC= 0x00004,
|
||||
FLAG_HIDDEN= 0x00008,
|
||||
FLAG_SHARED= 0x00010,
|
||||
FLAG_NORESET= 0x00020,
|
||||
FLAG_NODEFAULT= 0x00040,
|
||||
FLAG_NOSAVE= 0x00080,
|
||||
FLAG_CALLBACK= 0x00100,
|
||||
|
||||
FLAG_MENU_CLASSIC1= 0x00200,
|
||||
FLAG_MENU_CLASSIC2= 0x00400,
|
||||
FLAG_MENU_CLASSIC_BOTH=FLAG_MENU_CLASSIC1|FLAG_MENU_CLASSIC2,
|
||||
FLAG_MENU_WIN7= 0x00800,
|
||||
FLAG_MENU_MASK=FLAG_MENU_CLASSIC1|FLAG_MENU_CLASSIC2|FLAG_MENU_WIN7,
|
||||
|
||||
// for run-time use only
|
||||
FLAG_DEFAULT= 0x01000,
|
||||
FLAG_FORCED_DEFAULT= 0x02000,
|
||||
FLAG_LOCKED_REG= 0x04000, // locked by HKLM registry setting
|
||||
FLAG_LOCKED_GP= 0x08000, // locked by a group policy
|
||||
FLAG_LOCKED_MASK=FLAG_LOCKED_REG|FLAG_LOCKED_GP,
|
||||
FLAG_WARNING= 0x10000, // show a warning icon
|
||||
// top 8 bits need to stay unused. that's where we store the color index
|
||||
};
|
||||
|
||||
const wchar_t *name;
|
||||
Type type;
|
||||
int nameID, tipID; // resource strings
|
||||
CComVariant defValue; // default value
|
||||
unsigned int flags;
|
||||
const wchar_t *depend;
|
||||
const wchar_t *nest;
|
||||
ISettingsPanel *pPanel; // custom panel for editing this group of settings
|
||||
|
||||
CSetting *pLinkTo; // if this is not NULL, then the value is stored in the linked setting (the default value, radio settings, etc. must match between the two)
|
||||
|
||||
// runtime use only
|
||||
CComVariant value; // current value
|
||||
CComVariant tempValue; // the value is stored here when editing begins and restored if the editing is canceled
|
||||
unsigned int tempFlags;
|
||||
|
||||
bool IsEnabled( void ) const;
|
||||
bool IsDefault( void ) const { return ((pLinkTo?pLinkTo->flags:flags)&FLAG_DEFAULT)!=0; }
|
||||
bool IsForcedDefault( void ) const { return ((pLinkTo?pLinkTo->flags:flags)&FLAG_FORCED_DEFAULT)!=0; }
|
||||
bool IsLocked( void ) const { return ((pLinkTo?pLinkTo->flags:flags)&FLAG_LOCKED_MASK)!=0; }
|
||||
bool IsLockedReg( void ) const { return ((pLinkTo?pLinkTo->flags:flags)&FLAG_LOCKED_REG)!=0; }
|
||||
bool ShouldLoad( bool bShared ) const;
|
||||
bool MatchFilter( const wchar_t *filter ) const;
|
||||
const CComVariant &GetValue( void ) const { return pLinkTo?pLinkTo->value:value; }
|
||||
|
||||
void LoadValue( CRegKey ®Settings, CRegKey ®SettingsUser, CRegKey ®Policy, CRegKey ®PolicyUser );
|
||||
|
||||
private:
|
||||
bool ReadValue( CRegKey ®Key, const wchar_t *valName );
|
||||
};
|
||||
|
||||
// Images in the tree image list
|
||||
enum {
|
||||
SETTING_STATE_NONE=1,
|
||||
SETTING_STATE_SETTING=2,
|
||||
SETTING_STATE_CHECKBOX=4,
|
||||
SETTING_STATE_RADIO=8,
|
||||
|
||||
// additional flags
|
||||
SETTING_STATE_DISABLED=1,
|
||||
SETTING_STATE_CHECKED=2,
|
||||
|
||||
SETTING_IMAGE_COLOR=13, // 10 blank images to use for custom colors
|
||||
};
|
||||
|
||||
enum TSettingsComponent
|
||||
{
|
||||
COMPONENT_EXPLORER,
|
||||
COMPONENT_MENU,
|
||||
COMPONENT_IE,
|
||||
COMPONENT_UPDATE,
|
||||
COMPONENT_SHARED,
|
||||
};
|
||||
|
||||
class ICustomSettings
|
||||
{
|
||||
public:
|
||||
virtual int AppendBackupMenu( HMENU menu, int id ) = 0;
|
||||
virtual void ExecuteBackupMenu( int id ) = 0;
|
||||
};
|
||||
|
||||
void InitSettings( CSetting *pSettings, TSettingsComponent component, ICustomSettings *pCustom );
|
||||
void LoadSettings( void );
|
||||
void SaveSettings( void );
|
||||
void UpdateDefaultSettings( void );
|
||||
void EditSettings( const wchar_t *title, bool bModal, int tab, const wchar_t *appId = nullptr );
|
||||
void CloseSettings( void );
|
||||
void SetSettingsDirty( void );
|
||||
void SelectSettingsTab( int tab, bool bAdvanced, const CSetting *pSelect );
|
||||
void UpdateSettings( void ); // implemented by the user
|
||||
void UpgradeSettings( bool bShared ); // implemented by the user (called when converting 3.0 settings to 4.0)
|
||||
void ClosingSettings( HWND hWnd, int flags, int command ); // implemented by the user
|
||||
void SettingChangedCallback( const CSetting *pSetting ); // implemented by the user
|
||||
bool IsSettingsMessage( MSG *msg );
|
||||
bool ImportSettingsXml( const wchar_t *fname );
|
||||
bool ExportSettingsXml( const wchar_t *fname );
|
||||
const CSetting *GetAllSettings( void );
|
||||
void SetSettingsStyle( int style, int mask );
|
||||
void GetSettingsStyle( int &style, int &mask );
|
||||
|
||||
// Finds a setting by name
|
||||
CSetting *FindSetting( const wchar_t *name );
|
||||
// Updates the setting with a new default value and locked flag
|
||||
void UpdateSetting( const wchar_t *name, const CComVariant &defValue, bool bLockedGP );
|
||||
// Updates the setting with a new tooltip and a warning flag
|
||||
void UpdateSettingText( const wchar_t *name, int nameID, int tipID, bool bWarning );
|
||||
|
||||
void HideSetting( const wchar_t *name, bool bHide );
|
||||
void HideSettingGroup( const wchar_t *name, bool bHide );
|
||||
void UpdateGroupText( const wchar_t *name, int nameID );
|
||||
|
||||
bool GetSettingBool( const wchar_t *name );
|
||||
int GetSettingInt( const wchar_t *name );
|
||||
CString GetSettingString( const wchar_t *name );
|
||||
bool IsSettingLocked( const wchar_t *name );
|
||||
bool IsSettingForcedDefault( const wchar_t *name );
|
||||
|
||||
// In some cases the default can change dynamically, so the setting may be out of date. Use bDef to detect if the default value should be used
|
||||
int GetSettingInt( const wchar_t *name, bool &bDef );
|
||||
bool GetSettingBool( const wchar_t *name, bool &bDef );
|
||||
|
||||
struct CSettingsLockRead
|
||||
{
|
||||
CSettingsLockRead( void );
|
||||
~CSettingsLockRead( void );
|
||||
};
|
||||
|
||||
struct CSettingsLockWrite
|
||||
{
|
||||
CSettingsLockWrite( void );
|
||||
~CSettingsLockWrite( void );
|
||||
};
|
||||
|
||||
bool HasHelp( void );
|
||||
void ShowHelp( void );
|
||||
|
||||
#ifndef _WIN64
|
||||
bool SaveAdmx( TSettingsComponent component, const char *admxFile, const char *admlFile, const char *docFile );
|
||||
#endif
|
||||
|
||||
// Opens the registry keys for the settings of the given component
|
||||
// Returns true if the user settings were read from the old HKCU location. That means the settings may need to be upgraded
|
||||
bool OpenSettingsKeys( TSettingsComponent component, CRegKey ®Settings, CRegKey ®SettingsUser, CRegKey ®Policy, CRegKey ®PolicyUser );
|
||||
|
||||
// Get a value from a manually loaded setting
|
||||
bool GetSettingBool( const CSetting &setting );
|
||||
CString GetSettingString( const CSetting &setting );
|
||||
|
||||
// the format for the location is key_name|value_name|file_name
|
||||
void VLogToFile( const wchar_t *location, const wchar_t *message, va_list args );
|
||||
void LogToFile( const wchar_t *location, const wchar_t *message, ... );
|
||||
554
Src/Lib/SettingsParser.cpp
Normal file
@@ -0,0 +1,554 @@
|
||||
// Classic Shell (c) 2009-2017, Ivo Beltchev
|
||||
// Open-Shell (c) 2017-2018, The Open-Shell Team
|
||||
// Confidential information of Ivo Beltchev. Not for disclosure or distribution without prior written consent from the author
|
||||
|
||||
#include <stdafx.h>
|
||||
#include "SettingsParser.h"
|
||||
#include "ResourceHelper.h"
|
||||
#include "StringUtils.h"
|
||||
#include <algorithm>
|
||||
|
||||
const int MAX_TREE_LEVEL=10;
|
||||
|
||||
// Reads a file into m_Text
|
||||
bool CSettingsParser::LoadText( const wchar_t *fname )
|
||||
{
|
||||
// read settings file into buf
|
||||
FILE *f=NULL;
|
||||
if (_wfopen_s(&f,fname,L"rb")) return false;
|
||||
if (!f) return false;
|
||||
fseek(f,0,SEEK_END);
|
||||
int size=ftell(f);
|
||||
fseek(f,0,SEEK_SET);
|
||||
std::vector<unsigned char> buf(size);
|
||||
if (size<4 || fread(&buf[0],1,size,f)!=size)
|
||||
{
|
||||
fclose(f);
|
||||
return false;
|
||||
}
|
||||
fclose(f);
|
||||
LoadText(&buf[0],size);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Reads a text resource into m_Text
|
||||
bool CSettingsParser::LoadText( HMODULE hMod, HRSRC hResInfo )
|
||||
{
|
||||
HGLOBAL hRes=LoadResource(hMod,hResInfo);
|
||||
int size=SizeofResource(hMod,hResInfo);
|
||||
unsigned char *buf=(unsigned char*)LockResource(hRes);
|
||||
if (!buf) return false;
|
||||
LoadText(buf,size);
|
||||
return true;
|
||||
}
|
||||
|
||||
void CSettingsParser::LoadText( const unsigned char *buf, int size )
|
||||
{
|
||||
// copy buf to text and convert to UTF16
|
||||
if (buf[0]==0xFF && buf[1]==0xFE)
|
||||
{
|
||||
// UTF16
|
||||
int len=(size-2)/2;
|
||||
m_Text.resize(len+1);
|
||||
memcpy(&m_Text[0],&buf[2],size-2);
|
||||
m_Text[len]=0;
|
||||
}
|
||||
else if (buf[0]==0xEF && buf[1]==0xBB && buf[2]==0xBF)
|
||||
{
|
||||
// UTF8
|
||||
int len=MultiByteToWideChar(CP_UTF8,0,(const char*)&buf[3],size-3,NULL,0);
|
||||
m_Text.resize(len+1);
|
||||
MultiByteToWideChar(CP_UTF8,0,(const char*)&buf[3],size-3,&m_Text[0],len);
|
||||
m_Text[len]=0;
|
||||
}
|
||||
else
|
||||
{
|
||||
// ACP
|
||||
int len=MultiByteToWideChar(CP_ACP,0,(const char*)&buf[0],size,NULL,0);
|
||||
m_Text.resize(len+1);
|
||||
MultiByteToWideChar(CP_UTF8,0,(const char*)&buf[0],size,&m_Text[0],len);
|
||||
m_Text[len]=0;
|
||||
}
|
||||
}
|
||||
|
||||
void CSettingsParser::LoadText( const wchar_t *buf, int size )
|
||||
{
|
||||
m_Text.resize(size+1);
|
||||
memcpy(&m_Text[0],buf,size*2);
|
||||
m_Text[size]=0;
|
||||
}
|
||||
|
||||
// Splits m_Text into m_Lines
|
||||
void CSettingsParser::ParseText( void )
|
||||
{
|
||||
if (m_Text.empty()) return;
|
||||
// split into lines
|
||||
wchar_t *str=&m_Text[0];
|
||||
while (*str)
|
||||
{
|
||||
if (*str!=';') // ignore lines starting with ;
|
||||
{
|
||||
// trim leading whitespace
|
||||
while (*str==' ' || *str=='\t')
|
||||
str++;
|
||||
m_Lines.push_back(str);
|
||||
}
|
||||
wchar_t *p1=wcschr(str,'\r');
|
||||
wchar_t *p2=wcschr(str,'\n');
|
||||
wchar_t *end=&m_Text[m_Text.size()-1];
|
||||
if (p1) end=p1;
|
||||
if (p2 && p2<end) end=p2;
|
||||
|
||||
wchar_t *next=end;
|
||||
while (*next=='\r' || *next=='\n')
|
||||
next++;
|
||||
|
||||
// trim trailing whitespace
|
||||
while (end>str && (*end==' ' || *end=='\t'))
|
||||
end--;
|
||||
*end=0;
|
||||
str=next;
|
||||
}
|
||||
}
|
||||
|
||||
// Filters the settings that belong to the given language
|
||||
// languages is a 00-terminated list of language names ordered by priority
|
||||
void CSettingsParser::FilterLanguages( const wchar_t *languages )
|
||||
{
|
||||
std::vector<const wchar_t*> lines;
|
||||
lines.swap(m_Lines);
|
||||
for (const wchar_t *lang=languages;*lang;lang+=wcslen(lang)+1)
|
||||
{
|
||||
size_t langLen=wcslen(lang);
|
||||
for (size_t i=0;i<lines.size();i++)
|
||||
{
|
||||
const wchar_t *line=lines[i];
|
||||
if (*line=='[' && _wcsnicmp(line+1,lang,langLen)==0 && line[langLen+1]==']')
|
||||
{
|
||||
for (i++;i<lines.size();i++)
|
||||
{
|
||||
line=lines[i];
|
||||
if (*line=='[') break;
|
||||
m_Lines.push_back(line);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
std::reverse(m_Lines.begin(),m_Lines.end());
|
||||
}
|
||||
|
||||
// Returns a setting with the given name. If no setting is found, returns def
|
||||
const wchar_t *CSettingsParser::FindSetting( const wchar_t *name, const wchar_t *def )
|
||||
{
|
||||
const wchar_t *str=FindSettingInt(name,wcslen(name));
|
||||
return (str && *str)?str:def;
|
||||
}
|
||||
|
||||
const wchar_t *CSettingsParser::FindSettingDirect( const wchar_t *name )
|
||||
{
|
||||
return FindSettingInt(name,wcslen(name));
|
||||
}
|
||||
|
||||
const wchar_t *CSettingsParser::FindSettingInt( const wchar_t *name, size_t len )
|
||||
{
|
||||
for (std::vector<const wchar_t*>::const_reverse_iterator it=m_Lines.rbegin();it!=m_Lines.rend();++it)
|
||||
{
|
||||
const wchar_t *str=*it;
|
||||
if (_wcsnicmp(name,str,len)==0)
|
||||
{
|
||||
str+=len;
|
||||
while (*str==' ' || *str=='\t')
|
||||
str++;
|
||||
if (*str!='=') continue;
|
||||
str++;
|
||||
while (*str==' ' || *str=='\t')
|
||||
str++;
|
||||
return str;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Frees all resources
|
||||
void CSettingsParser::Reset( void )
|
||||
{
|
||||
m_Lines.clear();
|
||||
m_Text.clear();
|
||||
}
|
||||
|
||||
// Parses a tree structure of items. The rootName setting must be a list of item names.
|
||||
void CSettingsParser::ParseTree( const wchar_t *rootName, std::vector<TreeItem> &items )
|
||||
{
|
||||
const wchar_t *str=FindSetting(rootName);
|
||||
if (str)
|
||||
{
|
||||
CString names[MAX_TREE_LEVEL];
|
||||
ParseTreeRec(str,items,names,0);
|
||||
}
|
||||
else
|
||||
{
|
||||
TreeItem last={L"",-1};
|
||||
items.push_back(last);
|
||||
}
|
||||
}
|
||||
|
||||
int CSettingsParser::ParseTreeRec( const wchar_t *str, std::vector<TreeItem> &items, CString *names, int level )
|
||||
{
|
||||
size_t start=items.size();
|
||||
while (*str)
|
||||
{
|
||||
wchar_t token[256];
|
||||
str=GetToken(str,token,_countof(token),L", \t");
|
||||
if (token[0])
|
||||
{
|
||||
//
|
||||
bool bFound=false;
|
||||
for (int i=0;i<level;i++)
|
||||
if (_wcsicmp(token,names[i])==0)
|
||||
{
|
||||
bFound=true;
|
||||
break;
|
||||
}
|
||||
if (!bFound)
|
||||
{
|
||||
TreeItem item={token,-1};
|
||||
items.push_back(item);
|
||||
}
|
||||
}
|
||||
}
|
||||
size_t end=items.size();
|
||||
if (start==end) return -1;
|
||||
|
||||
TreeItem item={L"",-1};
|
||||
items.push_back(item);
|
||||
|
||||
if (level<MAX_TREE_LEVEL-1)
|
||||
{
|
||||
for (size_t i=start;i<end;i++)
|
||||
{
|
||||
wchar_t buf[266];
|
||||
Sprintf(buf,_countof(buf),L"%s.Items",items[i].name);
|
||||
const wchar_t *str2=FindSetting(buf);
|
||||
if (str2)
|
||||
{
|
||||
names[level]=items[i].name;
|
||||
// these two statements must be on separate lines. otherwise items[i] is evaluated before ParseTreeRec, but
|
||||
// the items vector can be reallocated inside ParseTreeRec, causing the address to be invalidated -> crash!
|
||||
int idx=ParseTreeRec(str2,items,names,level+1);
|
||||
items[i].children=idx;
|
||||
}
|
||||
}
|
||||
}
|
||||
return (int)start;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
bool CSkinParser::LoadVariation( const wchar_t *fname )
|
||||
{
|
||||
m_VarText.swap(m_Text);
|
||||
bool res=LoadText(fname);
|
||||
if (res)
|
||||
{
|
||||
std::vector<const wchar_t*> lines;
|
||||
lines.swap(m_Lines);
|
||||
lines.push_back(L"[TRUE]");
|
||||
ParseText();
|
||||
m_Lines.insert(m_Lines.begin(),lines.begin(),lines.end());
|
||||
}
|
||||
m_VarText.swap(m_Text);
|
||||
return res;
|
||||
}
|
||||
|
||||
bool CSkinParser::LoadVariation( HMODULE hMod, HRSRC hResInfo )
|
||||
{
|
||||
m_VarText.swap(m_Text);
|
||||
bool res=LoadText(hMod,hResInfo);
|
||||
if (res)
|
||||
{
|
||||
std::vector<const wchar_t*> lines;
|
||||
lines.swap(m_Lines);
|
||||
lines.push_back(L"[TRUE]");
|
||||
ParseText();
|
||||
m_Lines.insert(m_Lines.begin(),lines.begin(),lines.end());
|
||||
}
|
||||
m_VarText.swap(m_Text);
|
||||
return res;
|
||||
}
|
||||
|
||||
void CSkinParser::Reset( void )
|
||||
{
|
||||
CSettingsParser::Reset();
|
||||
m_VarText.clear();
|
||||
}
|
||||
|
||||
static const wchar_t *g_OptionNames[SKIN_OPTION_TYPE_COUNT]={
|
||||
L"OPTION ",
|
||||
L"OPTION_NUMBER ",
|
||||
L"OPTION_STRING ",
|
||||
L"OPTION_COLOR ",
|
||||
L"OPTION_IMAGE ",
|
||||
};
|
||||
|
||||
// Parses the option from m_Lines[index]. Returns false if index is out of bounds
|
||||
bool CSkinParser::ParseOption( CString &name, TSkinOptionType &type, CString &label, bool &value, CString &condition, CString &disValue, int index )
|
||||
{
|
||||
if (index<0 || index>=(int)m_Lines.size())
|
||||
return false;
|
||||
name.Empty();
|
||||
wchar_t buf[256];
|
||||
const wchar_t *line=m_Lines[index];
|
||||
if (_wcsnicmp(line,L"OPTION",6)!=0)
|
||||
return true;
|
||||
type=SKIN_OPTION_NONE;
|
||||
for (int i=0;i<SKIN_OPTION_TYPE_COUNT;i++)
|
||||
{
|
||||
int len=Strlen(g_OptionNames[i]);
|
||||
if (_wcsnicmp(line,g_OptionNames[i],len)==0)
|
||||
{
|
||||
type=(TSkinOptionType)i;
|
||||
line+=len;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (type==SKIN_OPTION_NONE)
|
||||
return true;
|
||||
|
||||
const wchar_t *end=wcschr(line,'=');
|
||||
if (!end) return true;
|
||||
line=GetToken(line,buf,_countof(buf),L" \t=");
|
||||
name=buf;
|
||||
line=GetToken(line,buf,_countof(buf),L",");
|
||||
if (buf[0]=='#')
|
||||
label=LoadStringEx(_wtol(buf+1));
|
||||
else
|
||||
label=buf;
|
||||
if (label.IsEmpty())
|
||||
name.Empty();
|
||||
line=GetToken(line,buf,_countof(buf),L" \t,");
|
||||
value=_wtol(buf)!=0;
|
||||
line=GetToken(line,buf,_countof(buf),L",");
|
||||
condition=buf;
|
||||
line=GetToken(line,buf,_countof(buf),L" \t,");
|
||||
disValue=buf;
|
||||
if (type==SKIN_OPTION_BOOL && name==L"RADIOGROUP")
|
||||
type=SKIN_OPTION_GROUP;
|
||||
return true;
|
||||
}
|
||||
|
||||
// Filters the conditional groups
|
||||
// values/count - list of true options. the rest are assumed to be false
|
||||
void CSkinParser::FilterConditions( const wchar_t **values, int count )
|
||||
{
|
||||
std::vector<const wchar_t*> lines;
|
||||
lines.swap(m_Lines);
|
||||
|
||||
bool bEnable=true;
|
||||
|
||||
for (size_t i=0;i<lines.size();i++)
|
||||
{
|
||||
const wchar_t *line=lines[i];
|
||||
if (*line=='[')
|
||||
{
|
||||
bEnable=false;
|
||||
wchar_t condition[256];
|
||||
const wchar_t *end=wcschr(line,']');
|
||||
if (!end) continue; // not closed
|
||||
int len=(int)(end-line)-1;
|
||||
if (len>_countof(condition)-1)
|
||||
continue; // too long
|
||||
memcpy(condition,line+1,len*2);
|
||||
condition[len]=0;
|
||||
|
||||
// evaluate condition
|
||||
if (EvalCondition(condition,values,count)==1)
|
||||
bEnable=true;
|
||||
continue;
|
||||
}
|
||||
if (bEnable)
|
||||
m_Lines.push_back(line);
|
||||
}
|
||||
}
|
||||
|
||||
// Substitutes the provided macro strings
|
||||
void CSkinParser::ApplyMacros( const std::vector<std::pair<CString,CString>> ¯os )
|
||||
{
|
||||
std::vector<CString> names;
|
||||
for (std::vector<std::pair<CString,CString>>::const_iterator it=macros.begin();it!=macros.end();++it)
|
||||
{
|
||||
wchar_t name[256];
|
||||
Sprintf(name,_countof(name),L"@%s@",it->first);
|
||||
names.push_back(name);
|
||||
}
|
||||
|
||||
for (std::vector<const wchar_t*>::iterator it=m_Lines.begin();it!=m_Lines.end();++it)
|
||||
{
|
||||
if (wcschr(*it,'@'))
|
||||
{
|
||||
CString string=*it;
|
||||
for (size_t i=0;i<names.size();i++)
|
||||
string.Replace(names[i],macros[i].second);
|
||||
|
||||
m_ExtraStrings.push_back(string);
|
||||
*it=string;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Returns a setting with the given name
|
||||
const wchar_t *CSkinParser::FindSetting( const wchar_t *name )
|
||||
{
|
||||
const wchar_t *str=CSettingsParser::FindSetting(name);
|
||||
if (!str && m_Aliases)
|
||||
{
|
||||
for (int i=0;m_Aliases[i];i+=2)
|
||||
{
|
||||
if (wcscmp(name,m_Aliases[i])==0)
|
||||
return CSettingsParser::FindSetting(m_Aliases[i+1]);
|
||||
}
|
||||
}
|
||||
return str;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
enum TType
|
||||
{
|
||||
TYPE_AND,
|
||||
TYPE_OR,
|
||||
TYPE_NOT,
|
||||
TYPE_PAR, // '('
|
||||
};
|
||||
|
||||
static bool ApplyOperator( bool *valStack, int &vsp, TType op )
|
||||
{
|
||||
switch (op)
|
||||
{
|
||||
case TYPE_AND:
|
||||
if (vsp<2) return false;
|
||||
vsp--;
|
||||
valStack[vsp-1]=valStack[vsp-1] && valStack[vsp];
|
||||
return true;
|
||||
case TYPE_OR:
|
||||
if (vsp<2) return false;
|
||||
vsp--;
|
||||
valStack[vsp-1]=valStack[vsp-1] || valStack[vsp];
|
||||
return true;
|
||||
case TYPE_NOT:
|
||||
if (vsp<1) return false;
|
||||
valStack[vsp-1]=!valStack[vsp-1];
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
// Evaluates a boolean condition. vars/count - a list of variable names that are TRUE. The rest are assumed FALSE
|
||||
// Returns: 0 - false, 1 - true, -1 - error
|
||||
int EvalCondition( const wchar_t *condition, const wchar_t *const *values, int count )
|
||||
{
|
||||
wchar_t token[256];
|
||||
TType opStack[16];
|
||||
int osp=0;
|
||||
bool valStack[16];
|
||||
int vsp=0;
|
||||
|
||||
while (1)
|
||||
{
|
||||
// skip leading whitespace
|
||||
while (*condition==' ' || *condition=='\t')
|
||||
condition++;
|
||||
if (!*condition) break;
|
||||
|
||||
if (*condition=='(')
|
||||
{
|
||||
if (osp>=_countof(opStack)) return -1; // too much nesting
|
||||
opStack[osp]=TYPE_PAR;
|
||||
osp++;
|
||||
condition++;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (*condition==')')
|
||||
{
|
||||
bool found=false;
|
||||
while (osp>0)
|
||||
{
|
||||
osp--;
|
||||
if (opStack[osp]==TYPE_PAR)
|
||||
{
|
||||
found=true;
|
||||
break;
|
||||
}
|
||||
if (!ApplyOperator(valStack,vsp,opStack[osp])) return -1; // invalid operation
|
||||
}
|
||||
if (!found) return -1; // too many )
|
||||
condition++;
|
||||
continue;
|
||||
}
|
||||
|
||||
// find token
|
||||
const wchar_t *end=condition;
|
||||
while (*end && *end!=' ' && *end!='\t' && *end!='(' && *end!=')')
|
||||
end++;
|
||||
|
||||
int len=(int)(end-condition);
|
||||
if (len>=sizeof(token)) return -1; // too long token
|
||||
memcpy(token,condition,len*2);
|
||||
token[len]=0;
|
||||
condition=end;
|
||||
while (*condition==' ' || *condition=='\t')
|
||||
condition++;
|
||||
|
||||
if (_wcsicmp(token,L"and")==0 || _wcsicmp(token,L"or")==0)
|
||||
{
|
||||
while (osp>0 && opStack[osp-1]!=TYPE_PAR)
|
||||
{
|
||||
osp--;
|
||||
if (!ApplyOperator(valStack,vsp,opStack[osp])) return -1; // invalid operation
|
||||
}
|
||||
if (osp>=_countof(opStack)) return -1; // too much nesting
|
||||
opStack[osp]=(token[0]=='a' || token[0]=='A')?TYPE_AND:TYPE_OR;
|
||||
osp++;
|
||||
}
|
||||
else if (_wcsicmp(token,L"not")==0)
|
||||
{
|
||||
while (osp>0 && opStack[osp-1]==TYPE_NOT)
|
||||
{
|
||||
osp--;
|
||||
if (!ApplyOperator(valStack,vsp,opStack[osp])) return -1; // invalid operation
|
||||
}
|
||||
if (osp>=_countof(opStack)) return -1; // too much nesting
|
||||
opStack[osp]=TYPE_NOT;
|
||||
osp++;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (vsp>=_countof(valStack)) return -1; // too much nesting
|
||||
bool bValue=false;
|
||||
if (_wcsicmp(token,L"true")==0)
|
||||
bValue=true;
|
||||
else
|
||||
{
|
||||
for (int i=0;i<count;i++)
|
||||
if (_wcsicmp(token,values[i])==0)
|
||||
{
|
||||
bValue=true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
valStack[vsp++]=bValue;
|
||||
}
|
||||
}
|
||||
|
||||
while (osp>0)
|
||||
{
|
||||
osp--;
|
||||
if (opStack[osp]==TYPE_PAR) return -1; // unclosed (
|
||||
if (!ApplyOperator(valStack,vsp,opStack[osp])) return -1; // invalid operation
|
||||
}
|
||||
|
||||
if (vsp!=1) return -1; // unbalanced expression
|
||||
return valStack[0]?1:0;
|
||||
}
|
||||