Menú

Mostrar Mensajes

Esta sección te permite ver todos los mensajes escritos por este usuario. Ten en cuenta que sólo puedes ver los mensajes escritos en zonas a las que tienes acceso en este momento.

Mostrar Mensajes Menú

Mensajes - Serapis

#2341
Cita de: p4p4z0t3 en  3 Julio 2018, 21:32 PM
Una vez me dijeron ... VisualBasic, pero que también sería demasiada complicación para un programa tan simple como el que quiero hacer.
¿?¿?¿¿?¿?¿
El que te dijo eso, probablemente no sepa distinguir su mano izquierda del pie derecho.

Si has manejado Excel, Visual Basic, te irá perfecto...
#2342
Pués no sé qué resulta más intrigante, si los ocultos, o los visitantes...  :laugh: :laugh: :laugh:

...pareciera que vienen de Orión (o más lejos aún, de "Raticulín"),  :laugh: :laugh: :laugh: :laugh: :laugh:



#2343
Citarpor otro lado no solo se droga XD el va a nueva york a invadir la casa blanca
mmm... pudiera ser que utilice la palabra 'invadir' como sinónimo de 'cagar en'.... ???

...con la falta de papel higiénico en Venezuela, "la Casa Blanca" debe sonar como a un lugar repleto de rollos de papel higiénico por todas partes, a cada paso un rollo colgando de la pared, descendiendo por el suelo hasta mitad del pasillo... vamos, un paraíso orgíastico, para un cagón.
#2344
Creas una función que admita como parámetros 2 cadenas, las compara y si B es menor que A, las intercambia.


string A = Luis
string B = Andrés
string C = Pedro

invocar Ordenar3Cadenas(A, B, C)
imprimir A
imprimir B
imprimir C


Y aquí las dos funciones...

// Como son 3 cadenas, la función será invocada 3 veces
Funcion Ordenar3Cadenas(string ref A, string ref B, string ref C)
   Compara(A, B)
   Compara(A, C) // A la salida de aquí, ya se tiene la menor de las 3 en A
   Compara(B, C) // A la salida de aquí, ya están ordenadas las otras dos.
fin funcion

funcion Compara(string ref A, string ref B)
   string tmp

   Si (B < A)
       tmp = A
       A = B
       B = tmp
   fin si
fin funcion


...y listo... prueba con diferentes cadenas y siempre al final imprime el resultado.
#2345
Cita de: Fran1946 en  5 Julio 2018, 14:01 PM
... Como se hace un control de usuario transparente, que sería el que tendría el Picture que tengo donde se dibuja todo, y entonces sería reemplazar en todo el código en nombre del Picture. ...
No es difícil, son solo un cúmulo de condiciones concretas que como mínimo hay que mantener inalterables o bien, los cambios que se hagan deben ser consecuentes...

Mañana que tengo un poco más de tiempo libre, te hago uno con la funcionalidad mínima y adecuada al caso, del que partir...
#2346
Al final se me hizo muy tarde...

He visto el vídeo, y aunque sirve para hacerse una ídea d elo que estás haciendo, no aporta detalles sobre el problema. Quiero decir que no recala en ningún momento en el error que reportas.

Te decía que cuando debes utilizar gráficos a mansalva, los gráficos conviene que sean 'dibujados', es decir métodos y no 'controles'. Los controles ocupan espacio de memoria, pero más alla de eso, el uso indiscriminado puede hacerlo lento y caer en el error que te sugrge. estoy convencido que has alcanzado el límite máximo de controles que s epermite para un formulario (ahora mismo no recuerdo cual es, ya que es algo que uno nunca considera que se va a dar y lo acaba olvidando (el valor exacto)).

Para usar métodos gráficos, lo más adecuado es recurrir a las API gráficas que proveen GDI32 o al menos simplemente GDI, indistintamente de que uno se provea sus propios métodos cuando se quiera hacer algo específico que no esté prtevisto, o que no satisfaga por algna razón.
El inconveniente de usar las API, es que evidentemente se necesita aprender a conocerlo y eso lleva su tiempo. Especialmente si uno nunca se ha acercado a usar APIs, puede sonarle a chino, la forma de funcionar y no entender ciertos detalles por que se alejan (de alguna manera), de la forma relativamente sencilla (y a veces tortuosa) en que funcionan las cosas en VB6.

Otro forma, es que sin salirse de vb6, cree uno mismo determinada funcionalidad, por ejemplo crear un control de usuario transparente, que provea no solo funcionalidad gráfica, sino también alguna colección, para almacenar métodos gráficos, entonces de ese modo, un solo control, podría tener por ejemplo 200 métodos gráficos, usando un único control de usuario... y por ejemplo, el control podría contener dibujado toda esa escalera sobre sí, podrías tener luego otro control (otra instancia del mismo control), para la leyenda, o bien otros métodos gráficos en el mismo control...

Asumo que básicamente operas en un entorno 2D... aunque se puede hacer también un entorno 3D, e incluso ir más alla, con raytracing y tal... se sale de la envergadura de ayuda para unos foros, aunque siempre se puede dar orientación si la precisas...

...si el fin de semana saco un poquito de tiempo libre, veo de hacer un control así, bueno me conozco, y al final sé que aunque tenga tiempo libre surgirá algo, así que aprovecho ahora y en un momento te doy alguna orientación que puede servirte de guía...

La colección podría almacenar una estructura (o clase) con los siguientes tipos (así a bote pronto):
Código (vb) [Seleccionar]

Private ColGrPaths            As New Collection
private p_NumGrPaths       As long

' El texto o una polilínea requerirá otro desarrollo, porque el uno exige un string, y el otro múltiples puntos...
Public Type DatosGraficos
    Orden       As Byte     ' punto, línea, rectángulo, círculo, arco, polígono, elipse...
    SubOrden    As Byte     ' si línea, si círculo ó elipse, si arco...
    Activo      As Byte     ' Se dibuja si tiene valor 255, si no se omite (cuando se pide dibujar todo).
    X           As Long     ' cordenadas
    Y           As Long     '   "
    Ancho       As Long     ' medidas (radio en caso de círculo polígono, etc...)
    Alto        As Long     '   "     (aristas en caso de polígono, etc...)
    Color       As Long     ' Color con que se dibuja. Un flag determina si se usa el color por defecto, del control o se delega en el que aquí se designe.
    Grosor      As Byte     ' Grueso de línea "        "      "
    FlagABC     As Byte     ' Modificador de acciones
    Flags       As Long     ' por ejemplo rellenar interior (casos de círculo, elipse, polígono, etc)
    FlagXYZ     As Long     ' modificadores de posicionado, desplazamiento y escala...
End Type

' Dibuja toda la colección almacenada de métodos gráficos... (solo los que estén activos).
Public Sub PathDibujarTodo(Optional ByVal Actualizar As Boolean = True)
    Call PathsDibujar(0, ColGrPaths.Count - 1, Actualizar)
End Sub

' Dibuja de un plumazo todas las órdenes gráficas reclamadas y (si se reclama) acto seguido actualiza la imagen. Si cantidad es un valor negativo, dibuja en orden inverso. Si Cantidad excede el límite se ignora.
Public Sub PathsDibujar(ByVal Desde As Long, ByVal Cantidad As Long, Optional ByVal Actualizar As Boolean = True)
    Dim k As Long, Final As Long
   
    If (EnRango(Desde) = True) Then ' se exige que desde sea un valor 'dentro' de la colección.
        If Cantidad = 0 Then Exit Sub ' nada que dibujar... caso típico que el valor sea el resultado de una expresión.
       
        Final = (Desde + Cantidad)
        If (Cantidad > 0) Then
            If (Final >= ColGrPaths.Count) Then Final = ColGrPaths.Count - 1
           
            For k = Desde To Final
                If (ColGrPaths(k).Activo And c_Activo) Then
                    Dibujar (ColGrPaths(k))
                End If
            Next
        Else
            Final = -Final
           
            For k = Final To Desde Step -1
                If (ColGrPaths(k).Activo And c_Activo) Then
                    Dibujar (ColGrPaths(k))
                End If
            Next
        End If
       
        If (Actualizar = True) Then
            Call GrEndPath ' actualiza la imagen
        End If
    End If
End Sub

'...




Dibujar sería una función que simplemente recibe el objeto y mediante un 'select case' invoca a la función específica que se encarga de dibujar la orden específica...

Nota como esta función también es pública, para permitir dibujar una orden que no conste en la colección, peor que a cierto momento pueda interesar.
Lógicamente también podrán invocarse externamente los métodos gráficos, sin necesidad de que existan como un 'objeto'...
Código (vb) [Seleccionar]

Public Sub DibujarOrden(ByRef dg As DatosGraficos)
    With dg
        Select Case .Orden
            Case ORDEN_GRAFICA_LINEA   ' 0 más arriba las que sean más frecuentes de ser dibujadas
                Call Me.GrLinea(.X, .Y, .X + .Ancho, .Y + .Alto, .Color, .Grosor)
            Case ORDEN_GRAFICA_RECTANGULO
            Case ORDEN_GRAFICA_CIRCULO
            Case ORDEN_GRAFICA_POLIGONO
            ' ...
            Case Else             ' orden desconocida...
        End Select
    End With
End Sub


Y algunas funciones... en este ejemplo, varias funciones que definen un objeto sin ambigüedad, finalmente invocan al mismo (privado)...
Código (vb) [Seleccionar]

Public Sub GrLinea(Optional ByVal X1 As Variant, Optional ByVal Y1 As Variant, Optional ByVal X2 As Variant, Optional ByVal Y2 As Variant, Optional ByVal Color As Variant, Optional ByVal Ancho As Byte = 1, Optional ByVal AbsolutoOrigen As Boolean = True, Optional ByVal AbsolutoDestino As Boolean = True)
    Call LinRectCaja(X1, Y1, X2, Y2, Color, Ancho, AbsolutoOrigen, AbsolutoDestino)
End Sub

Public Sub GrRectangulo(Optional ByVal X1 As Variant, Optional ByVal Y1 As Variant, Optional ByVal X2 As Variant, Optional ByVal Y2 As Variant, Optional ByVal Color As Variant, Optional ByVal Ancho As Byte = 1, Optional ModoFusion As DrawModeConstants = vbCopyPen, Optional ByVal AbsolutoOrigen As Boolean = True, Optional ByVal AbsolutoDestino As Boolean = True)
    Call LinRectCaja(X1, Y1, X2, Y2, Color, Ancho, AbsolutoOrigen, AbsolutoDestino, ModoFusion, True)
End Sub

Public Sub GrCaja(Optional ByVal X1 As Variant, Optional ByVal Y1 As Variant, Optional ByVal X2 As Variant, Optional ByVal Y2 As Variant, Optional ByVal Color As Variant, Optional ModoFusion As DrawModeConstants = vbCopyPen, Optional ByVal AbsolutoOrigen As Boolean = True, Optional ByVal AbsolutoDestino As Boolean = True)
    Call LinRectCaja(X1, Y1, X2, Y2, Color, , AbsolutoOrigen, AbsolutoDestino, ModoFusion, True, True)
End Sub

' Resume las 3 funciones previas en una sola.
Private Sub LinRectCaja(Optional ByVal X1 As Variant, Optional ByVal Y1 As Variant, Optional ByVal X2 As Variant, Optional ByVal Y2 As Variant, Optional ByVal Color As Variant, Optional ByVal Ancho As Byte = 1, Optional ByVal AbsolutoOrigen As Boolean = True, Optional ByVal AbsolutoDestino As Boolean = True, Optional ModoFusion As DrawModeConstants = vbCopyPen, Optional ByVal Box As Boolean = False, Optional ByVal Relleno As Boolean = False)
    Dim AnchoPrevio             As Integer
    Dim ModoFusionPrevio        As DrawModeConstants
   
    With PicMask  ' es un objeto oculto, puede ser incluso un picturebox...(no visible)
        AnchoPrevio = .DrawWidth: .DrawWidth = Ancho
        ModoFusionPrevio = .DrawMode: .DrawMode = ModoFusion
       
        ' si se omiten ambos (x1 y x2), se trazará una línea de currentX a 0
        If (IsMissing(X1) = True) Then
            X1 = .CurrentX
        ElseIf (IsMissing(X2) = True) Then
            X2 = .CurrentX
        End If
   
        ' si se omiten ambos (y1 e y2), se trazará una línea de currentY a 0
        If (IsMissing(Y1) = True) Then
            Y1 = .CurrentY
        ElseIf (IsMissing(Y2) = True) Then
            Y2 = .CurrentY
        End If
       
        '
        If (Relleno = True) Then ' exige Boxed también
            If (IsMissing(Color) = True) Then Color = .FillColor
            If (AbsolutoOrigen = True) Then
                If (AbsolutoDestino = True) Then
                    PicMask.Line (X1, Y1)-(X2, Y2), Color, BF
                Else
                    PicMask.Line (X1, Y1)-Step(X2, Y2), Color, BF
                End If
            Else
                If (AbsolutoDestino = True) Then
                    PicMask.Line Step(X1, Y1)-(X2, Y2), Color, BF
                Else
                    PicMask.Line Step(X1, Y1)-Step(X2, Y2), Color, BF
                End If
            End If
        ElseIf (Box = True) Then
            If (IsMissing(Color) = True) Then Color = .ForeColor
            If (AbsolutoOrigen = True) Then
                If (AbsolutoDestino = True) Then
                    PicMask.Line (X1, Y1)-(X2, Y2), Color, B
                Else
                    PicMask.Line (X1, Y1)-Step(X2, Y2), Color, B
                End If
            Else
                If (AbsolutoDestino = True) Then
                    PicMask.Line Step(X1, Y1)-(X2, Y2), Color, B
                Else
                    PicMask.Line Step(X1, Y1)-Step(X2, Y2), Color, B
                End If
            End If
        Else
            If (IsMissing(Color) = True) Then Color = .ForeColor
            If (AbsolutoOrigen = True) Then
                If (AbsolutoDestino = True) Then
                    PicMask.Line (X1, Y1)-(X2, Y2), Color
                Else
                    PicMask.Line (X1, Y1)-Step(X2, Y2), Color
                End If
            Else
                If (AbsolutoDestino = True) Then
                    PicMask.Line Step(X1, Y1)-(X2, Y2), Color
                Else
                    PicMask.Line Step(X1, Y1)-Step(X2, Y2), Color
                End If
            End If
        End If
       
        .DrawWidth = AnchoPrevio
        .DrawMode = ModoFusionPrevio
    End With
End Sub


También puede suceder

CurrentX y CurrentY se guardan como propiedades que no aparecen en el visor de propiedades (deben retirarse, para estar disponibles solo en tiempo de ejecución), es adecuado, para trazar por ejemplo polilíneas... Una polilínea, sería simplemente una colección de puntos, + 1 orden gráfica que defina el primer punto, el color, ancho, etc...
Esto te permite obtener donde terminó de dibujar un objeto para (por ejemplo) seguir dibujando en un punto específico, algo que
Código (vb) [Seleccionar]

' Devuelve o establece las coordenadas verticales para el siguiente método Print o Draw.
Public Property Get CurrentY() As Single
    CurrentY = UserControl.CurrentY
End Property
    Public Property Let CurrentY(ByVal Y As Single)
        UserControl.CurrentY = Y
    End Property

' Devuelve o establece las coordenadas horizontales para el siguiente método Print o Draw.
Public Property Get CurrentX() As Single
    CurrentX = UserControl.CurrentX
End Property
    Public Property Let CurrentX(ByVal X As Single)
        UserControl.CurrentX = X
    End Property


Como hablamos de una colección lógicamente hacen falta dos cosas para ello, además operaciones en la colección: añadir, eliminar, vaciar...
Aquí un ejemplo para añadir:
Código (vb) [Seleccionar]

' Añade los datos de una orden gráfica en la posición indicada y devuelve el valor de dicha posición. Si el índice está fuera de rango, lo añade al final.
' OJO: No verifica si la orden existe o no, al dibujar, si no existe, o un parámetro no es válido, se ignora... y continúa con el siguiente.
'   Puede ser mejor desde aquí señalar que es erróneo... o devolver false, y el index devolverlo por referencia.
' DibujarAhora: fuerza a dibujar ahora mismo la orden gráfica, aunque en general es mejor almacenarlas y luego dibujarlas.
Public Function PathsAñadirIndex(ByRef Graf As DatosGraficos, Optional ByVal Index As Long = -1, Optional ByVal DibujarAhora As Boolean = False) As Long
    If ((Index < 0) Or (Index > ColGrPaths.Count)) Then
        Index = (ColGrPaths.Count + 1) ' en ambos casos se añade al final
    End If
   
    Call ColGrPaths.Add(Graf, , Index)

    If (DibujarAhora = True) Then
        Call Me.DibujarOrden(Graf)
        RaiseEvent Actualizado
    End If
   
    PathsAñadirIndex = Index
End Function



También es adecuado contar con otras operaciones menos frecuentes, pero igualmente útiles...
Aquí remplazar (una existente por otra que se entrega), y una que intercambia el orden de dos (el orden almacenado supone el orden en que se dibujan).
Código (vb) [Seleccionar]

' Remplaza un ítem gráfico (orden), que consta en la colección por otra orden procedente del exterior. Devuelve True, si el íitem existe.
Public Function PathsRemplazar(ByVal Index As Long, ByRef Graf As DatosGraficos) As Boolean
    If (EnRango(Index) = True) Then
        Call ColGrPaths.Add(Graf, , Index)
        Call ColGrPaths.Remove(Index + 1)
        PathsRemplazar = True
    End If
End Function

' Intercambia dos ítems (órdenes gráficas), de posición entre sí. Devuelve True, si ambos ítems existen.
Public Function PathsIntercambiar(ByVal Index As Long, ByVal PorIndex As Long) As Boolean
    Dim g As DatosGraficos
   
    If (EnRango(Index) = True) Then
        If (EnRango(PorIndex) = True) Then
            With ColGrPaths
                g = .Item(Index)
                .Item(Index) = .Item(PorIndex)
                .Item(PorIndex) = g
            End With
            PathsIntercambiar = True
        End If
    End If
End Function


También puede suceder que uno no quiera dibujar en orden todo, sino solo ciertas órdenes... puede construirse funciones que recorriendo la colección solo dibuje determinadas funciones, si es complicado y exige ciertos condicioonantes muy variables, se puede reclamar una enumeración de la colección y entonces en la entrega evaluar si debe o no dibujarse:
Código (vb) [Seleccionar]

' Enumera los ítems de la colección (por evento) desde el índice indicado hasta el final, en la dirección señalada. Es posible cancelar cuando se desee. Cuando llega al último ítem, lo indica expresamente.
Public Function PathsEnumerar(ByVal DesdeIndex As Long, Optional ByVal HaciaAtras As Boolean = False) As Boolean
    Dim k As Long, Cancelar As Boolean, Final As Long
    Dim dir As Long
    Dim g As DatosGraficos
   
    If (EnRango(DesdeIndex) = True) Then
        ' Con solo esto, podemos recorrer la colección enambas direcciones, el bucle apenas sufre cambios.
        If (HaciaAtras = False) Then    ' desde index hasta el final.
            Final = (ColGrPaths.Count - 1): dir = 1
        Else                            ' desde index hasta el 1º
            Final = 2: dir = -1
        End If
           
        ' si el index es el final, no entra en el bucle
        Do While (DesdeIndex <> Final)
            g = ColGrPaths.Item(DesdeIndex)
            RaiseEvent Listado(DesdeIndex, g, Cancelar, False)
            If (Cancelar = True) Then Exit Do
            DesdeIndex = (DesdeIndex + dir)
        Loop
        ' aunque se salga del Do...Loop, sabemos si se canceló porque el índice no llegó a sumar hasta el final.
        '   luego lo enviamos ahora, y ahora da igual que cancele, ya no hay más...
        If (DesdeIndex = Final) Then
            g = ColGrPaths.Item(Final)
            RaiseEvent Listado(Final, g, False, True) ' indicamos que es el final...
        End If
       
        PathsEnumerar = True ' también podría devolver el nº de ítems enviados.
    End If
End Function


Se ha mostrado algún evento... el control puede proveer algunos eventos, como cuando termina de redibujartodo, por si se precisa hacer algo desde fuera, como activar algún botón, etc...
Código (vb) [Seleccionar]

' Ocurre cada vez que se actualiza la Imagen.
Public Event Redibujado()
' Ocurre cada vez que se actualiza la imagen, cuando se reclama dibujar una sola orden gráfica.
Public Event Actualizado()
' Ocurre cuando se reclama una peración de Listar Paths (órdenes gráficas), adecuado cuando se deban modificar, algunos ítems.
Public Event Listado(ByVal Indice As Long, ByRef Grafico As DatosGraficos, ByRef Cancelar As Boolean, ByVal Final As Boolean)



Con el valor activo, puedes desactivar que un método gráfico no se dibuje la próxima vez, etc...
Como ves, un control así permite almacenar muchos métodos gráficos contiene todos los datos precisos para dibujar, pero no alcanza ni sobrepasa límites impuestos, además permite aislar adecuadamente unos gráficos de otros, por ejemplo un único control podría contener todos los métodos gráficos para dibujar la escalera... añadiendo además por ejemplo una función GrEscala(byval Escala as single), podría tomar toda la colección de métoso y rescalar su 'ancho y alto' o sólo a aqellos métodos que sean de cierto tipo... igualmente moverlos todos de sitio sería desplazar el control, pero mover a determinados objetos de sitio, podría hacer otra función que recorra la colección para añadir restar a las cordenadas un valor específico...

...y fíjate que sin embargo todo ese código, está en VB6 "puro", sin APIs, recurriendo a las APIs, sería más potente... (gráficamente VB6 es bastante pobre, no es esforzaron demasiado durante el diseño de VB, de dotarle de buneas funcionalidades) pero asumo que no dominas el mundo de las API.
#2347
Al inicio de Internet, la queja d eklas empresas de software (como microsoft) es que querían ver más presencia empresarial en la red, ya que ahasta el momento, la red parecía tener solo fines educativos...
Tímidamente fueron asomando la cabeza diferentes facetas de la vida, hasta que al final emergió el mundo empresarial...
Y así llegamos hasta esta época donde parece que la única finalidad de la RED es única y exclusivamente empresarial, es decir es como si fuera un diseño por y para las empresas donde el resto son intrusos y que por tanto, hay que eliminar o exigirles que paguen de alguna manera...


En estos casos yo siempre abogo por lo mismo, cifrado, cifrado y más cifrado... y nada de software de grandes compañías, a cada caso algo diseñado específicamente, cuánto más específico mejor, cuantos más diseños mejor...


...cuando entiendan que el mundo no tiene ni gente ni máquinas suficientes para espiar, a lo mejor entienden que lo mejor es dejarlo en paz. ...pero mientras crean tener el poder y poder controlarlo, todo, la tentación de intentarlo es demasiado grande... cifremos, pués.
#2348
Ya... vacantes sin rellenar...

Personal cualificado hay de sobra, lo que falta es personal que acepte que le paguen una miseria teniendo un currículum por la nubes.

Las empresas quieren astronautas al precio de barrenderos, así por supuesto que seguirán vacantes...
#2349
Es que éste tipo, es como un elefante 'hociqueando' en una farmacia... a cada paso que dá, rompe todo a su paso...

Si hay un conflicto armado en Venezuela que sea por que esa es la solución que elija el propio pueblo venezolano (pienso yo), no por intervención externa.
#2350
Un poco más tarde miro el vídeo, ahora tengo solo justo un ratito libre...

Bien... ya me has contestado...
Todo apunta a que el problema es el que asumía... 246 controles en el form... luego en efecto la causa es alcanzar el límite de controles para el formulario...
pero, vamos ahora a encasillarlo exactamente...

En la función que te origina el error, coloca algo de código similar a esto:
Código (vb) [Seleccionar]

private function tufuncionCargandocontroles
   On local error goto CuentameLosControles

   '... aquí tu código...


  Exit function ' ó Sub
CuentameLosControles:
   Call MsgBox(CStr(Me.Controls.Count))
End function


Lós métodos gráficos, circle, line, no son problema, pero ojo, no confundas los métodos gráficos con los 'controles de usuario': line, shape, label, image y frame, todos ellos son 'irreales', pero ocupan puesto como control de usuario...

A la noche que llegue a casa, miro el vídeo y te pongo un ejemplo de operativo...