2010-09-16 13 views
54

Visual Studio sigue tratando de aplicar sangría al código dentro de espacios de nombres.¿Hay alguna manera de hacer que Visual Studio deje de sangrar espacios de nombres?

Por ejemplo:

namespace Foo 
{ 
    void Bar(); 

    void Bar() 
    { 

    } 

} 

Ahora, si yo deshacer la sangría de forma manual y luego se mantenga de esa manera. Pero desafortunadamente, si agrego algo justo antes de void Bar();, como un comentario, VS seguirá intentando sangrarlo.

Esto es tan molesto que básicamente por esta única razón casi nunca uso espacios de nombres en C++. No puedo entender por qué trata de sangrarlos (¿cuál es el sentido de sangrar 1 o incluso 5 pestañas en el archivo completo?), O cómo hacer que se detenga.

¿Hay alguna manera de detener este comportamiento? Una opción de configuración, un complemento, una configuración de registro, incluso un truco que modifica devenv.exe directamente.

 
#define BEGIN_NAMESPACE(x) namespace x { 
#define END_NAMESPACE } 

suena tonto, pero usted se sorprendería de la cantidad de encabezados de sistemas usan esto:

+0

Puede deshabilitar la sangría automática por completo. O configúrelo para sangrar por una cantidad menor (por ejemplo, 2 espacios en lugar de 1 pestaña) – jalf

+3

Esto (configuración de sangría no configurable) es una de las muchas razones por las que detuve la edición de archivos en Visual Studio hace años ... :) –

+1

Lo haré otorgue la recompensa a quien encuentre una solución que no tenga efectos secundarios, o los menos efectos secundarios posibles. Por ahora, la mejor respuesta, IMO, es Bacar's; si no se proporcionan mejores respuestas, le otorgaré la respuesta. –

Respuesta

13

Aquí hay una macro que podría ayudarlo. Eliminará la sangría si detecta que está creando actualmente un namespace. No es perfecto, pero parece funcionar hasta ahora.

Public Sub aftekeypress(ByVal key As String, ByVal sel As TextSelection, ByVal completion As Boolean) _ 
     Handles TextDocumentKeyPressEvents.AfterKeyPress 
    If (Not completion And key = vbCr) Then 
     'Only perform this if we are using smart indent 
     If DTE.Properties("TextEditor", "C/C++").Item("IndentStyle").Value = 2 Then 
      Dim textDocument As TextDocument = DTE.ActiveDocument.Object("TextDocument") 
      Dim startPoint As EditPoint = sel.ActivePoint.CreateEditPoint() 
      Dim matchPoint As EditPoint = sel.ActivePoint.CreateEditPoint() 
      Dim findOptions As Integer = vsFindOptions.vsFindOptionsMatchCase + vsFindOptions.vsFindOptionsMatchWholeWord + vsFindOptions.vsFindOptionsBackwards 
      If startPoint.FindPattern("namespace", findOptions, matchPoint) Then 
       Dim lines = matchPoint.GetLines(matchPoint.Line, sel.ActivePoint.Line) 
       ' Make sure we are still in the namespace {} but nothing has been typed 
       If System.Text.RegularExpressions.Regex.IsMatch(lines, "^[\s]*(namespace[\s\w]+)?[\s\{]+$") Then 
        sel.Unindent() 
       End If 
      End If 
     End If 
    End If 
End Sub 

Ya que está funcionando todo el tiempo, es necesario asegurarse de que está instalando el interior macro en sus EnvironmentEvents project item MyMacros interior. Solo puede acceder a este módulo en el Explorador de macros (Herramientas-> Macros-> Explorador de macros).

una nota, que no admite actualmente "empaquetados" espacios de nombres tales como

namespace A { namespace B { 
... 
} 
} 

EDITAR

apoyar "lleno" espacios de nombres, como el ejemplo anterior y/o apoyo comentarios después del espacio de nombres, como namespace A { /* Example */, puede intentar utilizar la siguiente línea:

If System.Text.RegularExpressions.Regex.IsMatch(lines, "^[\s]*(namespace.+)?[\s\{]+$") Then 

No he tenido la oportunidad de probarlo mucho todavía, pero parece estar funcionando.

+0

Muchas gracias por su respuesta. Hubo un error que ahora corregí, pero además de eso funciona perfectamente. Grats en la recompensa. –

+0

¡Maldita sea, ya había empezado a gastar esa recompensa! ;-) – bacar

+0

Funciona bien para escribir, pero no para pegar, o p. La funcionalidad "Crear Implementación" de Visual Assist mientras que la solución de Bacar hace el truco allí. Sin embargo, es más limpio. – Adversus

12
probablemente no es lo que quería escuchar, pero una gran cantidad de personas que trabaja en torno a este mediante el uso de macros

. (La implementación stl de glibc, por ejemplo, tiene _GLIBCXX_BEGIN_NAMESPACE() para esto.)

De hecho, prefiero esta manera, porque siempre tiendo a encogerme cuando veo líneas sin sangría siguiendo un {. Aunque soy solo yo.

+8

Creo que esto es más por compatibilidad con compiladores antiguos que por Visual Studio =) –

+6

@andreas Creo que de esa manera puedes cambiar fácilmente el espacio de nombres de toda la lib sin editar todos los archivos fuente –

3

Entiendo el problema cuando hay espacios de nombres anidados. Solía ​​empaquetar todos los namespace s en una sola línea para evitar la sangría múltiple. Dejará un nivel, pero eso no es tan malo como muchos niveles. Ha pasado tanto tiempo desde que utilicé VS que apenas recuerdo esos días.

namespace outer { namespace middle { namespace inner { 
    void Test(); 
    ..... 
}}} 
30

Simplemente no inserte nada antes de la primera línea de código. Puede probar con el siguiente método para insertar una línea nula de código (que parece que funciona en VS2005):

namespace foo 
{; // !<--- 
void Test(); 
} 

Esto parece suprimir la sangría, pero los compiladores puede emitir advertencias y los colaboradores de código/mantenedores pueden ser sorprendidos! (Y con toda razón, en el caso habitual!)

+9

Me gusta esto también. Parece que incluso una macro que se expande a nada es suficiente para suprimir la sangría. Así que puedes '#definar SUPPRESS_INDENTATION' y luego abrir el espacio de nombres como' namespace foo {SUPPRESS_INDENTATION' :) –

+0

Nice - la intención es algo más clara y es menos probable que el compilador genere advertencias :) – bacar

+0

Si bien esta ha sido mi solución favorita , Quería mencionar que este truco no funciona en VS2013. Hay una configuración de usuario en VS2013 que evita que esto suceda (cuando funciona, vea otra respuesta). – jdknight

5

También podría declarar adelante sus tipos (o lo que sea) en el interior del espacio de nombres a continuación, poner en práctica fuera de la siguiente manera:

namespace test { 
    class MyClass; 
} 

class test::MyClass { 
//... 
}; 
35

como puntos KindDragon cabo, Visual Studio 2013 Actualización 2 tiene una opción para detener la sangría.

Puede desmarcar HERRAMIENTAS -> Opciones -> Editor de texto -> C/C++ -> Formatear -> Sangría -> Aplicar sangría al contenido del espacio de nombres.

+5

Parece haberse roto nuevamente ... Al menos en la Actualización 4. Espero que lo solucionen. – AzP

+2

De hecho, está roto. Aunque puedes usar el formato clang y simplemente solucionar el problema. –

+1

Acabo de probar VS2013 Update 5 CTP; parece estar trabajando de nuevo. Esperemos que siga así para la publicación oficial de la Actualización 5. – jdknight

0

Visual Studio 2017

Namespace Indention Menu VS2017

Se puede llegar a este "espacio de nombres contenidos sangría" ajuste en Herramientas> Opciones y luego de texto Editor-> C/C++ -> Formatting-> La sangría. Está en el fondo de los menús, pero extremadamente útil una vez encontrado.

+1

¡por favor no dejen solo respuestas de enlace! – monamona

Cuestiones relacionadas